我想创建一个对象,std::array<T, N>但问题是我只能使用返回constexpr类型的函数,否则编译器会抱怨。这里的问题是我需要根据另一个数组的大小来计算该数组的长度,可能是这样的:
template <typename T>
struct DataLength
{
template <typename iter>
size_t maxPossibleLength(iter begin, iter end)
{
size_t m_size = 0;
while (begin != end) {
m_size = m_size << 8 | std::numeric_limits<T>::max(); /* 0xff for uchar*/
begin++;
}
return m_size;
}
}
Run Code Online (Sandbox Code Playgroud)
我如何转换这个函数的输出,以便我可以使用它而不是N?
我写了一个简单的例子来解决我在写他的程序时遇到的问题。
\n\n在程序执行期间,当从函数返回值时,我得到 input1 和 input2 的值,这些值永远不会改变。然后稍后,在程序过程中进行各种计算后,我得到一个结果,该结果也不再可变。
\n\n我正在尝试使用 switch-case 来比较它们,但出现一个错误“\xe2\x80\x98input1\xe2\x80\x99 的值在常量表达式中不可用”。
\n\n#include <iostream>\n\nusing namespace std;\n\nchar getChar()\n{\n char c;\n cin >> c;\n return c;\n}\n\nint main()\n{\n // it doesn\'t work\n const char input1 = getChar();\n const char input2 = getChar();\n\n // it it works\n //const char input1 = \'R\';\n //const char input2 = \'X\';\n\n char result = getChar();\n switch(result)\n {\n case input1:\n cout << "input1" << endl;\n break;\n case input2:\n cout << "input2" << endl;\n break;\n }\n return 0;\n}\nRun Code Online (Sandbox Code Playgroud)\n 我想用constexpr char[]另一个constexpr char []成员初始化成员。可以在上面C++11或者上面做吗?
#include <iostream>
struct Base {
static constexpr char ValueOne[] = "One";
static constexpr char ValueTwo[] = "Two";
};
template <typename T>
struct ValueOneHolder {
static constexpr char Value[] = T::ValueOne; // << How can one initialize this?
};
int main() {
std::cout << ValueOneHolder<Base>::Value << std::endl;
return 0;
}
Run Code Online (Sandbox Code Playgroud) 有没有办法在 Qt 中定义静态 constexpr 字符串文字成员?即类似以下内容:
class X
{
static constexpr QString tag = "mytag";
};
Run Code Online (Sandbox Code Playgroud) 我正在尝试初始化一个多维数组,虽然可以在启动时填充该数组一次,但我真的更喜欢该数组constexpr,所以我想知道是否有一种方法可以让编译器为我执行此操作,特别是因为我可以提供一个 constexpr 函数,该函数接受每个索引的参数并返回数组应位于索引处的值。
例如:
constexpr bool test_values[64][64][64][64] = {
... // magic goes here
};
Run Code Online (Sandbox Code Playgroud)
我有一个函数constexpr bool f(int,int,int,int)可以告诉我每个元素应该是什么。我更喜欢通过数组访问条目,因为进行数组查找比调用 f() 获取非常量值更快。
我发现的大多数与在运行时初始化数组相关的其他问题都使用 std::array 而不是 C 数组,而且我找不到的问题都是多维的。我曾尝试将多维数组展开为一维数组,并使用 std::array 方法,例如我在这个问题的答案之一中找到的方法,但我发现 gcc 9.1 生成的结果代码仍然填充了数组在启动时一次,而不是编译器直接生成数组。
我可以做些什么来让编译器填充这种数组,还是我必须保留test_values有效的非constexpr,并在运行时初始化一次?
编辑:
澄清一下,我本质上并不反对使用 std::array 而不是内置的 C 风格数组,但我不认为 std::arrays 对多维特别友好,并且使用一维数组会混淆我的内容程序需要做的事情(坦率地说,如果必须的话,我愿意将其实现为一维 std::array ,但是多维数组感觉比手动展开的同等大小的一维数组更容易混淆,这就是为什么我用多维 C 数组来描述它)。
GNU C 和 C++ 提供const和pure函数属性。\n来自gnu 在线文档(重点是我的):
在 GNU C 和 C++ 中,您可以使用函数属性来指定某些函数属性,这些属性可以帮助编译器优化调用或更仔细地检查代码的正确性。例如,您可以使用属性来指定函数从不返回 (noreturn)、仅根据其参数的值返回值 (const)或具有 printf 样式参数 (format)。
\n其中 const 属性似乎是 pure 的子集,也取自gnu 文档:
\n\n\nconst 属性比类似的 pure 属性对函数\xe2\x80\x99s\n定义施加了更大的限制。诊断同时使用 const 和 pure 属性声明相同\n函数。
\n
在 C++ 11 中,添加了constexpr说明符。
当应用于函数时,const 属性和 constexpr 说明符之间有区别吗?GCC 是否应用了不同的优化?
\n一个听起来类似的问题是“constexpr”和“const”之间的差异。但我认为这不是重复的。我的问题具体是关于 function 属性const,它似乎与constexpr.
尽管阅读了一些 StackOverflow 帖子(this和this)和 cppreference 页面,但我无法弄清楚非静态局部变量与非静态局部变量 相比有何constexpr好处。 static constexpr
我能看到的唯一区别是每个调用都有自己的实例,但由于它是一个constexpr我在这里看不到实际优势(因为,如果我理解正确,这会导致每个实例都是相同且不可变的,使得多个实例只是多余的)。
或者,从另一个角度争论:由于非静态constexpr局部变量在(每次)函数调用时初始化,因此简单局部变量没有任何优势const,尽管它可以用于编译时评估。但是,当编译时评估需要它们时,没有必要将它们设置为非静态的。
所以我的问题是:我的论点有什么缺陷,在什么情况下非静态constexpr局部变量是合理的并且可能是最佳选择?
注意:Stack Overflow 上有很多标题看起来非常相似的问题,但恕我直言,我发现没有一个问题实际上是重复的。
我多年来一直在我的项目中使用如下代码,没有出现任何问题。但是,自从最近更新 Visual Studio 2019(16.7.2 - 尽管可能是16.7.1)以来,MSVC编译器已开始生成所示的错误(我将编译“标准”设置为 C++17 )。
#include <iostream>
class Foo {
public:
Foo() { }
static constexpr char Letters[6][10] = { "Alpha", "Bravo", "Charlie", "Delta", "Echo", "Foxtrot" };
};
int main()
{
Foo f;
for (int i = 0; i < 6; ++i) std::cout << f.Letters[i] << std::endl;
return 0;
}
Run Code Online (Sandbox Code Playgroud)
错误(在行的左大括号处constexpr):
错误 C2131:表达式未计算为常量
消息:失败是由读取未初始化的符号引起的
clang-cl编译器继续接受代码,没有任何警告。
我对这个问题有一个相当“微不足道”的修复,如下所示:
class Foo {
public:
Foo() { }
inline static const char …Run Code Online (Sandbox Code Playgroud) 在以下代码中,我尝试存储对另一个类的 const 引用:
struct A {
};
struct B {
constexpr B(A const & _a) : a(_a) {}
A const & a;
};
int main() {
constexpr A s1;
constexpr B s2{s1};
}
Run Code Online (Sandbox Code Playgroud)
然而,编译器(gcc 11.1)抱怨:
cctest.cpp: In function ‘int main()’:
cctest.cpp:12:22: error: ‘B{s1}’ is not a constant expression
12 | constexpr B s2{s1};
|
Run Code Online (Sandbox Code Playgroud)
我无法弄清楚为什么s1不被视为常量表达式。s1本身是代码中的 constexpr。我知道这可能与引用的生命周期有关,但我无法弄清楚逻辑。在这个例子的代码中,我不想存储 A 的副本,我真的只想要一个引用或(智能)指针。所以:
s1不是常量表达式?非常感谢!
我的意思是,有可能以某种方式做这样的事情吗?
class Color {
public:
static constexpr Color BLACK = {0, 0, 0};
constexpr Color(int r, int g, int b) : r_(r), g_(g), b_(b) {}
private:
int r_;
int g_;
int b_;
};
Run Code Online (Sandbox Code Playgroud)
编译器Color在定义BLACK常量时抱怨类不完整。