Вы находитесь на странице: 1из 11

Modern C++

Static Assertions
(compile-time assert)

Static Assertions

What are static assertions?


tests evaluated at compile-time, causing compile-time errors on failure can be used to detect platform and compiler constraints can be used to detect versioning issues can be used to detect programmer errors can be used to vastl simplif compiler output !ero runtime overhead fle"ibilit unmatched b alternative methods

Static Assertions

#istor

prior to C++$$ %e onl had t%o %a s to mimic static assertions


$

'

the preprocessor &error directive &error %as not designed to be used as a comple" static anal sis tool preprocessing happens before in a stage before compilation starts placing code that generates a compiler error in an e"pected manner generall , such code should produce an error such that it is obvious %hat has happened boost provides such a mechanism b a clever use of templates that fails b a sizeof e"pression %ith an undefined t pe this method is not necessaril guaranteed to produce the same output on all compilers, but usuall %or(s %ell enough

Static Assertions

S nta") static_assert(bool-const-expression, string-literal)

bool-const-expression must be:


deducible at compile-time*$+ implicitl convertible to bool

string-literal must be a string literal*'+


if bool-const-expression is true, then the e"pression is a no-op if bool-const-expression is false, then the program is ill-formed and a compile-time error of string-literal is generated

*$+ more formall , e"pression must be a constant expression (, -.$/) *'+ note that compilers are permitted to exclude characters that are not found in the basic source character set from the diagnostic message (, '.0)

Static Assertions

Scoping Bules

static assertions can appear at bloc( scope, namespace scope, and class scope static assertions cannot appear in enums or enum classes

$ 11 static assertion in namespace scope ' static2assert(22cplusplus 34 '5$$506, 7A C++$$ compiler is re8uired to compile this97): 0 ; &include <arra 3 11 for std))arra &include <iostream3 11 for std))cout, std))endl = > int main() ? @ / std))arra <int, ;3 arra @$, ', 0, ;A: $5 for(int i ) arra ) $$ @ $' std))cout << i << std))endl: $0 A $; A $2222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222 3 clang++ -pedantic -std4c++$$ static2assert2namespace2scope.cpp

Static Assertions
J"amples Continued
$ static2assert(true, 77): C $ static assertion in global namespace scope ' namespace D @ static2assert(true, 77): A C ' static assertion in namespace scope 0 C 0 ; class E C ; @ C = static2assert(true, 77): C = static assertion in class scope > class F @ static2assert(true, 77): A: C > static assertion in nested class scope ? C ? / template<t pename G, t pename H3 class I @ static2assert(true, 77): A: C / static assertion in template class $5 C $5 $$ E() @ static2assert(true, 77): A C $$ static assertion in constructor definition $' A: C $' $0 C $0 $; namespace F @ static2assert(true, 77): namespace I @ static2assert(true, 77): AA C $; static assertion in namespace scope and nested namespace scope $C $$= int main() C $= $> @ C $> $? @ static2assert(true, 77): A C $? static assertion in bloc( scope $/ auto test 4 *+() C $/ '5 @ C '5 '$ 11 assertions can even be used in lambda e"pressions C '$ '' static2assert(true, 77): C '' static assertion in lambda bloc( scope '0 A: C '0 '; static2assert(true, 77): C '; static assertion in bloc( scope 'A C '2222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222 3 clang++ -std4c++$$ -pedantic static2assert2scopes.cpp

Static Assertions

Common Hse Cases


detecting platform and compiler constraints detecting versioning issues Comple" static anal sis Jnforcing template concepts

Static Assertions

Ketecting platform and compiler constraints

$ 11 22cplusplus is a standard built-in macro that defines %hich standard revision a compiler meets ' static2assert(22cplusplus 34 '5$$506, 7A C++$$ compiler is re8uired to compile these e"amples97): 0 ; 11 22clang22 is a non-standard macro defined b the clang compiler - static2assert(22clang22, 7C6ALM is most li(el re8uired to compile some of these e"amples97): = > static2assert(22cplusplus 34 '5$$506 NN 22clang22, 7A combination of the above t%o assertions7): ? / static2assert(si!eof(long) 34 ?, 7A =;-bit platform is re8uired to compile this program97): $5 $$ int main() $' @ $0 $; A $222222222222222222222222222222222222222222222222222222222222222222222222222222222222 3 clang++ -pedantic .1e"amples1static2assert.cpp

Static Assertions

Ketecting versioning issues

$ &include 7M 6ibrar .hpp7 ' 0 11 Oretend that M 6ibrar .hpp contains a constant PMF26QRBABF2SJBSQTLP ; - static2assert(MF26QRBABF2SJBSQTL 34 ;, 7M 6ibrar version ; or higher is re8uired to compile this program7): = > int main() ? @ / $5 A $$ 2222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222 3 clang++ -pedantic -std4c++$$ static2assert2versioning.cpp

Static Assertions

Comple" Static Anal sis

$ &include <arra 3 11 for std))arra ' &include <utilit 3 11 for std))for%ard 0 ; template<t pename G, std))si!e2t L3 class Guple = @ > std))arra <G, L3 elements: ? public) / template<t pename ...J3 Guple(JNN ...elements) ) elements @ std))for%ard<G3(elements)...A $5 @ $$ static2assert(si!eof...(J) 44 L, 7Qncorrect number of elements provided to constructor7): $' A $0 A: $; $- int main() $= @ $> Guple<int, 03 test($, ', 0): 11 TU $? Guple<int, 03 test'($, '): 11 Jrror V static assertion fails $/ Guple<int, 03 test0($, ', 0, ;) 11 Jrror V static assertion fails '5 A '$ 22222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222 3 clang++ -std4c++$$ -pedantic comple"2static2anal sis.cpp

Static Assertions

Jnforcing Gemplate Concepts

$ &include <t pe2traits3 11 for std))is2arra , std))is2destructible ' 0 template<t pename G3 class Keleter ; static2assert(9std))is2arra <G3))value, 7Ghe t pe provided to Keleter must not be an arra 97): = static2assert(std))is2destructible<G3))value, 7Ghe t pe provided to Keleter must be able to be deleted97): > const GW ra%2pointer: ? / public) $5 Keleter(const GW pointer) ) ra%2pointer(pointer) @ A $$ XKeleter() @ delete ra%2pointer: A $' A: $0 $; class Hndeletable $@ $= XHndeletable() @ A $> A: $? $/ int main() '5 @ '$ Keleter<int3 valid(ne% int(;')): 11 Wor(s '' 11Keleter<int*+3 invalidArra (ne% int*;'+): 11 static2assertion fails (arra t pe) '0 11Keleter<Hndeletable3 invalid(ne% Hndeletable): 11 static2assertion fails (private destructor) '; A '2222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222222 3 clang++ -std4c++$$ -pedantic enforcing2template2concepts.cpp

Вам также может понравиться