1

我经常遇到这种情况,你有一个临时变量,它的值需要修改,修改后你不需要访问旧值

// Find out if the jello will be jiggly
// at a certain time
bool IsJiggly( JelloType jello, float time )
{
    // JelloType has some weird overloads..
    jello = jello + time ; // I don't need the unrefrigerated jello,
    // _so I overwrite jello_..

    return jello.jiggles() ;
}

bool IsJiggly( JelloType jello, float time )
{
    JelloType jello2 = jello + time ; // I don't need the unrefrigerated jello,
    // but I create a new variable anyway, 
    return jello2.jiggles() ;
}

(我意识到上面的例子有些做作,即JelloType应该有一个成员函数operator+=..但情况不是!)

所以,问题是: _在 C++ 中,覆盖变量或创建一个新变量并使用它更好吗?

4

3 回答 3

1

编译器可能会在几乎所有情况下优化差异。

请注意,简单地调用您的函数会导致jello被复制。如果复制 aJelloType很便宜,那么就没有问题。如果它很昂贵,那么您可能应该将 const 引用传递给它。

在你的第二个例子中,你引入了jello2临时的,你——理论上——调用另一个复制构造函数。如果这有副作用,那么编译器将无法优化它。如果它没有副作用(一个好的复制构造函数不应该副作用),那么编译器可能会消除临时的(因为你的jello参数已经是一个临时副本)。

有时,制作副本是有意义的,例如,如果副本的名称有助于理解。如果该副本不能使代码更易于理解,并且您已经制作了一个临时副本,因为您传入的是副本而不是引用,那么我可能不会引入jello2.

于 2013-01-18T23:37:49.323 回答
1

您的代码可以通过删除临时对象并通过时间来发挥更好的编码风格来增强jiggles功能,也可以在返回 bool 时重命名为jigglesIsJiglly另外一个 const 引用应该足够了,而不是对象副本(也许编译器会优化掉副本?):

bool IsJiggly(const JelloType& jello, float time )
{
   return jello.IsJiggly(time);
}

如果编译器不删除副本,至少这个函数与你的两个函数相同可以收集更好的性能。并且它的功能设计更好,更直观,更易于维护。

在 C++ 中,覆盖变量或创建一个新变量并使用它会更好,性能明智吗?

这不是真正的语言问题,它取决于应用程序设计。如果 JeloType 是很小的对象,复制起来非常便宜(比复制引用便宜),那么我可能不在乎复制它。

于 2013-01-18T23:30:54.273 回答
0

好吧,我不得不说不,不,先生。

C++ 优于 C 和 C 优于普通机器代码的整个想法是为代码赋予一些人类可以理解的“含义”,并使编译器能够强制执行设计决策(函数可见性等)。特别是对于 C++,它允许您将变量和函数分组到可以与实际问题对象相关的“对象”中。如果有的话,优化应该是你脑子里最后一件事。与原始性能相比,您的项目更有可能因施工难度、错误和不可维护性而失败。

呜呜……

1)如果 jello 是一个简单的计数器,那么当然,你不需要保存旧值。我们都知道它会随时间递增,我们都知道 + 会做什么,并且我们在使用时都会小心。我只是建议将其称为 jelloTime 或其他名称。

2)如果果冻是一个对象,那么NOOO:

Jello 应是与“真实”业务对象相关的实体,因此:

a) + 不得用于添加时间或其他任何内容。任何人都无法知道这一点,果冻+时间对我来说毫无意义。(我的团队知道这不是一个有效的答案)。添加一个名为 .addFrozentTime() 的方法或其他方法。(避免 addTime(),仍然不清楚……)。

b) 此外,jello 将一些 jello 永远称为实体,因此方法永远不会改变对象的身份,只会改变它的状态。(享元是一个例外,但这不是重点)所以要么:

B1)您的评论是错误的:

// 我不需要未冷藏的果冻

它是不同状态下的同一个对象。说“果冻现在冷藏”并保留变量……</p>

或者

B2)代码错误:

果冻=果冻+时间

  • 创建一个不同的果冻,然后当然永远不要为新对象重用旧变量!稍后会有人来,但无法分辨,只是在错误的对象上调用 jello,xxx。

因此,答案是“视情况而定”,但无论哪种方式,您都需要修改代码。

我的 2 cts 我只是想帮忙。

于 2013-01-19T00:53:32.757 回答