问题引入

cout << (uf.is_same_set(x, y)) ? 'Y' : 'N'<<endl;

请问大家,这条语句对吗?(这里的uf.is_same_set(x, y)是一个自定义函数,返回bool值;所以不是问题的关键)==》

答案是这条语句报错了。我再写了以下的语句,却能准确无误。

  cout << ((uf.is_same_set(x, y)) ? 'Y' : 'N') << endl;

为什么呢? ==》

1.这是因为第一条语句中,<<的优先级会高于三目运算符,即它先返回的是 ostream&;

然后会再执行ostream?'Y':'N'部分;三目判断返回'Y'

但是'Y' 是 char 类型,不是一个可以用 << 运算的对象。

2.cout << ((uf.is_same_set(x, y)) ? 'Y' : 'N') << endl; 这个表达式会先执行三目,返回‘Y’或者‘N’;然后变为:cout<<'Y'<<endl; 所以就没有错。

基于这个问题,我们今天就来聊聊cout

cout是什么?

cout 是一个全局的 输出流对象,本质上是 ostream 类的一个实例,通过 运算符重载(operator<<,实现了类似 cout << x 这样的打印效果。

此外还有其他流对象是:

名称类型功能
cinistream标准输入流
cerrostream错误输出流
clogostream日志输出流

为什么能用 << 打印?

这是 C++ 的经典设计:通过重载运算符 <<(插入运算符)来模拟输出操作。它的原型类似于这样:即它使重载的运算符函数;

ostream& operator<<(ostream& os, int value);
ostream& operator<<(ostream& os, const char* str);
ostream& operator<<(ostream& os, char c);
ostream& operator<<(ostream& os, double d);
ostream& operator<<(ostream& os, bool b);
// 等等,针对不同类型都做了重载

这就意味着你可以这样使用:

cout << "Hello" << ' ' << 42 << ' ' << true;

它的底层执行顺序是:

cout << "Hello"          // 返回 ostream&<< ' '             // 继续插入<< 42              // 继续插入<< ' '             // ...<< true;           // 一连串流式操作

因为每次 << 都返回 ostream&,所以可以链式调用。


输出是怎么“流”到控制台的?

cout 内部持有一个缓冲区(buffer),你每调用一次 <<,其实是将数据写入这个缓冲区。只有当你:

  • 显式使用 endl(刷新并换行);

  • 或缓冲区满;

  • 或程序结束前清理资源;

才会真正把内容输出到终端控制台所以我们便能理解下面两条语句的区别了。

cout << "hello\n";       // 可能只是写进缓冲区
cout << "world" << endl; // 此时强制刷新缓冲区

endl 是什么?

endl 是一个特殊的东西,它不是字符串,而是一个 函数指针,原型是:

ostream& endl(ostream& os);

它的作用是:

  1. 向流中插入一个换行符(\n);

  2. 刷新缓冲区(flush);

所以cout << "Hello" << endl; 等价于:

cout << "Hello";
cout.put('\n');
cout.flush();

自定义类型如何支持 << 输出?

你可以为你的类自己写一个 << 重载,让 cout << 对象 成为可能:

class Person {
public:string name;int age;
};
​
// 重载 <<
ostream& operator<<(ostream& os, const Person& p) {os << "Name: " << p.name << ", Age: " << p.age;return os;
}

这样你就能这样写:

Person p{"麦兜", 20};
cout << p << endl;

ok,这个知识点实际上涉及到了运算符重载函数的编写;我先说一个结论:

operator<<必须写成全局函数(或友元函数),为什么呢?

因为 cout << p 是这样调用的:operator<<(cout, p); // ostream 是左边,Person 是右边

如果你写成:

class Person { ostream& operator<<(ostream& os); // 错误!只能是 p << cout 
};

这就变成了 p << cout,方向颠倒了,所以没法实现 cout << p 的语法。

故哪些运算符建议写成成员函数?哪些建议全局?

运算符类型推荐形式说明
=, [], (), ->成员函数这些操作符需要访问类的内部状态或作用于“左侧对象本身”
<<, >>, +, -, ==, !=全局函数或友元函数左侧不是类对象(如 cout << obj),或需要双操作数对称性

cout的使用技巧

  1. 运算符优先级陷阱 (如我们上面的问题)

  2. 输出 bool 值时注意格式

cout << true << endl;      // 输出: 1
cout << boolalpha << true << endl;  // 输出: true ✅

   3.输出字符和整数要区

    char ch = 'A';
    int x = 65;
    cout << ch << endl;     // 输出: A
    cout << static_cast<int>(ch) << endl;  // 输出: 65

    4.其他格式化技巧:

    我们需要加上 头文件: #include <iomanip>

    1) 设置小数精度 ;如上

    2) 宽度对齐 & 填充字符

    cout << setw(10) << 42 << endl;         // 宽度为10,默认右对齐
    cout << setfill('*') << setw(10) << 42 << endl;  // 输出:********42

    3)左右对齐

    cout << left << setw(10) << 42 << endl;   // 左对齐
    cout << right << setw(10) << 42 << endl;  // 右对齐

    4) 输出十六进制/八进制

    cout << hex << 255 << endl;  // ff
    cout << oct << 255 << endl;  // 377
    cout << dec << 255 << endl;  // 255 (恢复十进制)

    显示符号位(正数也带 + )

    cout << showpos << 123 << endl;  // +123

    再次理解

    运算符重载是指可以自定义某个类使用某个运算符的逻辑,譬如+,-,*等等。

    而<<这个运算符也是可以被重载的;例如ostream类就是重载了这个运算符 。

    cout是ostream的一个对象,它使用<<能够将数据写入这个缓冲区。

    实际上cout<<10是operator<<(cout, 10);的语法糖。即他本质上是调用了operator<<,并把要打印的东西(整数,浮点数,字符,字符串)作为参数。

    而这个运算符重载函数返回的是ostream&,即引用类型,则他可以实现链式调用;

    本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
    如若转载,请注明出处:http://www.pswp.cn/bicheng/85335.shtml
    繁体地址,请注明出处:http://hk.pswp.cn/bicheng/85335.shtml
    英文地址,请注明出处:http://en.pswp.cn/bicheng/85335.shtml

    如若内容造成侵权/违法违规/事实不符,请联系英文站点网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

    相关文章

    山东大学项目实训-创新实训-法律文书专家系统-项目报告(八)

    项目实训博客 : 项目后端架构 , 项目的四端交互(前端 ,后端 ,模型端 ,数据库)的开发和维护 , 项目功能总览 作为项目的后端和前端交互功能主要开发者,我需要对项目的四端交互进行开发和维护. 总览: 整体项目结构如图所示: 前后端的交互: 前端封装了request.js : 方便前端…

    12.8Java Swing 中的MVC

    在 Java Swing 中&#xff0c;MVC 模式被广泛应用。例如&#xff0c;JTable、JList 等组件都采用了这种模式。通常&#xff1a; 模型&#xff1a;实现特定的 Swing 模型接口&#xff08;如 TableModel、ListModel&#xff09;。视图&#xff1a;是 Swing 组件本身&#xff08;…

    DDS(Data Distribution Service)

    DDS&#xff08;Data Distribution Service&#xff09;是一种以数据为中心的发布/订阅&#xff08;DCPS&#xff09;通信中间件协议栈标准&#xff08;由OMG组织维护&#xff09;。它专为高性能、可预测、实时、可靠的分布式系统设计&#xff0c;广泛应用于国防、航空航天、工…

    python爬虫关于多进程,多线程,协程的使用

    简介&#xff1a; python其实没有真正意义的多线程&#xff0c;因为有GIL锁存在&#xff0c;但是python3.13去掉GIL锁&#xff0c;有两个版本&#xff0c;python3.13t和python3.13&#xff0c;python3.13去掉GIL锁相当于python底层大规模改变&#xff0c;肯定会影响一些库的使…

    java 设计模式_行为型_23状态模式

    23.状态模式 Java中的状态设计模式是一种软件设计模式&#xff0c;当对象的内部状态更改时&#xff0c;该模式允许对象更改其行为。状态设计模式通常用于以下情况&#xff1a;对象取决于其状态&#xff0c;并且在运行期间必须根据其内部状态更改其行为。状态设计模式是许多行为…

    Flink CDC MySQL 时区相差 8 小时问题优雅解决方式

    Flink CDC MySQL 时区相差 8 小时问题解析 代码运行环境 Flink 1.15 + FlinkCDC 2.4.0 + jdk1.8 +springboot 2.31、原因分析 Flink CDC 底层使用 Debezium 连接器来捕获 MySQL 的数据变更,而 Debezium 在解析 MySQL 的 binlog 日志时,默认使用 UTC 时区来处理时间字段。若…

    如何在 MX Linux 上安装 Blender CAD 软件

    Blender 是一款免费且开源的 CAD 软件,可用于 3D 动画、建模、动态图形、纹理处理、电脑游戏、UV 展开等。同时它也是一款专业的开源程序,是商业软件(如 Maya 或 Cinema 4D)的替代品,支持导入或导出标准格式,如 OBJ、FBX、3DS、PLY 和 STL。Blender 还可以作为视频编辑软…

    电脑上的.ssh目录只做什么的

    .ssh 目录的作用和来源 系统自动创建 这个目录是在你第一次使用SSH相关功能时自动创建的比如第一次执行 ssh 命令连接服务器时或者使用Git通过SSH协议克隆代码时 主要用途 SSH密钥存储 - 存放公钥/私钥对已知主机记录 - known_hosts 文件记录你连接过的服务器指纹SSH客户端…

    Excel大厂自动化报表实战(互联网金融-数据分析周报制作下)

    这是Excel大厂自动化报表实战第四期--互联网金融-数据分析周报制作下 数据资源已经与这篇博客捆绑&#xff0c;有需要者可以下载通过网盘分享的文件&#xff1a;2.4自动化报表-8月成交数据.xlsx&#xff0c;2.4自动化报表-8月获客数据.csv等2个文件 链接: https://pan.baidu.c…

    界面组件DevExpress WPF中文教程:Grid - 节点(Nodes)概述

    DevExpress WPF拥有120个控件和库&#xff0c;将帮助您交付满足甚至超出企业需求的高性能业务应用程序。通过DevExpress WPF能创建有着强大互动功能的XAML基础应用程序&#xff0c;这些应用程序专注于当代客户的需求和构建未来新一代支持触摸的解决方案。 无论是Office办公软件…

    开源统一数据库管理平台完全指南:私有化部署方案与技术解析

    摘要:面对MySQL、Oracle、Redis等混合数据库环境,如何实现统一管控?本文深度评测5大开源平台,附私有化部署方案和性能对比。 一、核心需求场景与技术选型 典型痛点: #mermaid-svg-LuCYYyJjBakpzzFH {font-family:"trebuchet ms",verdana,arial,sans-serif;font…

    hot100 -- 14.贪心算法

    1.买卖股票的最佳时机 方法&#xff1a; def MaxProfit(prices):max_pro, min_num 0, float(inf)for num in prices:if num < min_num:min_num nummax_pro max(max_pro, num - min_num)return max_pro 2.跳跃游戏 问题&#xff1a; 给你一个非负整数数组 nums &#…

    Celery+fastAPI/Flask实现高性能应用

    本文在创作过程中借助 AI 工具辅助资料整理与内容优化。图片来源网络。 引言 大家好&#xff0c;我是沛哥儿。 在当今的软件开发领域&#xff0c;异步任务处理和高效的 Web 开发框架是提升应用性能和可扩展性的关键因素。Celery 作为一个强大的分布式任务队列系统&#xff0c;…

    【音视频】PJSIP库——pjsua命令使用详解

    1、源码编译 1)安装依赖库 sudo apt install libsrtp2-dev sudo apt install libopus-dev alsa-tools libalsaplayer-dev ffmpeg libalsa* pulseaudio-module-jack sudo apt install jackd libjack-jackd2-dev libjack-dev libsdl2-dev libv4l-dev libavcodec-dev libavde…

    Python实例题:图片批量处理工具

    目录 Python实例题 题目 问题描述 解题思路 关键代码框架 难点分析 Python实例题 题目 图片批量处理工具 问题描述 开发一个 Python 工具&#xff0c;实现以下功能&#xff1a; 遍历指定文件夹下的所有图片文件&#xff08;支持常见格式如 jpg、png、webp&#xff0…

    超图superMap iObjects for Java的Jar使用中遇到的问题

    一、 cannot open shared object file: No such file or directory 1. 问题 2. 解决方法 &#xff08;1&#xff09;检查有没有配置环境变量 PATH &#xff08;2&#xff09;创建软连接 ln -s &#xff08;3&#xff09;将主机 /usr/lib64 目录中的libgomp.so.1 复制到 /pla…

    常见的蓝牙5.0抗干扰技术和算法

    常见的蓝牙5.0抗干扰技术和算法&#xff1a; 跳频扩频&#xff08;Frequency Hopping Spread Spectrum, FHSS&#xff09; 通过在不同的频率通道上快速切换数据传输&#xff0c;减少与固定频率干扰源的冲突。 直接序列扩频&#xff08;Direct Sequence Spread Spectrum, DSSS&…

    牛客与Moka深化合作,升级AI面试对接,引领招聘变革

    近日&#xff0c;AI 招聘平台牛客与国内领先的人力资源全模块平台 Moka 宣布完成 AI 面试产品的全新对接升级。此次升级实现了从 Moka 到牛客的一键互绑&#xff0c;并打通了简历出题、风险点提问、优势技能挖掘等核心功能&#xff0c;为企业提供更加高效智能的面试体验。 这一…

    Vue 3 路由跳转全面指南(Composition API + <script setup>)

    一、前言&#xff1a;为什么要学习 Vue Router&#xff1f; 在单页面应用(SPA)开发中&#xff0c;路由管理是核心功能之一。Vue Router 作为 Vue.js 官方推荐的路由解决方案&#xff0c;与 Vue.js 深度集成&#xff0c;提供了以下重要功能&#xff1a; 页面无刷新跳转&#x…

    JavaScript基础-常用的键盘事件

    一、前言 在网页开发中&#xff0c;用户交互 是非常重要的一环。除了鼠标操作之外&#xff0c;键盘事件也是前端开发中最常见的交互方式之一。 JavaScript 提供了多个用于监听和处理键盘输入的事件&#xff0c;例如 keydown、keyup 和 keypress。掌握这些事件可以帮助我们实现…