这是这个问题的后续问题:声明constexpr initializer_list对象是否合法?.
从C++ 14开始,std::initializer_list该类的所有方法都标有constexpr.能够通过执行来初始化实例似乎很自然,
constexpr std::initializer_list<int> list = {1, 2, 3};
但是Clang 3.5抱怨list没有被常量表达式初始化.
正如dyp在评论中指出的那样,任何std::initializer_list文字类型的要求似乎都从规范中消失了.
如果我们甚至不能将类完全定义为constexpr,那么有什么意义呢?这是标准中的疏忽,将来会得到修复吗?
这里描述了为c ++提出的对象nullopt_t和对象:nulloptoptional
Run Code Online (Sandbox Code Playgroud)struct nullopt_t{see below}; constexpr nullopt_t nullopt(unspecified);[...]类型nullopt_t不应具有默认构造函数.它应该是文字类型.常量nullopt应使用文字类型的参数进行初始化.
其原因在文档的op = {}语法章节中进行了解释:为了op = {}明确一些必须采用的技巧,其中一个nullopt_t必须不是默认的可构造的.
我的问题是文字类型在这里意味着什么?我找到了这个SO帖子.所以在我看来,只有另一个空类才能做到.它也可以是一个构造函数int吗?
最小的整合nullopt_t课程会是什么样的?
像这样的东西:
struct nullopt_t_construct_tag_t{};
struct nullopt_t {
nullopt_t() = delete; // I know declaring it as deleted is redundant
constexpr nullopt_t(nullopt_t_construct_tag_t) {};
};
constexpr nullopt_t nullopt(nullopt_t_construct_tag_t{});
Run Code Online (Sandbox Code Playgroud)
或这个:
struct nullopt_t {
nullopt_t() = delete;
constexpr nullopt_t(int) {};
};
constexpr nullopt_t nullopt(0);
Run Code Online (Sandbox Code Playgroud) 在C++ Primer,第五版,§6.5.2中:
甲
constexpr函数被定义像任何其他的功能,但必须满足某些限制:返回类型和每一个参数的类型必须是文字型,和函数体必须只包含一个返回语句(第2.4.4节,第66页.)
但本章的另一句话(第239页):
允许constexpr函数返回不是常量的值
Run Code Online (Sandbox Code Playgroud)// scale(arg) is a constant expression if arg is a constant expression constexpr size_t scale(size_t cnt) { return new_sz() * cnt; }
这是一个矛盾的总结吗?我很困惑.
返回类型scale是文字类型?
更新:文字类型和常量之间有什么区别?
我有类似以下内容
class Base {
public:
explicit Base(int* i) noexcept { type = new int; *type = *i; };
constexpr Base(std::nullptr_t) : type(nullptr) { };
~Base() { cout << "Destroying!" << endl; delete type; };
protected:
int* type;
};
class Derived : public Base {
public:
explicit Derived(int* i) noexcept : Base(i) { };
//constexpr Derived(std::nullptr_t) : type(nullptr) { };
//constexpr Derived(std::nullptr_t) : Base(nullptr) { };
~Derived() { };
};
Run Code Online (Sandbox Code Playgroud)
我想constexpr为派生类实现一些null构造函数,但编译器对我所做的两个选项和类似测试抱怨很多.
当然代码更复杂,我有一个不透明的处理程序,析构函数应该以更复杂的方式运行.资源自由总是相同的(不需要多个析构函数,只需要Base一个).
我不知道如何实现这一点,也许我正走错路?有任何想法吗?我希望能够做到这样的事情:
Derived a(nullptr);
Derived b(handler1); …Run Code Online (Sandbox Code Playgroud)