static_assert - 一种动态自定义错误消息的方法

sma*_*llB 12 c++ static-assert c++11

有没有办法让static_assert的字符串动态定制然后显示?
我的意思是:

//pseudo code
static_assert(Check_Range<T>::value, "Value of " + typeof(T) + " type is not so good ;)");
Run Code Online (Sandbox Code Playgroud)

Mat*_* M. 9

不,那里没有.

然而,这并不重要,因为static_assert在编译时进行评估,并且在出现错误的情况下,编译器不仅会打印出消息本身,而且还会打印实例堆栈(如果是模板).

在ideone中查看这个合成示例:

#include <iostream>

template <typename T>
struct IsInteger { static bool const value = false; };

template <>
struct IsInteger<int> { static bool const value = true; };

template <typename T>
void DoSomething(T t) {
  static_assert(IsInteger<T>::value, // 11
  "not an integer");

  std::cout << t;
}

int main() {
  DoSomething("Hello, World!"); // 18
}
Run Code Online (Sandbox Code Playgroud)

编译器不仅会发出诊断信息,还会发出完整的堆栈:

prog.cpp: In function 'void DoSomething(T) [with T = const char*]':
prog.cpp:18:30:   instantiated from here
prog.cpp:11:3: error: static assertion failed: "not an integer"
Run Code Online (Sandbox Code Playgroud)

如果您了解Python或Java以及它们如何在异常情况下打印堆栈,那么它应该是熟悉的.事实上,它甚至更好,因为你不仅获得了调用堆栈,而且还获得了参数值(这里的类型)!

因此,动态消息不是必要的:)

  • 感谢您的回答,尽管我明白您想要表达的观点,但我仍然相信能够自定义 static_assert 输出的内容会非常好。 (3认同)

小智 8

该标准指定了第二个参数为static_assert字符串文字,因此我无法在其中看到计算机会(预处理器宏除外).

编译器可以扩展标准并允许在这个位置使用适当类型的const表达式,但我不知道是否有任何编译器.

  • 看起来“constexpr”也没有帮助:https://godbolt.org/g/Fb4WfF 似乎该标准出于某种原因特别需要“string-literal”:请参阅[第155页](http://www. open-std.org/jtc1/sc22/wg21/docs/papers/2017/n4659.pdf) (2认同)

OLP*_*OLP 5

正如 Matthieu 所说,这是不可能的,但您可以通过使用宏获得一些您正在寻找的功能:

#define CHECK_TYPE_RANGE(type)\
    static_assert(Check_Range<type>::value, "Value of " #type " type is not so good ;)");

CHECK_TYPE_RANGE(float); // outputs "Value of float type is not so good ;)"
Run Code Online (Sandbox Code Playgroud)

  • 实际上,我觉得你将会有`CHECK_TYPE_RANGE(T)`,它会说不太有用的*“T 类型的值不太好”*。 (3认同)