static_assert
declaration
(since C++11)
컴파일 타임 어서션 검사를 수행합니다.
목차 |
구문
static_assert(
bool-constexpr
,
unevaluated-string
)
|
(1) | ||||||||
static_assert(
bool-constexpr
)
|
(2) | (C++17부터) | |||||||
static_assert(
bool-constexpr
,
constant-expression
)
|
(3) | (C++26부터) | |||||||
정적 어서션(static assertion)을 선언합니다. 어서션이 실패할 경우 프로그램은 형식에 맞지 않으며(ill-formed), 진단 오류 메시지가 생성될 수 있습니다.
설명
| bool-constexpr | - |
|
||||
| unevaluated-string | - | 평가되지 않는 문자열 리터럴 으로 오류 메시지로 나타납니다. | ||||
| constant-expression | - |
다음 모든 조건을 만족하는
상수 표현식
msg
:
|
static_assert 선언은 네임스페이스 및 블록 scope ( block declaration 으로)와 클래스 본문 내부( member declaration 으로)에 나타날 수 있습니다.
만약 bool-constexpr 이 형식적으로 올바르고 true 로 평가되거나, 템플릿 정의의 문맥에서 평가되고 템플릿이 인스턴스화되지 않은 경우, 이 선언은 아무 효과가 없습니다. 그렇지 않으면 컴파일 타임 오류가 발생하며, 사용자가 제공한 메시지가 있는 경우 진단 메시지에 포함됩니다.
사용자가 제공한 메시지의 텍스트는 다음과 같이 결정됩니다:
- 메시지가 unevaluated-string 의 구문 요구사항과 일치하는 경우, 메시지의 텍스트는 unevaluated-string 의 텍스트입니다.
|
(C++26부터) |
참고 사항
표준은 컴파일러가 error message 의 원문을 출력하도록 요구하지 않지만, 컴파일러들은 일반적으로 가능한 한 많이 그렇게 합니다.
|
오류 메시지는 문자열 리터럴이어야 하므로, 동적 정보나 문자열 리터럴 자체가 아닌 상수 표현식 을 포함할 수 없습니다. 특히 이름 이나 템플릿 타입 인자 를 포함할 수 없습니다. |
(until C++26) |
| 기능 테스트 매크로 | 값 | 표준 | 기능 |
|---|---|---|---|
__cpp_static_assert
|
200410L
|
(C++11) | static_assert (문법 ( 1 ) ) |
201411L
|
(C++17) | 단일 인자 static_assert (문법 ( 2 ) ) | |
202306L
|
(C++26) | 사용자 생성 오류 메시지 (문법 ( 3 ) ) |
키워드
예제
#include <format> #include <type_traits> static_assert(03301 == 1729); // C++17부터 메시지 문자열은 선택사항입니다 template<class T> void swap(T& a, T& b) noexcept { static_assert(std::is_copy_constructible_v<T>, "Swap requires copying"); static_assert(std::is_nothrow_copy_constructible_v<T> && std::is_nothrow_copy_assignable_v<T>, "Swap requires nothrow copy/assign"); auto c = b; b = a; a = c; } template<class T> struct data_structure { static_assert(std::is_default_constructible_v<T>, "Data structure requires default-constructible elements"); }; template<class> constexpr bool dependent_false = false; // CWG2518/P2593R1 이전의 해결 방법 template<class T> struct bad_type { static_assert(dependent_false<T>, "error on instantiation, workaround"); static_assert(false, "error on instantiation"); // CWG2518/P2593R1 덕분에 OK }; struct no_copy { no_copy(const no_copy&) = delete; no_copy() = default; }; struct no_default { no_default() = delete; }; #if __cpp_static_assert >= 202306L // 아직 실제 C++이 아닙니다 (std::format이 constexpr이어야 작동함): static_assert(sizeof(int) == 4, std::format("Expected 4, got {}", sizeof(int))); #endif int main() { int a, b; swap(a, b); no_copy nc_a, nc_b; swap(nc_a, nc_b); // 1 [[maybe_unused]] data_structure<int> ds_ok; [[maybe_unused]] data_structure<no_default> ds_error; // 2 }
가능한 출력:
1: error: static assertion failed: Swap requires copying 2: error: static assertion failed: Data structure requires default-constructible elements 3: error: static assertion failed: Expected 4, got 2
결함 보고서
다음 동작 변경 결함 보고서는 이전에 발표된 C++ 표준에 소급 적용되었습니다.
| DR | 적용 대상 | 게시된 동작 | 올바른 동작 |
|---|---|---|---|
| CWG 2039 | C++11 | 변환 전 표현식만 상수 표현식이어야 함 |
변환도 상수 표현식에서
유효해야 함 |
|
CWG 2518
( P2593R1 ) |
C++11 | 인스턴스화되지 않은 static_assert ( false , "" ) ; 는 잘못된 형식이었음 | 올바른 형식으로 변경됨 |
참조문헌
- C++23 표준 (ISO/IEC 14882:2024):
-
- 9.1 서문 [dcl.pre] (p: 10)
- C++20 표준(ISO/IEC 14882:2020):
-
- 9.1 서문[dcl.pre] (p: 6)
- C++17 표준 (ISO/IEC 14882:2017):
-
- 10 선언 [dcl.dcl] (p: 6)
- C++14 표준 (ISO/IEC 14882:2014):
-
- 7 선언 [dcl.dcl] (p: 4)
- C++11 표준 (ISO/IEC 14882:2011):
-
- 7 선언 [dcl.dcl] (p: 4)
참고 항목
|
주어진 오류 메시지를 표시하고 프로그램을 비정형으로 만듭니다
(전처리기 지시문) |
|
|
사용자 지정 조건이
true
가 아닌 경우 프로그램을 중단합니다.
릴리스 빌드에서는 비활성화될 수 있습니다.
(함수 매크로) |
|
contract_assert
statement
(C++26)
|
실행 중 내부 조건을 검증합니다 |
|
(C++11)
|
조건부로 함수 오버로드 또는 템플릿 특수화를
오버로드 해결에서 제거합니다
(클래스 템플릿) |
| Type traits (C++11) | 타입의 속성을 질의하기 위한 컴파일 타임 템플릿 기반 인터페이스를 정의합니다 |
|
C documentation
for
Static assertion
|
|