【C++】:浅析 “std::cout << std::endl”

一、引子

std::cout << "Hello, world" << std::endl;

以上,作为任何一名接触过C++编程的朋友们来说,基本应该都是自己写下的第一行代码吧(别钻牛角尖,说什么头文件啥的)。

也许你也曾心里疑惑过,std::cout这也不是函数的表示方式啊,为啥他能这么写?也许你的老师也跟你说过,记住这个固定句式,它就这么写!然后,没有然后。你就这样已知遵循着“谆谆教诲”,教条式的传用了整个职业生涯~

本篇,作为打破你的思维,开始刨根问题的第N次分享,我们尽量深入浅出,更多的了解下std::cout << "Hello, world" << std::endl;,做到知其然,知其所以然。

二、鱼游浅底

2.1 cout是什么?

extern _CRTDATA2_IMPORT ostream cout;

cout 是什么? 对,它ostream类型的实例对象,而且是extern修饰的全局对象。

所以,既然是实例对象,我们还可以这样使用:

使用示例

#include <iostream>

int main() {
   
    std::ostream& out = std::cout; // std::cout is an instance of std::ostream
    out << "Hello, World!" << std::endl;
    return 0;
}

2.2 cout为何能直接 接<<操作符 ?

对象后面 直接接 << 操作符,这个不难联想,自然是有实现 << 操作符。
所以,我们简单看看ostream

using ostream       = basic_ostream<char, char_traits<char>>;

ostreambasic_ostream<char, char_traits<char>> 的一个类型别名。我们简单了解 下basic_ostream 类模板及其相关组件。

  1. basic_ostream 类模板:

    • basic_ostream 是 C++ 标准库中的一个类模板,用于表示输出流。它是一个通用的流类,可以与不同的字符类型和字符特性(traits)一起使用。
    • 模板参数包括字符类型(如 charwchar_t)和字符特性类(如 char_traits<char>)。
  2. char:

    • char 是 C++ 中的基本数据类型,用于表示单字节字符。
    • basic_ostream<char, char_traits<char>> 中,char 指定了流处理的字符类型。
  3. char_traits<char>:

    • char_traits 是一个特性类模板,定义了如何处理特定字符类型的操作。
    • char_traits<char> 提供了一组静态成员函数和类型,用于描述 char 类型字符的特性和操作,如比较、复制、查找等。
  4. using 声明:

    • using ostream = basic_ostream<char, char_traits<char>>; 是一种类型别名声明。
    • 它将 basic_ostream<char, char_traits<char>> 类型重命名为 ostream,使得代码更简洁和易读。

2.3 basic_ostream

在上面2.2 中我们已经了解到,iostream 其实只是类模版basic_ostream特化类型basic_ostream<char, char_traits<char>> 的别名,那么回到我们最开始的问题,为何能直接使用<< 操作符连接使用,答案不言而喻,必然存在<<的操作符函数,而且是多个函数的重载!!

说这话,我必然是有依据的。这里我为大家附上部分basic_ostream 中的代码:

 basic_ostream& __CLR_OR_THIS_CALL operator<<(
        basic_ostream&(__cdecl* _Pfn)(basic_ostream&) ) {
    // call basic_ostream manipulator
        return _Pfn(*this);
    }

    basic_ostream& __CLR_OR_THIS_CALL operator<<(_Myios&(__cdecl* _Pfn)(_Myios&) ) {
    // call basic_ios manipulator
        _Pfn(*this);
        return *this;
    }

    basic_ostream& __CLR_OR_THIS_CALL operator<<(ios_base&(__cdecl* _Pfn)(ios_base&) ) {
    // call ios_base manipulator
        _Pfn(*this);
        return *this;
    }

    basic_ostream& __CLR_OR_THIS_CALL operator<<(bool _Val) {
    // insert a boolean
        ios_base::iostate _State = ios_base::goodbit;
        const sentry _Ok(*this);

        if (_Ok) {
    // state okay, use facet to insert
            const _Nput& _Nput_fac = _STD use_facet<_Nput>(this->getloc());

            _TRY_IO_BEGIN
            if (_Nput_fac.put(_Iter(_Myios::rdbuf()), *this, _Myios::fill(), _Val).failed()) {
   
                _State |= ios_base::badbit;
            }
            _CATCH_IO_END
        }

        _Myios::setstate(_State);
        return *this;
    }

    basic_ostream
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

键盘会跳舞

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值