Attribute specifier sequence (since C++11)
型、オブジェクト、コードなどに対する実装定義の属性を導入します。
目次 |
構文
[[
属性リスト
]]
|
(C++11以降) | ||||||||
[[
using
属性名前空間
:
属性リスト
]]
|
(C++17以降) | ||||||||
where
attribute-list
is a comma-separated sequence of zero or more
attribute
s (possibly ending with an ellipsis
...
indicating a
pack expansion
)
| 識別子 | (1) | ||||||||
属性名前空間
::
識別子
|
(2) | ||||||||
識別子
(
引数リスト
(オプション)
)
|
(3) | ||||||||
属性名前空間
::
識別子
(
引数リスト
(オプション)
)
|
(4) | ||||||||
attribute-namespace は identifier であり、 argument-list は括弧、角括弧、波括弧が均衡しているトークンの列( balanced-token-seq )である。
|
属性リストの先頭に
[[using CC: opt(1), debug]] // same as [[CC::opt(1), CC::debug]] [[using CC: CC::opt(1)]] // error: cannot combine using and scoped attribute |
(C++17以降) |
説明
属性は、GNUやIBMの言語拡張
__attribute__((...))
やMicrosoft拡張
__declspec()
など、実装定義の言語拡張に対する統一された標準構文を提供します。
属性はC++プログラムのほぼどこでも使用でき、ほぼすべてのものに適用できます:型、変数、関数、名前、コードブロック、翻訳単位全体に適用可能ですが、各特定の属性は実装によって許可されている場所でのみ有効です:
[[expect_true]]
は
if
でのみ使用でき、クラス宣言では使用できない属性である可能性があります。
[[omp::parallel()]]
はコードブロックや
for
ループに適用可能ですが、型
int
などには適用できない属性である可能性があります(これらの2つの属性は架空の例であることに注意してください。標準およびいくつかの非標準属性については以下を参照してください)。
宣言において、属性は宣言全体の前に現れることも、宣言されるエンティティの名前の直後に現れることもあり、その場合は結合されます。他のほとんどの状況では、属性は直前のエンティティに適用されます。
alignas
指定子
は、構文が異なるものの、属性指定子シーケンスの一部です。これは
[[...]]
属性が現れる場所で現れ、それらと混在することができます(ただし、
alignas
が許可されている場所で使用される場合に限ります)。
2つの連続する左角括弧トークン (
[[
) は、属性指定子を導入する場合、または属性引数の内部でのみ使用できます。
void f() { int y[3]; y[[] { return 0; }()] = 1; // エラー int i [[cats::meow([[]])]]; // OK }
以下の標準属性に加えて、実装は実装定義の動作を持つ任意の非標準属性をサポートする場合があります。 実装が認識しないすべての属性は、エラーを引き起こさずに無視されます。 (C++17以降)
|
attribute-namespace
を持たない属性、およびその名前が
|
(C++20以降) |
標準属性
以下の属性はC++標準によって定義されています。
標準属性は構文的に無視することはできません:それらは構文エラーを含むことができず、正しいターゲットに適用されなければならず、引数内のエンティティは ODR-use されなければなりません。
標準属性は意味的に無視することもできません:特定の標準属性のすべてのインスタンスが削除された場合の動作は、属性が存在する元のプログラムに対する適合動作であったはずです。
[[
noreturn
]]
(C++11)
|
関数が戻らないことを示す
(属性指定子) |
[[
carries_dependency
]]
(C++11)
(C++26で削除)
|
release-consumeにおける依存性チェーンが関数の内外で伝播することを示す
std::memory_order
(属性指定子) |
[[
deprecated
]]
[[
deprecated
("
reason
")]]
(C++14)
(C++14)
|
この属性で宣言された名前またはエンティティの使用が許可されているが、何らかの
理由
で推奨されないことを示す
(属性指定子) |
[[
fallthrough
]]
(C++17)
|
前のcaseラベルからのフォールスルーが意図的であり、フォールスルーについて警告するコンパイラによって診断されるべきではないことを示す
(属性指定子) |
[[
maybe_unused
]]
(C++17)
|
未使用エンティティに関するコンパイラ警告を抑制する(もしあれば)
(属性指定子) |
|
戻り値が破棄された場合に警告を発行するようコンパイラに促す
(属性指定子) |
|
|
文を通る実行パスが他のどの実行パスよりも可能性が高い、または低い場合にコンパイラが最適化すべきことを示す
(属性指定子) |
|
[[
no_unique_address
]]
(C++20)
|
非静的データメンバーがそのクラスの他のすべての非静的データメンバーとは異なるアドレスを持つ必要がないことを示す
(属性指定子) |
[[
assume
(
expression
)]]
(C++23)
|
指定された時点で
式
が常に
true
と評価されることを指定する
(属性指定子) |
[[
indeterminate
]]
(C++26)
|
オブジェクトが初期化されていない場合、不定値を持つことを指定する
(属性指定子) |
|
(TM TS)
|
関数定義が
synchronized文
からの呼び出しに対して最適化されるべきことを示す
(属性指定子) |
注記
各プラットフォームにおける個々の属性の有無は、
__has_cpp_attribute
プリプロセッサマクロで確認できます。
| 機能テストマクロ | 値 | 規格 | 機能 |
|---|---|---|---|
__cpp_attributes
|
200809L
|
(C++11) | 属性 |
__cpp_namespace_attributes
|
201411L
|
(C++17) | 名前空間 の属性 |
例
[[gnu::always_inline]] [[gnu::hot]] [[gnu::const]] [[nodiscard]] inline int f(); // 4つの属性を持つfを宣言 [[gnu::always_inline, gnu::const, gnu::hot, nodiscard]] int f(); // 上記と同じだが、4つの属性を含む単一の属性指定子を使用 // C++17: [[using gnu : const, always_inline, hot]] [[nodiscard]] int f[[gnu::always_inline]](); // 属性は複数の指定子に現れることが可能 int f() { return 0; } int main() {}
不具合報告
以下の動作変更に関する欠陥報告書は、以前に公開されたC++規格に対して遡及的に適用されました。
| DR | 適用バージョン | 公開時の動作 | 正しい動作 |
|---|---|---|---|
| CWG 2079 | C++11 |
[[
は属性引数内に出現できなかった
|
許可される |
| CWG 2538 | C++11 | 標準属性を構文的に無視できるか不明確だった | 禁止される |
| CWG 2695 | C++11 | 標準属性を意味的に無視できるか不明確だった | 禁止される |
| P2156R1 | C++11 | すべての標準属性は attribute-list 内で最大1回しか出現できないことが要求されていた | 要求されない |
関連項目
__has_cpp_attribute
- 属性の存在をチェックします
|
|
|
Cドキュメント
for
属性指定子シーケンス
|
外部リンク
| 1. |
GCCにおける属性
。これらの属性は
[[gnu::...]]
形式で使用可能、
SO参照
。
|
| 2. | Clangにおける属性 。 |
| 3. | MSVCにおける属性 。 |