我的代码如下。
struct conv{
struct des
{
des(int a) {}
des(int a, int b) {}
des(int a, int b, int c) {}
};
};
int main(int argc, const char * argv[]) {
int a = 1;
int b = 1;
int c = 1;
if (a > 1)
{
auto conv_desc = conv::des(1, 2, 3);
} else if(b > 1) {
auto conv_desc = conv::des(1, 2);
} else {
auto conv_desc = conv::des(1);
}
return 0;
}
代码的模式是从mkldnn中提取的。我唯一想做的就是从if-else语句中取出auto conv_desc。我试图从if-else语句中声明auto conv_desc。它发生了一个错误:声明
带有推导类型'auto'的变量'conv_desc'需要初始值设定项
获取'conv :: des'类型的临时对象的地址
如果我无法解决这个问题,我将不得不在每个分支中写一大段重复的代码。
将您的if
代码移动到单独的函数中:
conv::des make_des(int a, int b) {
if (a > 1) {
return conv::des(1, 2, 3);
} else if(b > 1) {
return conv::des(1, 2);
} else {
return conv::des(1);
}
}
int main(int argc, const char * argv[]) {
int a = 1;
int b = 1;
int c = 1;
auto conv_desc = make_des(a, b);
return 0;
}
您也可以使用立即调用的lambda。这是一种常见的模式,可以在某些变量不可能的情况下使其成为常量。
这个解决方案与@yachoor回答非常相似,但使用的是lambda。
int main(int argc, const char * argv[]) {
int a = 1;
int b = 1;
int c = 1;
// Kind of an inline function that is called immediately
auto const conv_desc = [&]{
if (a > 1) {
return conv::des(1, 2, 3);
} else if(b > 1) {
return conv::des(1, 2);
} else {
return conv::des(1);
}
}();
// Parens calls the function
return 0;
}
如果将if ... else
链移动到单独的函数中,则可以使用return
struct conv
{
struct des
{
des(int a) {
}
des(int a, int b) {
}
des(int a, int b, int c) {
}
};
};
conv::des make_conv_des(int a, int b)
{
if (a > 1) {
return conv::des(1, 2, 3);
} else if(b > 1) {
return conv::des(1, 2);
} else {
return conv::des(1);
}
}
int main(int argc, const char * argv[]) {
int a = 1;
int b = 1;
auto conv_des = make_conv_des(a, b);
return 0;
}
好像你使代码过于复杂。目前尚不清楚为什么要以这种方式区分这三种构造函数。为什么不使用这样的默认值来隐藏对象内部的复杂性?
struct conv{
struct des
{
des(int a, int b = 0, int c = 0) {
if(a > 1) {
/// do some logic
} else if(b > 1) {
// do some logic
} else {
// do some logic
}
}
};
};
int main(int argc, const char * argv[]) {
int a = 1;
int b = 1;
int c = 1;
auto conv_desc = conv::des(a, b, c);
return 0;
}
不要使用汽车。如果您需要声明一个变量并且还无法分配值,则无法使用auto。
int main(int argc, const char * argv[]) {
// ...
conv::des conv_desc; // calls default constructor.
if (a > 1)
{
conv_desc = conv::des(1, 2, 3);
} else if(b > 1) {
conv_desc = conv::des(1, 2);
} else {
conv_desc = conv::des(1);
}
// conv_desc is initialized at this point.
return 0;
}
你不能使用像这样的指针
int *a;
{ // new scope
int b = 5;
a = &b; // error.
}
// b is no longer in scope here
当b
超出范围时,a
将指向b
曾经的地址,现在不再有效。
如果你想使用指针,那么你可以使用new。但是,在这种情况下,您必须在之后释放内存。
int main(int argc, const char** argv)
{
conv::des *conv_desc = nullptr; // does not call default constructor.
if (a > 1)
{
conv_desc = new conv::des(1, 2, 3);
} else if(b > 1) {
conv_desc = new conv::des(1, 2);
} else {
conv_desc = new conv::des(1);
}
if (conv_desc == nullptr) { /* memory allocation failed */ }
// conv_desc is initialized at this point.
// ...
// remember to delete conv_desc
if (conv_desc != nullptr) { delete conv_desc; conv_desc = nullptr; }
return 0;
}