C++ 值和指针之间赋值的差异?

C++ 值和指针之间赋值的差异?,c++,C++,当我执行以下操作时,我发现紧密循环中存在巨大的性能差异: MyObject foo = bar.GetObject(); vs 其中,类函数的细节如下: class MyClass { MyObject someobject; MyObject& GetObject() { return someobject; } MyObject* GetObjectPtr() { return &someobject; } } bar; 第一行的作业比第二行慢得多。有人能解释

当我执行以下操作时,我发现紧密循环中存在巨大的性能差异:

MyObject foo = bar.GetObject();
vs

其中,类函数的细节如下:

class MyClass
{
  MyObject someobject;
  MyObject& GetObject() { return someobject; }
  MyObject* GetObjectPtr() { return &someobject; }
} bar;
第一行的作业比第二行慢得多。有人能解释一下发生了什么事吗?这与默认的副本分配有关吗?

特别是

  • 指针和引用在生成的机器代码中是相同的, 除了编译器可以在某些情况下使用 由于较少的别名乐趣,参考
  • 几乎可以肯定的是,没有任何分析数据表明这一行有问题。事实上,该变量甚至可能不存在于生成的机器代码中,而是直接访问的。这意味着,试图确定其性能对于所有相关人员来说都是巨大的时间浪费
  • 您的微基准测试代码在执行过程中完全有缺陷。即使是非优化编译器也会为这两行生成相同的结果。如果您发布了基准代码,我可以更具体一些

  • 发布的代码中真正的问题是出现了大量的封装冲突。

    如果您发布的代码确实是您测试的代码,那么您的测试方法肯定有问题,因为几乎任何现代编译器都会为这两个变体生成相同的代码(当然,不会产生任何形式的性能差异)


    如果您正在测试其他内容,那么您必须提供有关测试的更多详细信息。

    这两行应该做几乎相同的事情。您确定这不是代码中其他内容的产物吗?性能上的“巨大”差异是什么,您是如何测试的?您真的在做
    MyObject&foo=bar.GetObject()
    或者你真的在做
    MyObject&foo=…;foo=bar.GetObject();
    ?哦,天哪,我在上面打错了。我的意思是“MyObject-foo=…”.MyObject foo=…;和
    MyObject*foo=&…;
    其中一个设置指针,另一个创建副本,这可能涉及到任意大量的工作,包括非常缓慢的操作,如分配内存…我发布的代码是对我的项目的简化ss包含更多的成员函数。我注意到的问题与我提到的完全一样——返回引用比返回指针慢。我以紧密循环的方式运行每一行来验证这一点。@dracore:你的意思是你注意到了“更重”的差异循环,然后将源代码缩小到上面?抱歉,我不相信。即使某些编译器决定为上面的两个变体生成稍有不同的代码,在“更重”的版本中也不会注意到循环。不管怎样,你能发布编译器为紧循环生成的程序集吗?我的项目需要多次调用上述函数,这时我注意到,在使用第1行时,我感觉到性能明显下降。我只是试图理解是什么导致了这样的差异,因为我正在刮我的代码头。我想这可能与默认的副本分配有关……但老实说,我没有任何线索。@dracore:在这种情况下,人们犯的一个典型错误是他们使用
    MyObject foo=bar.GetObject()
    而不是
    MyObject&foo=bar.GetObject()
    ,即忘记接收端的
    &
    符号。这当然会对性能产生相当大的影响,因为它实际上是按值接收对象(即按复制构造函数复制结果).谢谢AndreyT!这就解决了它!这是我这边的一个错误..没有抓住这一点。原来问题中有一个输入错误,在这种情况下使用引用根本不像使用指针。实际代码显然是在比较指针赋值和复制构造函数。
    class MyClass
    {
      MyObject someobject;
      MyObject& GetObject() { return someobject; }
      MyObject* GetObjectPtr() { return &someobject; }
    } bar;