首页 > 编程笔记

C++ static_assert(静态断言)

断言是编程中常用的一种调试手段。在 C++11 之前,C++ 使用 assert() 宏进行断言。但是,assert() 宏只能在程序运行时期执行,这意味着不运行程序将无法检测到断言错误。如果每次断言都要执行一遍程序,则检测效率就会降低。

另外,对于 C++ 中使用较多的模板来说,模板实例化是在编译阶段完成的,assert() 断言不能在编译阶段完成对模板实例化的检测。为此,C++11 引入了静态断言 static_assert,用于实现编译时断言。

静态断言的语法格式如下所示:

static_assert(常量表达式, 提示字符串);

在上述语法格式中,static_assert 有两个参数:
在执行断言时,编译器首先检测“常量表达式”的值,若常量表达式的值为真,则 static_assert() 不做任何操作,程序继续完成编译;若常量表达式的值为假,则static_assert() 产生一条编译错误提示,错误提示的内容就是第二个参数。

示例

下面通过案例演示静态断言的用法,C++ 代码如下:
#include<iostream>
using namespace std;
template<typename T, typename U>
void func(T& t, U& u)       //定义函数模板func()
{
    static_assert(sizeof(t) == sizeof(u),    //静态断言
        "the parameters must be the same width.");
    cout << t << "与" << u << "字节大小相同" << endl;
}
int main()
{
    int x = 100;        //定义变量
    int y = 20;        //定义变量
    char ch = 'a';        //定义变量
    func(x, y);        //调用func()函数
    func(x, ch);        //调用func()函数
    return 0;
}
编译错误,运行结果如下:

the parameters must be the same width.

示例分析:
本例编译错误就是由于第 16 行代码断言失败。如果注释掉第16 行代码,则程序编译通过。

需要注意的是,static_assert() 断言表达式的结果必须在编译阶段就可以计算出来,即必须是常量表达式。

如果使用了变量,则会导致编译错误,示例代码如下:
void set_age(const int n) 
{  
    static_assert(n > 0, "The age should be greater than zero!");  
}
上述代码中,在 static_assert() 中使用了参数变量 n,编译时报错“表达式的计算结果不是常数”。

优秀文章