千家信息网

C++临时对象实例分析

发表于:2025-11-10 作者:千家信息网编辑
千家信息网最后更新 2025年11月10日,这篇"C++临时对象实例分析"文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇"C++临时
千家信息网最后更新 2025年11月10日C++临时对象实例分析

这篇"C++临时对象实例分析"文章的知识点大部分人都不太理解,所以小编给大家总结了以下内容,内容详细,步骤清晰,具有一定的借鉴价值,希望大家阅读完这篇文章能有所收获,下面我们一起来看看这篇"C++临时对象实例分析"文章吧。

    一、初探临时对象

    1.问题

    下面的程序输出什么?为什么?

    下面编写程序进行实验:

    #include class Test {    int mi;public:    Test(int i) {        mi = i;    }    Test() {        Test(0);    }    void print() {        printf("mi = %d\n", mi);    }};int main(){    Test t;    t.print();    return 0;}

    输出结果如下:

    程序意图:

    • 在 Test() 中以 0 作为参数调用 Test(int i)

    • 将成员变量 mi 的初始值设置为 0

    运行结果:

    • 成员变量 mi 的值为随机值

    2.思考

    构造函数是一个特殊的函数

    • 是否可以直接调用?

    • 是否可以在构造函数中调用构造函数?

    • 直接调用构造函数的行为是什么?

    3.答案

    • 直接调用构造函数将产生一个临时对象

    • 临时对象的生命周期只有一条语句的时间(过了这条 C++ 语句,临时对象将被析构而不复存在)

    • 临时对象的作用域只在一条语句中

    • 临时对象是 C++ 中值得警惕的灰色地带

    可以将上面代码写成这样,避免临时对象:

    #include class Test {    int mi;    void init(int i)    {        mi = i;    }public:    Test(int i) {       init(i);    }    Test() {       init(0);    }    void print() {        printf("mi = %d\n", mi);    }};int main(){    Test t;    t.print();    return 0;}

    输出结果如下:

    再来看一个程序,深刻体会一下临时对象:

    #include class Test {    int mi;    void init(int i)    {        mi = i;    }public:    Test(int i) {        printf("Test(int i)\n");        init(i);    }    Test() {        printf("Test()\n");        init(0);    }    void print() {        printf("mi = %d\n", mi);    }    ~Test()    {        printf("~Test()\n");    }};int main(){    printf("main begin\n");    Test();    Test(10);    printf("main end\n");    return 0;}

    输出结果如下:

    这个程序很好的说明了临时对象的生命周期只有一条语句的时间(过了这条 C++ 语句,临时对象将被析构而不复存在)

    二、编译器的行为

    现代 C++ 编译器在不影响最终执行结果的前提下,会尽力减少临时对象的产生!!!

    下面来看一个例子:

    #include class Test{    int mi;public:    Test(int i)    {        printf("Test(int i) : %d\n", i);        mi = i;    }    Test(const Test& t)    {        printf("Test(const Test& t) : %d\n", t.mi);        mi = t.mi;    }    Test()    {        printf("Test()\n");        mi = 0;    }    int print()    {        printf("mi = %d\n", mi);    }    ~Test()    {        printf("~Test()\n");    }};Test func(){    return Test(20);}int main(){    //Test t(10); 等价于 Test t = Test(10);    Test t = Test(10); // ==> Test t = 10;    Test tt = func();  // ==> Test tt = Test(20); ==> Test tt = 20;    t.print();    tt.print();    return 0;}

    输出结果如下:

    注意两点:

    • 通过输出结果可以看到【编译器并没有按照生成临时对象,再用临时对象初始化 t 对象(其中涉及调用拷贝构造函数)】的步骤,因为现代的编译器都会尽力避免临时对象的产生。

    • Test t = Test(10); 等价于 Test t = 10; 写成Test t = 10; 可以杜绝临时对象的产生。因为临时对象的产生会带来性能上的问题,Test t = Test(10); 相当于调用了两次构造函数, 而 Test t = 10; 少调用一次函数,性能得到提升。

    以上就是关于"C++临时对象实例分析"这篇文章的内容,相信大家都有了一定的了解,希望小编分享的内容对大家有帮助,若想了解更多相关的知识内容,请关注行业资讯频道。

    0