2009-10-06 131 views
5
初始化临时聚合对象

比方说,我有一个类:使用大括号

class Aggregate { 

public: 

    int x; 
    int y; 

}; 

我知道如何使用大括号来初始化的对象:

Aggregate a1 = { 1500, 2900 }; 

但我不能找到一个合适的语法来创建临时对象,并将其传递作为参数传递给一些方法,例如:

void frobnicate(const Aggregate& arg) { 
    // do something 
} 

//... 

frobnicate(Aggregate {1500, 2900}); // what should this line look like? 

最简单的方法会将构造函数添加到Aggregate类,但是让我们假设我没有访问Aggregate标题的权限。另一个想法是写某种工厂方法,即

Aggregate makeAggregate(int x, int y). 

我还可以创建一个对象,然后将其作为参数传递,等等,等等

解决方法有很多,但我我只是好奇,如果有可能实现这个目标使用大括号初始化。

+0

呃......如果你没有访问标题,你不能假定对象可以使用大括号初始化,可以吗? – unwind 2009-10-06 12:36:44

+3

实际上,makeXXX方法并没有那么糟糕。最近的编译器能够应用NRVO(命名的返回值优化),从而导致高效的代码。当应用NRVO并且内联函数时,就效率而言,这相当于C++ 0x语法。 – sellibitze 2009-10-06 13:14:20

回答

8

你想要的是C++ 0x初始值设定项列表。

class Aggregate { 
public: 
    int x, y; 
}; 

void frobnicate(const Aggregate& arg) { 

} 

int main() { 
    frobnicate({1, 2}); 
    return 0; 
} 

GCC 4.4已经支持-std=c++0x这个标志。可能VS2010 CTP也支持这个(纠正我,如果我错了)。使用C++ 98/C++ 03,你将不得不编写和调用构造函数。

1

“有很多解决方案,但我只是好奇如果可以使用大括号初始化来实现这个目标。”

不可能。如果你不能改变源那么你唯一的选择是包装在一个内联函数或辅助结构:

struct AggregateHelper 
{ 
    Aggregate a; 
    AggregateHelper(int x, int y) { a.x=x; a.y=y; } 
    operator const Aggregate&() { return a; } 
}; 

frobnicate(AggregateHelper(1500,2900)); 

编辑:去除不相关的构造解决方案。

+0

但是,这也会将类型的属性从聚合(以及本例中的POD)更改为非聚合。这可能不会被期望,并且它需要搜索并替换所有以前的{}初始化。 – 2009-10-06 12:53:02