让我们想象一下,我们有一个结构可以容纳带有某些成员函数的3个double:
struct Vector {
double x, y, z;
// ...
Vector &negate() {
x = -x; y = -y; z = -z;
return *this;
}
Vector &normalize() {
double s = 1./sqrt(x*x+y*y+z*z);
x *= s; y *= s; z *= s;
return *this;
}
// ...
};
为了简化起见,这有点人为设计,但是我敢肯定您同意类似的代码已经存在。这些方法使您可以方便地进行链接,例如:
Vector v = ...;
v.normalize().negate();
甚至:
Vector v = Vector{1., 2., 3.}.normalize().negate();
现在,如果我们提供了begin()和end()函数,则可以在一种新的for循环中使用Vector,例如在3个坐标x,y和z上循环(您无疑可以构造更多“有用”的示例通过将Vector替换为例如String):
Vector v = ...;
for (double x : v) { ... }
我们甚至可以:
Vector v = ...;
for (double x : v.normalize().negate()) { ... }
并且:
for (double x : Vector{1., 2., 3.}) { ... }
但是,以下(在我看来)被破坏了:
for (double x : Vector{1., 2., 3.}.normalize()) { ... }
虽然这似乎是前两种用法的逻辑组合,但我认为最后一种用法会创建一个悬空的引用,而前两种用法完全可以。
- 这是正确的并且受到广泛赞赏吗?
- 上面的哪一部分是“不良”部分,应避免?
- 是否可以通过更改基于范围的for循环的定义来改进语言,以使在for表达式中构造的临时对象在循环持续时间内存在?