在不调用initializer_list构造函数的情况下,将不可复制的不可移动类型构造为函数参数

时间:2014-03-24 22:19:40

标签: c++ c++11 initializer-list

#include <initializer_list>
#include <iostream>

namespace {

class C {
public:
    C(C const &) = delete;
    C(C &&) = delete;
    C(int) {
        std::cout << "int\n";
    }
    C(std::initializer_list<int>) {
        std::cout << "initializer\n";
    }
};

void f(C) {
}

// Compiles and prints "initializer" when called
C g() { return {0}; }
// Fails to compile
// C h() { return 0; }

}   // namespace

int main() {
    // Compiles and prints "initializer"
    f({0});
    // Fails to compile
    // f(0);
}

是否可以在不调用initializer_list构造函数的情况下将C(不可复制的,不可移动的类型)构造成函数参数或函数返回值?

1 个答案:

答案 0 :(得分:2)

只有你可以改变C,才能选择所需的构造函数而不是初始化列表构造函数,例如:通过将参数类型包装在不可转换为initializer-list构造函数的元素类型的内容中:

#include <initializer_list>
#include <iostream>

namespace {

template<class T>
struct wrap
{
  T value;
};

class C {
public:
    C(C const &) = delete;
    C(C &&) = delete;
    C(wrap<int>) {
        std::cout << "int\n";
    }
    C(std::initializer_list<int>) {
        std::cout << "initializer\n";
    }
};

void f(C) {
}

// Compiles and prints "int" when called
C g() { return {wrap<int>{0}}; }

}   // namespace

int main() {
    // Compiles and prints "int"
    f({wrap<int>{0}});
    g();
}

打印:

int
int