C++ Core Guidelinesの各ルールのタイトルの日本語訳です。
- 間違いを見つけた場合は編集してもらえると助かります
- Core Guidelinesがそれなりに高頻度で更新されているので、以下のルールのリストや原文は古い可能性があります
- ただし、Core Guidelinesは機械的にチェックして警告を出すことも行われているので、ルールが消滅することは稀だと思われます
Abstact
In: Introduction / 導入
(略)
P: Philosophy / 指針
-
P.1: Express ideas directly in code
(アイデアをコードで直接表現する) -
P.2: Write in ISO Standard C++
(ISO標準C++で書く) -
P.3: Express intent
(意図を表現する) -
P.4: Ideally, a program should be statically type safe
(理想的には、プログラムは静的に型安全であるべきである) -
P.5: Prefer compile-time checking to run-time checking
(実行時よりコンパイル時にチェックする) -
P.6: What cannot be checked at compile time should be checkable at run time
(コンパイル時にチェックできないものは、実行時にチェックできなければならない) -
P.7: Catch run-time errors early
(実行時エラーを早めにキャッチする) -
P.8: Don't leak any resources
(リソースを漏らさない) -
P.9: Don’t waste time or space
(時間とメモリーを無駄にしない) -
P.10: Prefer immutable data to mutable data
(不変なデータを優先する) -
P.11: Encapsulate messy constructs, rather than spreading through the code
(ごちゃごちゃしたオブジェクトの構築をコード中に散らかすのではなくカプセル化する) -
P.12: Use supporting tools as appropriate
(支援ツールを適切に使う) -
P.13: Use support libraries as appropriate
(支援ライブラリを適切に使う)
I: Interfaces / インターフェース
-
I.1: Make interfaces explicit
(インターフェースは明示的にする) -
I.2: Avoid non-const global variables
(非constグローバル変数を避ける) -
I.3: Avoid singletons
(シングルトンを避ける) -
I.4: Make interfaces precisely and strongly typed
(インターフェースに詳細かつ強い型付けを与える) -
I.5: State preconditions (if any)
(事前条件があれば明示する) -
I.6: Prefer Expects() for expressing preconditions
(事前条件を記述するのにExpects()
を使う) -
I.7: State postconditions
(事後条件を明示する) -
I.8: Prefer Ensures() for expressing postconditions
(事後条件を明示するのにEnsures()
を使う) -
I.9: If an interface is a template, document its parameters using concepts
(インターフェースがテンプレートの場合、引数にコンセプトで注釈をつける) -
I.10: Use exceptions to signal a failure to perform a required task
(必要な措置を講じるために失敗の通知には例外を使う) -
I.11: Never transfer ownership by a raw pointer (T*) or reference (T&)
(決して生ポインタで所有権を渡さない) -
I.12: Declare a pointer that must not be null as not_null
(nullになってはいけないポインターは、(GSLの)not_nullとして宣言する) -
I.13: Do not pass an array as a single pointer
(配列をポインター1つだけで渡さない) -
I.22: Avoid complex initialization of global objects
(グローバルオブジェクトの複雑な初期化は避ける) -
I.23: Keep the number of function arguments low
(できるだけ引数の数は少なくする) -
I.24: Avoid adjacent unrelated parameters of the same type
(同じ型の無関係な引数が隣接しないようにする) -
I.25: Prefer abstract classes as interfaces to class hierarchies
(クラス階層よりもインターフェースとしての抽象クラスを使う) -
I.26: If you want a cross-compiler ABI, use a C-style subset
(コンパイラを跨ぐABIが必要なら、C言語の機能に絞ったサブセットを使う) -
I.27: For stable library ABI, consider the Pimpl idiom
(安定したライブラリのABIのためにPimplパターンの使用を検討する) -
I.30: Encapsulate rule violations
(ルール違反をカプセル化する)
F: Functions / 関数
F.def: Function definitions / 関数定義
-
F.1: "Package" meaningful operations as carefully named functions
(意味のある一連の処理を関数に注意深く命名して、「まとめる」) -
F.2: A function should perform a single logical operation
(関数は論理的に1つの処理のみをするべきである) -
F.3: Keep functions short and simple
(関数は短くシンプルに保つ) -
F.4: If a function may have to be evaluated at compile time, declare it
constexpr
(関数がコンパイル時に評価されうるなら、constexpr
で宣言する) -
F.5: If a function is very small and time-critical, declare it
inline
(関数が非常に小さく時間的制約が強ければ、inline
で宣言する) -
F.6: If your function may not throw, declare it
noexcept
(関数が例外を投げないなら、noexcept
で宣言する) -
F.7: For general use, take T* or T& arguments rather than smart pointers
(一般的な用途の引数にはスマートポインタより普通のポインタまたは参照を使う) -
F.8: Prefer pure functions
(関数はできるだけ純粋関数(副作用のない関数)にする) -
F.9: Unused parameters should be unnamed
(使用しない仮引数に名前を付けてはいけない)
F.call: Parameter passing / 引数・戻り値の受け渡し
Parameter passing expression rules / 引数の表現のルール
-
F.15: Prefer simple and conventional ways of passing information
(情報を渡す方法はシンプルかつ一般的なものにする) -
F.16: For "in" parameters, pass cheaply-copied types by value and others by reference to const
(入力用引数は、安価にコピーできる型は値で渡し、それ以外はconst参照で渡す) -
F.17: For "in-out" parameters, pass by reference to non-const
(入出力用引数は非const参照で渡す) -
F.19: For "forward" parameters, pass by
T&&
and onlystd::forward
the parameter
(転送する引数はT&&
にして、引数をstd::forward
する) -
F.20: For "out" output values, prefer return values to output parameters
(値を返すには、出力用引数よりも戻り値を使う) -
F.21: To return multiple "out" values, prefer returning a tuple or struct
(複数の値を返すには、タプルか構造体を使う) -
F.60: Prefer
T*
overT&
when "no argument" is a valid option
(「値なし」がありえるなら参照ではなくポインターを使う)
Parameter passing semantic rules / 引数の意味論的なルール
-
F.22: Use
T*
orowner<T*>
to designate a single object
(1つのオブジェクトを指すのにT*
か(GSLの)owner<T*>
を使う) -
F.23: Use a
not_null<T>
to indicate that "null" is not a valid value
(nullにならないことを示すのに(GSLの)not_null<T>
を使う) -
F.24: Use a
span<T>
or aspan_p<T>
to designate a half-open sequence
(半開区間を指すには(GSLの)span<T>
か(GSLの)span_p<T>
を使う) -
F.25: Use a
zstring or
anot_null<zstring>
to designate a C-style string
(C文字列を指すには(GSLの)zstring
か(GSLの)not_null<zstring>
を使う) -
F.26: Use a
unique_ptr<T>
to transfer ownership where a pointer is needed
(所有権の移動にはunique_ptr<T>
を使用する) -
F.27: Use a
shared_ptr<T>
to share ownership
(所有権の共有にはshared_ptr<T>
を使用する)
Value return semantic rules / 戻り値の意味論的なルール
-
F.42: Return a
T*
to indicate a position (only)
(位置を知らせる場合に限りポインターを返す) -
F.43: Never (directly or indirectly) return a pointer or a reference to a local object
(ローカルオブジェクトの参照やポインターを決して返さない) -
F.44: Return a
T&
when copy is undesirable and "returning no object" isn’t needed
(コピーが望ましくなく、「値なし」が必要なければ参照を返す) -
F.45: Don’t return a
T&&
(右辺値参照を返さない) -
F.46:
int
is the return type formain()
(main()
の戻り値はint
) -
F.47: Return
T&
from assignment operators
(代入演算子は非const参照を返す) -
F.48: Don’t return std::move(local)
(ローカル変数をmoveして返さない)
Other function rules / その他の関数のルール
-
F.50: Use a lambda when a function won’t do (to capture local variables, or to write a local function)
(関数が上手くいかないときはラムダ式を使う(ローカル変数をキャプチャーするか、ローカル関数を書きたい場合)) -
F.51: Where there is a choice, prefer default arguments over overloading
(デフォルト引数とオーバーロードを選べるときはデフォルト引数を使う) -
F.52: Prefer capturing by reference in lambdas that will be used locally, including passed to algorithms
(標準アルゴリズムへ渡す場合を含めて、ローカルで使われるラムダ式は参照キャプチャーを優先する) -
F.53: Avoid capturing by reference in lambdas that will be used nonlocally, including returned, stored on the heap, or passed to another thread
(ローカルスコープを超えて使用されるラムダ式では参照キャプチャーを避ける(関数から戻すもの、ヒープに取るもの、他のスレッドに渡すものなど)) -
F.54: If you capture
this
, capture all variables explicitly (no default capture)
(this
をキャプチャーするときは、すべての変数を明示的にキャプチャーする(デフォルトキャプチャーを使用しない)) -
F.55: Don’t use
va_arg
arguments
(va_arg
による可変長引数を使用しない)
C: Classes and class hierarchies / クラスとクラス階層
-
C.1: Organize related data into structures (
struct
s orclass
es)
(関連するデータをクラスまたは構造体で組織化する) -
C.2: Use
class
if the class has an invariant; usestruct
if the data members can vary independently
(クラスが不変条件を持つならclass
を、メンバーが独立に変更できるならstruct
を使う) -
C.3: Represent the distinction between an interface and an implementation using a class
(クラスを使ってインターフェースと実装の区別を表現する) -
C.4: Make a function a member only if it needs direct access to the representation of a class
(クラスの内部表現(※privateメンバー)に直接アクセスする必要がある場合に限り、関数をメンバーにする) -
C.5: Place helper functions in the same namespace as the class they support
(ヘルパー関数は対象とするクラスと同じ名前空間に置く) -
C.7: Don’t define a class or enum and declare a variable of its type in the same statement
(クラスなどの定義とその型の変数の宣言を1文で書かない) -
C.8: Use class rather than struct if any member is non-public
(publicではないメンバーがあるなら構造体ではなくクラスを使う) -
C.9: Minimize exposure of members
(メンバーの露出を最小限にする)
C.concrete: Concrete types / 具象型
-
C.10: Prefer concrete types over class hierarchies
(クラス階層よりも具象クラスを使う) -
C.11: Make concrete types regular
(具象型の振る舞いを一般的なものにする) -
C.12: Don’t make data members const or references
(データメンバーをconst
または参照にしない)
C.ctor: Constructors, assignments, and destructors / コンストラクター、代入、デストラクター
C.defop: Default Operations / デフォルトの操作
-
C.20: If you can avoid defining any default operations, do
(できるだけデフォルトの操作を(自分で)定義しない) -
C.21: If you define or
=delete
any default operation, define or=delete
them all
(デフォルトの操作を1つでも(自分で)定義または削除するなら、残りも明示的に定義または削除する) -
C.22: Make default operations consistent
(デフォルトの操作に一貫性を持たせる)
C.dtor: Destructors / デストラクター
-
C.30: Define a destructor if a class needs an explicit action at object destruction
(オブジェクトの破棄において特別な処理が必要ならデストラクターを定義する) -
C.31: All resources acquired by a class must be released by the class’s destructor
(クラスが獲得したすべてのリソースをデストラクターで解放する) -
C.32: If a class has a raw pointer (
T*
) or reference (T&
), consider whether it might be owning
(生ポインターや参照をメンバーに持つなら、それらがオブジェクトを所有するか考慮する) -
C.33: If a class has an owning pointer member, define or
=delete
a destructor
(オブジェクトを所有するポインターがメンバーにあるなら、デストラクターを定義または削除する) -
C.35: A base class with a virtual function needs a virtual destructor
(仮想関数を持つ基底クラスは仮想デストラクターを持たなければならない) -
C.36: A destructor may not fail
(デストラクターは失敗してはいけない) -
C.37: Make destructors
noexcept
(デストラクターをnoexcept
にする)
C.ctor: Constructors / コンストラクター
-
C.40: Define a constructor if a class has an invariant
(クラスが不変条件を持つ場合はコンストラクターを定義する) -
C.41: A constructor should create a fully initialized object
(コンストラクターはオブジェクトを完全に初期化すること) -
C.42: If a constructor cannot construct a valid object, throw an exception
(コンストラクターが正しいオブジェクトを構築できないときは例外を投げる) -
C.43: Ensure that a copyable (value type) class has a default constructor
(コピー可能なクラス(値型)にはデフォルトコンストラクターを持たせる) -
C.44: Prefer default constructors to be simple and non-throwing
(デフォルトコンストラクターはシンプルかつ例外を投げないようにする) -
C.45: Don’t define a default constructor that only initializes data members; use member initializers instead
(データメンバーを初期化するだけのデフォルトコンストラクターを定義せず、メンバー初期化子を使用する) -
C.46: By default, declare single-argument constructors
explicit
(理由がない限り、1引数のコンストラクターはexplicit
にする) -
C.47: Define and initialize member variables in the order of member declaration
(メンバー変数は宣言の順に定義し、初期化する) -
C.48: Prefer in-class initializers to member initializers in constructors for constant initializers
(定数で初期化する場合、コンストラクターでのメンバー初期化子よりもクラス内メンバー初期化子を使う) -
C.49: Prefer initialization to assignment in constructors
(コンストラクター内では代入よりメンバー初期化子を使う) -
C.50: Use a factory function if you need "virtual behavior" during initialization
(初期化中に仮想関数的な動作をするにはファクトリー関数を使う) -
C.51: Use delegating constructors to represent common actions for all constructors of a class
(すべてのコンストラクターに共通する処理を表現するのには委譲コンストラクターを使う) -
C.52: Use inheriting constructors to import constructors into a derived class that does not need further explicit initialization
(追加の初期化処理が必要ない場合は継承コンストラクターを使ってコンストラクターを派生クラスに取り込む)
C.copy: Copy and move / コピーとムーブ
-
C.60: Make copy assignment non-virtual, take the parameter by const
&
, and return by non-const&
(コピー代入演算子は非virtualにし、引数はconst参照で受け取り、返り値は非const参照にする) -
C.61: A copy operation should copy
(コピー演算はコピーをしなければならない) -
C.62: Make copy assignment safe for self-assignment
(コピー代入演算子は自己代入しても問題ないようにする) -
C.63: Make move assignment non-virtual, take the parameter by
&&
, and return by non-const&
(ムーブ代入演算子は非virtualにし、引数は右辺値参照で受け取り、返り値は非const参照にする) -
C.64: A move operation should move and leave its source in a valid state
(ムーブ操作によってムーブ元を無効な状態にしないこと) -
C.65: Make move assignment safe for self-assignment
(ムーブ代入演算子は自己代入しても問題ないようにする) -
C.66: Make move operations
noexcept
(ムーブ操作をnoexcept
にする) -
C.67: A polymorphic class should suppress copying
(ポリモーフィッククラスはコピーを禁止する)
C.other: Other default operation rules / その他のデフォルト操作のルール
-
C.80: Use
=default
if you have to be explicit about using the default semantics
(デフォルトの動作が必要なら=default
で実装する) -
C.81: Use
=delete
when you want to disable default behavior (without wanting an alternative)
(デフォルトの動作を無効にするには=delete
で実装を削除する) -
C.82: Don’t call virtual functions in constructors and destructors
(コンストラクターまたはデストラクターで仮想関数を呼ばない) -
C.83: For value-like types, consider providing a noexcept swap function
(値のような型には例外を投げないswap関数の実装を検討する) -
C.84: A swap may not fail
(swap関数は失敗しないようにする) -
C.85: Make swap noexcept
(swap関数は例外を投げないようにする) -
C.86: Make == symmetric with respect of operand types and noexcept
(それぞれのオペランドについて==
を対称にする。==
をnoexcept
にする) -
C.87: Beware of
==
on base classes
(基底クラスでの==
に注意する) -
C.89: Make a
hash
noexcept
(hash
をnoexceptにする) -
C.90: Rely on constructors and assignment operators, not
memset
andmemcpy
(memset
やmemcpy
ではなくコンストラクターと代入演算子を信頼する)
C.con: Containers and other resource handles / コンテナとその他のリソースハンドル
-
C.100: Follow the STL when defining a container
(コンテナを定義するときはSTLに従う) -
C.101: Give a container value semantics
(コンテナには値のセマンティクスを持たせる) -
C.102: Give a container move operations
(コンテナはムーブ可能にする) -
C.103: Give a container an initializer list constructor
(コンテナには初期化リストを受け取るコンストラクタを持たせる) -
C.104: Give a container a default constructor that sets it to empty
(コンテナはデフォルト初期化可能にし、デフォルト値を空とする) -
C.109: If a resource handle has pointer semantics, provide * and ->
(リソースハンドルがポインターセマンティクスを持つなら、*
と->
の演算子を定義する)
C.lambdas: Function objects and lambdas / 関数オブジェクトとラムダ
F.50, F.52, F.53, ES.28の引用のみ
-
F.50: Use a lambda when a function won’t do (to capture local variables, or to write a local function)
(関数が上手くいかないときはラムダ式を使う(ローカル変数をキャプチャーするか、ローカル関数を書きたい場合)) -
F.52: Prefer capturing by reference in lambdas that will be used locally, including passed to algorithms
(標準アルゴリズムへ渡す場合を含めて、ローカルで使われるラムダ式は参照キャプチャーを優先する) -
F.53: Avoid capturing by reference in lambdas that will be used nonlocally, including returned, stored on the heap, or passed to another thread
(ローカルスコープを超えて使用されるラムダ式では参照キャプチャーを避ける(関数から戻すもの、ヒープに取るもの、他のスレッドに渡すものなど)) -
ES.28: Use lambdas for complex initialization, especially of const variables
(複雑な初期化にはラムダ式を使う(特にconst変数の場合))
C.hier: Class hierarchies (OOP) / クラス階層
-
C.120: Use class hierarchies to represent concepts with inherent hierarchical structure (only)
(クラス階層は元々階層的な構造を備えているものを表現するためだけに用いる) -
C.121: If a base class is used as an interface, make it a pure abstract class
(インターフェースとして使う基底クラスは純粋抽象クラスにする) -
C.122: Use abstract classes as interfaces when complete separation of interface and implementation is needed
(インターフェースと実装の分離が必要なら抽象クラスをインターフェースとして使う)
C.hierclass: Designing classes in a hierarchy / 階層的なクラスの設計
-
C.126: An abstract class typically doesn’t need a constructor
(抽象クラスは普通はコンストラクタを必要としない) -
C.127: A class with a virtual function should have a virtual or protected destructor
(仮想関数を持つクラスはvirtual
またはprotected
なデストラクタを持つこと) -
C.128: Virtual functions should specify exactly one of
virtual
,override
, orfinal
(仮想関数にはvirtual
,override
,final
のうち1つだけを必ず指定すること) -
C.129: When designing a class hierarchy, distinguish between implementation inheritance and interface inheritance
(クラス階層を設計するときは、実装の継承とインターフェースの継承を区別する) -
C.130: For making deep copies of polymorphic classes prefer a virtual clone function instead of copy construction/assignment
(多相クラスのディープコピーを実装するときは、コピーコンストラクタ/代入よりも仮想clone関数を使う) -
C.131: Avoid trivial getters and setters
(自明なゲッター/セッターを避ける) -
C.132: Don’t make a function virtual without reason
(訳もなく仮想関数にしない) -
C.133: Avoid protected data
(メンバー変数をprotectedにしない) -
C.134: Ensure all non-const data members have the same access level
(すべての非constなメンバー変数を同じアクセスレベルにする) -
C.135: Use multiple inheritance to represent multiple distinct interfaces
(複数の独立したインターフェースを表すのには多重継承を使う) -
C.136: Use multiple inheritance to represent the union of implementation attributes
(複数の実装の共通部分を表すのには多重継承を使う) -
C.137: Use virtual bases to avoid overly general base classes
(基底クラスを過度に一般化することを防ぐには仮想基底クラスを使う) -
C.138: Create an overload set for a derived class and its bases with
using
(派生クラスと基底クラスに跨るオーバーロード集合を作るのにはusing
を使う) -
C.139: Use
final
sparingly
(final
は控えめに使う) -
C.140: Do not provide different default arguments for a virtual function and an overrider
(仮想関数とそのオーバーライダーに異なるデフォルト引数を与えない)
C.hier-access: Accessing objects in a hierarchy / 階層的なクラスへのアクセス
-
C.145: Access polymorphic objects through pointers and references
(多相的オブジェクトにはポインターと参照を通じてアクセスする) -
C.146: Use
dynamic_cast
where class hierarchy navigation is unavoidable
(クラス階層を下っていくことが避けられない場合はdynamic_cast
を使用する) -
C.147: Use
dynamic_cast
to a reference type when failure to find the required class is considered an error
(キャストの失敗がエラーだと考えられる場合は、参照型にdynamic_cast
を使用する) -
C.148: Use
dynamic_cast
to a pointer type when failure to find the required class is considered a valid alternative
(キャストの失敗が有効な場合の1つと考えられる場合は、ポインター型にdynamic_cast
を使用する) -
C.149: Use
unique_ptr
orshared_ptr
to avoid forgetting to delete objects created using new
(new
で作成したオブジェクトを確実に解放するために、unique_ptr
やshared_ptr
を使用する) -
C.150: Use
make_unique()
to construct objects owned byunique_ptr
s
(unique_ptr
で保持するオブジェクトはmake_unique()
で作る) -
C.151: Use
make_shared()
to construct objects owned byshared_ptr
s
(shared_ptr
で保持するオブジェクトはmake_shared()
で作る) -
C.152: Never assign a pointer to an array of derived class objects to a pointer to its base
(派生クラスの配列へのポインターを基本クラスのポインターへ代入しない) -
C.153: Prefer virtual function to casting
(キャストではなく仮想関数を使う)
C.over: Overloading and overloaded operators / オーバーロードと演算子オーバーロード
-
C.160: Define operators primarily to mimic conventional usage
(演算子は慣例的な用法に倣って定義する) -
C.161: Use nonmember functions for symmetric operators
(対称な演算子は非メンバー関数として定義する) -
C.162: Overload operations that are roughly equivalent
(おおよそ等価な操作はオーバーロードする) -
C.163: Overload only for operations that are roughly equivalent
(おおよそ等価な操作だけをオーバーロードする) -
C.164: Avoid implicit conversion operators
(暗黙の変換演算子を避ける) -
C.165: Use
using
for customization points
(カスタマイゼーションポイントにはusing
を使う) -
C.166: Overload unary
&
only as part of a system of smart pointers and references
(単項&
演算子はスマートポインターと参照の系を作る場合のみオーバーロードする) -
C.167: Use an operator for an operation with its conventional meaning
(慣習的に演算子が用いられている操作には演算子を使う) -
C.168: Define overloaded operators in the namespace of their operands
(オーバーロードする演算子はオペランドの名前空間で定義する) -
C.170: If you feel like overloading a lambda, use a generic lambda
(ラムダ式をオーバーロードしたいときは、ジェネリックラムダを使う)
C.union: Unions / 共用体
-
C.180: Use unions to save memory
(共用体を使ってメモリーを節約する) -
C.181: Avoid "naked" unions
(裸の共用体を避ける) -
C.182: Use anonymous unions to implement tagged unions
(無名共用体を使ってタグ付けされた共用体を実装する) -
C.183: Don’t use a union for type punning
(共用体を型変換のために使わない)
Enum: Enumerations / 列挙
-
Enum.1: Prefer enumerations over macros
(マクロより列挙型を使う) -
Enum.2: Use enumerations to represent sets of related named constants
(名前の付いた定数のセットを表すのに列挙型を使う) -
Enum.3: Prefer enum classes over "plain" enums
(素のenum
よりenum class
を使う) -
Enum.4: Define operations on enumerations for safe and simple use
(列挙型に演算子を定義して安全かつシンプルに使えるようにする) -
Enum.5: Don’t use ALL_CAPS for enumerators
(列挙型の名前を全て大文字の名前にしない) -
Enum.6: Avoid unnamed enumerations
(無名の列挙型を避ける) -
Enum.7: Specify the underlying type of an enumeration only when necessary
(列挙型の基本型は必要な場合のみ与える) -
Enum.8: Specify enumerator values only when necessary
(列挙型の値は必要な場合のみ与える)
R: Resource management / リソース管理
-
R.1: Manage resources automatically using resource handles and RAII (Resource Acquisition Is Initialization)
(リソースはハンドルとRAIIを使って自動で管理する) -
R.2: In interfaces, use raw pointers to denote individual objects (only)
(インターフェースでは、生ポインターは1個のオブジェクトを表すためだけに使う) -
R.3: A raw pointer (a
T*
) is non-owning
(生ポインタで所有権を表さない) -
R.4: A raw reference (a
T&
) is non-owning
(参照で所有権を表さない) -
R.5: Prefer scoped objects, don’t heap-allocate unnecessarily
(スコープのあるオブジェクトを使い、不必要にヒープを使わない) -
R.6: Avoid non-const global variables
(非constなグローバル変数を避ける)
R.alloc: Allocation and deallocation / 確保と解放
-
R.10: Avoid
malloc()
andfree()
(malloc()
とfree()
を避ける) -
R.11: Avoid calling
new
anddelete
explicitly
(明示的なnew
とdelete
を避ける) -
R.12: Immediately give the result of an explicit resource allocation to a manager object
(明示的なリソース確保の結果を直ちに管理オブジェクトへ渡す) -
R.13: Perform at most one explicit resource allocation in a single expression statement
(1つの式文で行う明示的なリソース確保は最大でも1つにする) -
R.14: Avoid
[]
parameters, preferspan
(引数の型に[]
をつけるのを避け、span
を使う) -
R.15: Always overload matched allocation/deallocation pairs
(対応する確保と破棄を組でオーバーロードする)
R.smart: Smart pointers / スマートポインター
-
R.20: Use
unique_ptr
orshared_ptr
to represent ownership
(所有権を表すのにunique_ptr
かshared_ptr
を使う) -
R.21: Prefer
unique_ptr
overshared_ptr
unless you need to share ownership
(所有権の共有が必要でない限りshared_ptr
よりunique_ptr
を使う) -
R.22: Use
make_shared()
to makeshared_ptr
s
(shared_ptr
の構築にはmake_shared()
を使う) -
R.23: Use
make_unique()
to makeunique_ptr
s
(unique_ptr
の構築にはmake_unique()
を使う) -
R.24: Use
std::weak_ptr
to break cycles ofshared_ptr
s
(shared_ptr
の循環を断つにはweak_ptr
を使う) -
R.30: Take smart pointers as parameters only to explicitly express lifetime semantics
(引数にスマートポインタを取るのは寿命に関するセマンティクスを表現する時だけにする) -
R.31: If you have non-std smart pointers, follow the basic pattern from std
(非標準のスマートポインタを使うとしても、標準の基本的なパターンに従う) -
R.32: Take a
unique_ptr<widget>
parameter to express that a function assumes ownership of a widget
(関数がwidget
の所有権を取る場合はunique_ptr<widget>
型の引数を取る) -
R.33: Take a
unique_ptr<widget>&
parameter to express that a function reseats the widget
(関数がwidget
を置き換える場合はunique_ptr<widget>&
型の引数を取る) -
R.34: Take a
shared_ptr<widget>
parameter to express that a function is part owner
(関数がwidget
を共同所有する場合はshared_ptr<widget>
型の引数を取る) -
R.35: Take a
shared_ptr<widget>&
parameter to express that a function might reseat the shared pointer
(関数がshared_ptr
を置き換える可能性がある場合はshared_ptr<widget>&
型の引数を取る) -
R.36: Take a
const shared_ptr<widget>&
parameter to express that it might retain a reference count to the object
(関数がshared_ptr
の参照カウントを変えない可能性がある場合はconst shared_ptr<widget>&
型の引数を取る) -
R.37: Do not pass a pointer or reference obtained from an aliased smart pointer
(スマートポインターのエイリアスから得たポインターや参照を渡さない)
ES: Expressions and statements / 式と文
-
ES.1: Prefer the standard library to other libraries and to "handcrafted code"
(自作や非標準の物より、標準ライブラリを使う) -
ES.2: Prefer suitable abstractions to direct use of language features
(言語機能を直接使うより適切な抽象化を使う)
ES.dcl: Declarations / 宣言
-
ES.5: Keep scopes small
(スコープを小さく保つ) -
ES.6: Declare names in for-statement initializers and conditions to limit scope
(条件部やfor文の初期化部で名前を宣言し、スコープを制限する) -
ES.7: Keep common and local names short, and keep uncommon and nonlocal names longer
(一般的で局所的な名前は短く、そうでない名前は長くする) -
ES.8: Avoid similar-looking names
(似たような見た目の名前を避ける) -
ES.9: Avoid
ALL_CAPS
names
(すべて大文字の名前を避ける) -
ES.10: Declare one name (only) per declaration
(1つの宣言で1つの名前だけを宣言する) -
ES.11: Use
auto
to avoid redundant repetition of type names
(冗長な型名の繰り返しを避けるためにauto
を使用する) -
ES.12: Do not reuse names in nested scopes
(入れ子になったスコープの内側で名前を再利用しない) -
ES.20: Always initialize an object
(オブジェクトは常に初期化する) -
ES.21: Don’t introduce a variable (or constant) before you need to use it
(必要になるまで変数や定数を導入しない) -
ES.22: Don’t declare a variable until you have a value to initialize it with
(初期化するための値が揃うまで変数を宣言しない) -
ES.23: Prefer the {}-initializer syntax
({}
での初期化を優先的に使う) -
ES.24: Use a
unique_ptr<T>
to hold pointers
(ポインターを保持するのにunique_ptr<T>
を使う) -
ES.25: Declare an object const or constexpr unless you want to modify its value later on
(後で変更する必要がない限り、オブジェクトはconstかconstexprにする) -
ES.26: Don’t use a variable for two unrelated purposes
(変数を無関係な別の目的に使わない) -
ES.27: Use std::array or stack_array for arrays on the stack
(配列にはstd::array
か(GSLの)stack_array
を使う) -
ES.28: Use lambdas for complex initialization, especially of const variables
(複雑な初期化にはラムダ式を使う(特にconst変数の場合)) -
ES.30: Don’t use macros for program text manipulation
(マクロでプログラムのテキストを変更しない) -
ES.31: Don’t use macros for constants or "functions"
(定数や関数形式のためにマクロを使用しない) -
ES.32: Use
ALL_CAPS
for all macro names
(マクロの名前はすべて大文字にする) -
ES.33: If you must use macros, give them unique names
(マクロを使わざるを得ないのであれば、ユニークな名前を付ける) -
ES.34: Don’t define a (C-style) variadic function
(Cの可変引数関数を定義しない)
ES.expr: Expressions / 式
-
ES.40: Avoid complicated expressions
(複雑な式を避ける) -
ES.41: If in doubt about operator precedence, parenthesize
(演算子の優先順位が疑わしい場合、カッコを使う) -
ES.42: Keep use of pointers simple and straightforward
(ポインターの使用箇所は単純明快にする)) -
ES.43: Avoid expressions with undefined order of evaluation
(未定義の実行順序を持つ式を避ける) -
ES.44: Don’t depend on order of evaluation of function arguments
(引数の評価順に依存しない) -
ES.45: Avoid "magic constants"; use symbolic constants
(マジックナンバーを避け、名前の付いた定数を使う) -
ES.46: Avoid narrowing conversions
(縮小変換を避ける) -
ES.47: Use
nullptr
rather than0
orNULL
(0
やNULL
よりもnullptr
を使う) -
ES.48: Avoid casts
(キャストを避ける) -
ES.49: If you must use a cast, use a named cast
(キャストを使わざるを得ないのであれば、名前の付いたキャストを使う) -
ES.50: Don’t cast away const
(const
を外さない) -
ES.55: Avoid the need for range checking
(範囲チェックの必要性を避ける) -
ES.56: Write
std::move()
only when you need to explicitly move an object to another scope
(std::move()
は、オブジェクトを他のスコープへ明示的にムーブする必要があるときだけ書く) -
ES.60: Avoid
new
anddelete
outside resource management functions
(リソースを管理する関数の中以外でnew
、delete
を避ける) -
ES.61: Delete arrays using
delete[]
and non-arrays usingdelete
(配列はdelete[]
、それ以外のオブジェクトはdelete
で解放する) -
ES.62: Don’t compare pointers into different arrays
(異なる配列の中を指すポインターを比較しない) -
ES.63: Don’t slice
(スライシングをしない) -
ES.64: Use the
T{e}
notation for construction
(構築にはT{e}
の記法を使う) -
ES.65: Don’t dereference an invalid pointer
(無効なポインターをデリファレンスしない)
ES.stmt: Statements / 文
-
ES.70: Prefer a switch-statement to an if-statement when there is a choice
(選べるならif文よりswitch文を使う) -
ES.71: Prefer a range-for-statement to a for-statement when there is a choice
(選べるならfor文より範囲for文を使う) -
ES.72: Prefer a for-statement to a while-statement when there is an obvious loop variable
(明確なループ変数があるならwhile文よりfor文を使う) -
ES.73: Prefer a while-statement to a for-statement when there is no obvious loop variable
(明確なループ変数がないならfor文よりwhile文を使う) -
ES.74: Prefer to declare a loop variable in the initializer part of a for-statement
(ループ変数をfor文の初期化部で宣言する) -
ES.75: Avoid do-statements
(do文を避ける) -
ES.76: Avoid goto
(gotoを避ける) -
ES.77: Minimize the use of break and continue in loops
(ループでのbreak
とcontinue
の使用を最小限にする) -
ES.78: Always end a non-empty case with a break
(空でないcaseは常にbreakで終える) -
ES.79: Use
default
to handle common cases (only)
(default
は一般の場合を扱う場合のみ使用する) -
ES.84: Don’t try to declare a local variable with no name
(名前のないローカル変数を宣言しない) -
ES.85: Make empty statements visible
(空文を見えるようにする) -
ES.86: Avoid modifying loop control variables inside the body of raw for-loops
(ループ変数をfor文の本体で変更することを避ける) -
ES.87: Don’t add redundant
==
or!=
to conditions
(条件に冗長な==
や!=
を書かない)
Arithmetic / 算術
-
ES.100: Don’t mix signed and unsigned arithmetic
(符号ありと符号なしの計算を混在させない) -
ES.101: Use unsigned types for bit manipulation
(ビット演算には符号なしの型を使う) -
ES.102: Use signed types for arithmetic
(算術演算には符号ありの型を使う) -
ES.103: Don’t overflow
(オーバーフローさせない) -
ES.104: Don’t underflow
(アンダーフローさせない) -
ES.105: Don’t divide by zero
(0で割らない) -
ES.106: Don’t try to avoid negative values by using unsigned
(符号なしの型を使って負の数を避けようとしない) -
ES.107: Don’t use unsigned for subscripts, prefer
gsl::index
(添字に符号なしの型を使わず、gsl::index
を使う)
Per: Performance / パフォーマンス
-
Per.1: Don’t optimize without reason
(訳もなく最適化しない) -
Per.2: Don’t optimize prematurely
(早すぎる最適化をしない) -
Per.3: Don’t optimize something that’s not performance critical
(パフォーマンス上重要でない部分を最適化しない) -
Per.4: Don’t assume that complicated code is necessarily faster than simple code
(複雑なコードがシンプルなコードより早いと思わない) -
Per.5: Don’t assume that low-level code is necessarily faster than high-level code
(低レベルなコードが高レベルなコードより早いと思わない) -
Per.6: Don’t make claims about performance without measurements
(計測せずに意見しない) -
Per.7: Design to enable optimization
(最適化できるように設計する) -
Per.10: Rely on the static type system
(静的型システムを信頼する) -
Per.11: Move computation from run time to compile time
(実行時処理をコンパイル時処理に変える) -
Per.12: Eliminate redundant aliases
(冗長なエイリアスを除去する) -
Per.13: Eliminate redundant indirections
(冗長な間接参照を除去する) -
Per.14: Minimize the number of allocations and deallocations
(確保と解放を最小限にする) -
Per.15: Do not allocate on a critical branch
(クリティカルブランチ上で確保しない) -
Per.16: Use compact data structures
(小さなデータ構造を使う) -
Per.17: Declare the most used member of a time-critical struct first
(タイムクリティカルな構造体では最もよく使われるメンバーを最初に宣言する) -
Per.18: Space is time
(空間は時間である) -
Per.19: Access memory predictably
(メモリーへは予期できるようにアクセスする) -
Per.30: Avoid context switches on the critical path
(クリティカルパス上でのコンテキストスイッチを避ける)
CP: Concurrency and parallelism / 並行・並列処理
-
CP.1: Assume that your code will run as part of a multi-threaded program
(マルチスレッドプログラムの一部として実行される可能性を考慮する) -
CP.2: Avoid data races
(データ競合を避ける) -
CP.3: Minimize explicit sharing of writable data
(書き込み可能なデータの明示的な共有を最小限にする) -
CP.4: Think in terms of tasks, rather than threads
(スレッドよりもタスクで考える) -
CP.8: Don’t try to use
volatile
for synchronization
(同期のためにvolatile
を使おうとしない) -
CP.9: Whenever feasible use tools to validate your concurrent code
(並行処理のコードを検証するのにツールが使えるときは使う)
CP.con: Concurrency / 並行処理
-
CP.20: Use RAII, never plain
lock()
/unlock()
(素のlock()
/unlock()
を避け、RAIIにする) -
CP.21: Use
std::lock()
orstd::scoped_lock
to acquire multiple mutexes
(複数のミューテックスを獲得するのにstd::lock()
やstd::scoped_lock
を使う) -
CP.22: Never call unknown code while holding a lock (e.g., a callback)
(ロックを持っている間、コールバックのような未知のコードを決して呼び出さない) -
CP.23: Think of a joining
thread
as a scoped container
(joinするスレッドをスコープ付きコンテナとみなす) -
CP.24: Think of a
thread
as a global container
(スレッドをグローバルなコンテナとみなす) -
CP.25: Prefer
gsl::joining_thread
overstd::thread
(std::thread
よりもgsl::joining_thread
を使う) -
CP.26: Don’t
detach()
athread
(スレッドをdetach()
しない) -
CP.31: Pass small amounts of data between threads by value, rather than by reference or pointer
(スレッド間では、参照やポインターを使うより値で少量のデータを渡す) -
CP.32: To share ownership between unrelated threads use
shared_ptr
(無関係なスレッドの間で所有権を共有するにはshared_ptr
を使用する) -
CP.40: Minimize context switching
(コンテキストスイッチを最小限にする) -
CP.41: Minimize thread creation and destruction
(スレッドの生成と破棄を最小限にする) -
CP.42: Don’t wait without a condition
(無条件に待機しない) -
CP.43: Minimize time spent in a critical section
(クリティカルセクションへの滞在時間を最小限にする) -
CP.44: Remember to name your
lock_guard
s andunique_lock
s
(lock_guard
やunique_lock
には忘れずに名前を付ける(変数へ束縛する)) -
CP.50: Define a
mutex
together with the data it guards. Usesynchronized_value<T>
where possible
(ガードするデータとミューテックスを同時に宣言する。可能ならsynchronized_value<T>
を使う)
CP.par: Parallelism / 並列処理
未定義
CP.mess: Message passing / メッセージパッシング
-
CP.60: Use a
future
to return a value from a concurrent task
(並行するタスクから値を返すにはfuture
を使う) -
CP.61: Use an
async()
to spawn a concurrent task
(並行タスクをスポーンするにはasync()
を使う)
CP.vec: Vectorization / ベクトル化
未定義
CP.free: Lock-free programming / ロックフリープログラミング
-
CP.100: Don’t use lock-free programming unless you absolutely have to
(本当に必要な場合を除き、ロックフリープログラミングをしない) -
CP.101: Distrust your hardware/compiler combination
(自分のハードウェア、コンパイラの組み合わせを信用しない) -
CP.102: Carefully study the literature
(文献で入念に勉強する) -
CP.110: Do not write your own double-checked locking for initialization
(初期化のためのダブルチェックロックを自分で書かない) -
CP.111: Use a conventional pattern if you really need double-checked locking
(本当にダブルチェックロックが必要ならパターンに従う)
CP.etc: Etc. concurrency rules / その他
-
CP.200: Use
volatile
only to talk to non-C++ memory
(volatile
はC++外のメモリーを読み書きするためだけに使う)
E: Error handling / エラーハンドリング
-
E.1: Develop an error-handling strategy early in a design
(エラーハンドリング戦略を設計の早い段階で作る) -
E.2: Throw an exception to signal that a function can’t perform its assigned task
(関数がその目的を果たせないことを知らせるために例外を投げる) -
E.3: Use exceptions for error handling only
(例外はエラーハンドリングのためだけに使う) -
E.4: Design your error-handling strategy around invariants
(不変条件に関するエラーハンドリング戦略を設計する) -
E.5: Let a constructor establish an invariant, and throw if it cannot
(コンストラクターで不変条件を確立し、できないときは例外を投げる) -
E.6: Use RAII to prevent leaks
(リークを防ぐためにRAIIを使う) -
E.7: State your preconditions
(事前条件を明記する) -
E.8: State your postconditions
(事後条件を明記する) -
E.12: Use
noexcept
when exiting a function because of a throw is impossible or unacceptable
(例外を投げることが不可能または受け入れられない関数を抜けるためにnoexcept
を使う) -
E.13: Never throw while being the direct owner of an object
(オブジェクトを直接(RAIIラッパー無しで)所有している場合は決して例外を投げない) -
E.14: Use purpose-designed user-defined types as exceptions (not built-in types)
(目的に沿って設計されたユーザー定義の例外クラスを用いる(組み込みのものを使わない)) -
E.15: Catch exceptions from a hierarchy by reference
(クラス階層を持つ例外は参照でcatch
する) -
E.16: Destructors, deallocation, and
swap
must never fail
(デストラクター、解放処理、swap
は失敗してはいけない) -
E.17: Don’t try to catch every exception in every function
(すべての関数ですべての例外をcatch
しようとしない) -
E.18: Minimize the use of explicit
try
/catch
(明示的なtry
/catch
の使用を最小限にする) -
E.19: Use a
final_action
object to express cleanup if no suitable resource handle is available
(適当なリソースハンドラーが使えない場合はfinal_action
オブジェクトで後始末の処理を表現する) -
E.25: If you can’t throw exceptions, simulate RAII for resource management
(例外を投げることができない場合、リソース管理はRAIIをシミュレートする) -
E.26: If you can’t throw exceptions, consider failing fast
(例外を投げることができない場合、早めに失敗させる) -
E.27: If you can’t throw exceptions, use error codes systematically
(例外を投げることができない場合、エラーコードは体系的に使う) -
E.28: Avoid error handling based on global state (e.g.
errno
)
(errno
のようなグローバルな状態を使ったエラーハンドリングを避ける) -
E.30: Don’t use exception specifications
(例外仕様を使わない) -
E.31: Properly order your catch-clauses
(catch
節を適切に並べる)
Con: Constants and immutability / 定数と不変性
-
Con.1: By default, make objects immutable
(まずはオブジェクトを不変にする) -
Con.2: By default, make member functions
const
(まずはメンバ-関数をconst
にする) -
Con.3: By default, pass pointers and references to
const
s
(まずはポインターと参照はconst
で渡す) -
Con.4: Use
const
to define objects with values that do not change after construction
(構築後に変化しないオブジェクトはconst
で定義する) -
Con.5: Use
constexpr
for values that can be computed at compile time
(コンパイル時にも計算できる値にはconstexpr
を使う)
T: Templates and generic programming / テンプレートとジェネリックプログラミング
T.gp: Generic programming / ジェネリックプログラミング
-
T.1: Use templates to raise the level of abstraction of code
(テンプレートを使ってコードの抽象化度を上げる) -
T.2: Use templates to express algorithms that apply to many argument types
(テンプレートを使って多数の引数の型に適用できるアルゴリズムを表現する) -
T.3: Use templates to express containers and ranges
(テンプレートを使ってコンテナと範囲を表現する) -
T.4: Use templates to express syntax tree manipulation
(テンプレートを使って構文木の操作を表現する) -
T.5: Combine generic and OO techniques to amplify their strengths, not their costs
(ジェネリックプログラミングとオブジェクト指向プログラミングを組み合わせ、お互いのコストではなく、強みを伸ばす)
T.concepts: Concept rules / コンセプトのルール
T.con-use: Concept use / コンセプト利用時のルール
-
T.10: Specify concepts for all template arguments
(すべてのテンプレート引数にコンセプトを書く) -
T.11: Whenever possible use standard concepts
(可能なら標準のコンセプトを使う) -
T.12: Prefer concept names over
auto
for local variables
(ローカル変数の宣言にはauto
よりコンセプト名を使う) -
T.13: Prefer the shorthand notation for simple, single-type argument concepts
(1引数の単純なコンセプトには略記法を使う)
T.concepts.def: Concept definition rules / コンセプト定義時のルール
-
T.20: Avoid "concepts" without meaningful semantics
(有意義な意味論の無いコンセプトを作らない) -
T.21: Require a complete set of operations for a concept
(コンセプトの制約には必要な操作をすべて含める) -
T.22: Specify axioms for concepts
(コンセプトを定義する公理を(コメントで)書く) -
T.23: Differentiate a refined concept from its more general case by adding new use patterns
(汎用的なコンセプトに制約を追加して詳細なコンセプトを定義する) -
T.24: Use tag classes or traits to differentiate concepts that differ only in semantics
(意味論的な違いだけが違うコンセプトを差別化するためにタグクラスやトレイトを使用する) -
T.25: Avoid complementary constraints
(補集合としてのコンセプトを避ける) -
T.26: Prefer to define concepts in terms of use-patterns rather than simple syntax
(コンセプトをはシンプルな構文で定義するよりも使用例によって定義する) -
T.30: Use concept negation (
!C<T>
) sparingly to express a minor difference
(コンセプトの否定は控えめにする) -
T.31: Use concept disjunction (
C1<T> || C2<T>
) sparingly to express alternatives
(コンセプトのOR条件は控えめにする)
Template interfaces / テンプレートインターフェース
-
T.40: Use function objects to pass operations to algorithms
(アルゴリズムへ操作を渡すのには関数オブジェクトを使う) -
T.41: Require only essential properties in a template’s concepts
(テンプレートのコンセプトでは最も重要な性質だけを要求する) -
T.42: Use template aliases to simplify notation and hide implementation details
(テンプレートのエイリアスを使って記述を簡潔にし、実装の詳細を隠す) -
T.43: Prefer
using
overtypedef
for defining aliases
(typedef
よりもusing
を使う) -
T.44: Use function templates to deduce class template argument types (where feasible)
(可能ならクラステンプレートの引数を推論するために関数テンプレートを使う) -
T.46: Require template arguments to be at least
Regular
orSemiRegular
(テンプレート引数は最低でもRegular
かSemiRegular
であることを要求する) -
T.47: Avoid highly visible unconstrained templates with common names
(一般的な名前で広範囲に渡って見えている制約のないテンプレートを避ける) -
T.48: If your compiler does not support concepts, fake them with
enable_if
(コンセプトに対応していないコンパイラの場合は、enable_if
で再現する) -
T.49: Where possible, avoid type-erasure
(可能な限り型消去をしない)
T.def: Template definitions / テンプレート定義
-
T.60: Minimize a template’s context dependencies
(テンプレートはコンテキストにできる限り依存させない) -
T.61: Do not over-parameterize members (SCARY)
(メンバーをパラメーター化しすぎない) -
T.62: Place non-dependent class template members in a non-templated base class
(非依存のクラステンプレートメンバーはテンプレートではない基底クラスに置く) -
T.64: Use specialization to provide alternative implementations of class templates
(クラステンプレートの別の実装を提供するには特殊化をする) -
T.65: Use tag dispatch to provide alternative implementations of functions
(関数の別の実装を与えるにはタグディスパッチを使う) -
T.67: Use specialization to provide alternative implementations for irregular types
(特別な型に対する異なる実装を与えるには特殊化をする) -
T.68: Use
{}
rather than()
within templates to avoid ambiguities
(テンプレートでは()
より{}
を使い、曖昧性を避ける) -
T.69: Inside a template, don’t make an unqualified nonmember function call unless you intend it to be a customization point
(テンプレートの中では、カスタマイゼーションポイントである場合を除いて非修飾・非メンバーの関数を呼び出さない)
T.temp-hier: Template and hierarchy rules / テンプレートとクラス階層のルール
-
T.80: Do not naively templatize a class hierarchy
(クラス階層全体を単純にテンプレート化しない) -
T.81: Do not mix hierarchies and arrays
(クラス階層と配列を混ぜて使わない) -
T.82: Linearize a hierarchy when virtual functions are undesirable
(仮想関数が好ましくないなら、クラス階層を直線的にする) -
T.83: Do not declare a member function template virtual
(メンバー関数テンプレートをvirtual
宣言しない) -
T.84: Use a non-template core implementation to provide an ABI-stable interface
(安定したABIを提供するには、中核部分の実装はテンプレートにしない)
T.var: Variadic template rules / 可変引数テンプレートのルール
-
T.100: Use variadic templates when you need a function that takes a variable number of arguments of a variety of types
(異なる型の可変長の引数をとる関数が必要な場合は、可変引数テンプレートを使う) -
T.103: Don’t use variadic templates for homogeneous argument lists
(同じ型の引数リストを可変引数テンプレートにしない)
T.meta: Template metaprogramming (TMP) / テンプレートメタプログラミング
-
T.120: Use template metaprogramming only when you really need to
(テンプレートメタプログラミングは本当に必要なときだけにする) -
T.121: Use template metaprogramming primarily to emulate concepts
(テンプレートメタプログラミングでコンセプトを模倣する) -
T.122: Use templates (usually template aliases) to compute types at compile time
(コンパイル時に型を計算するにはテンプレートやテンプレートエイリアスを使う) -
T.123: Use
constexpr
functions to compute values at compile time
(コンパイル時に値を計算するにはconstexpr
を使う) -
T.124: Prefer to use standard-library TMP facilities
(標準ライブラリのテンプレートメタプログラミングライブラリを使用する) -
T.125: If you need to go beyond the standard-library TMP facilities, use an existing library
(標準ライブラリのテンプレートメタプログラミングライブラリの範囲で出来ないときも、既存のライブラリを使う)
Other template rules / その他
-
T.140: Name all operations with potential for reuse
(再利用する可能性があるすべての操作に名前をつける) -
T.141: Use an unnamed lambda if you need a simple function object in one place only
(一か所でしか使わない単純な関数オブジェクトが必要ならラムダ式を使う) -
T.142: Use template variables to simplify notation
(変数テンプレートを使って記述を簡素にする) -
T.143: Don’t write unintentionally nongeneric code
(意図せずに汎用性の低いコードを書かない) -
T.144: Don’t specialize function templates
(関数テンプレートを特殊化しない) -
T.150: Check that a class matches a concept using
static_assert
(static_assert
を使ってクラスがコンセプトを満たすか確認する)
CPL: C-style programming / Cスタイルプログラミング
-
CPL.1: Prefer C++ to C
(CよりもC++) -
CPL.2: If you must use C, use the common subset of C and C++, and compile the C code as C++
(Cを使わざるを得ないなら、CとC++の共通部分を使い、CのコードをC++としてコンパイルする) -
CPL.3: If you must use C for interfaces, use C++ in the calling code using such interfaces
(Cをインターフェースに使わざるを得ないなら、そのようなインターフェースを呼び出すコードはC++で書く)
SF: Source files / ソースファイル
-
SF.1: Use a
.cpp
suffix for code files and.h
for interface files if your project doesn’t already follow another convention
(プロジェクトがまだ他の慣習に従っていないのであれば、ソースファイルには.cpp
、ヘッダーファイルには.h
の拡張子を使う) -
SF.2: A
.h
file may not contain object definitions or non-inline function definitions
(.h
ファイルにオブジェクトの定義やインラインでない関数の定義を含めてはいけない) -
SF.3: Use
.h
files for all declarations used in multiple source files
(.h
ファイルに複数のソースファイルで使う宣言を書く) -
SF.4: Include
.h
files before other declarations in a file
(.h
ファイルをファイル内の他の宣言より先にインクルードする) -
SF.5: A
.cpp
file must include the.h
file(s) that defines its interface
(.cpp
ファイルはそのインターフェースを定義する.h
ファイルをインクルードしなければならない) -
SF.6: Use
using namespace
directives for transition, for foundation libraries (such as std), or within a local scope (only)
(using namespace
は移行のため、std
のような基礎的ライブラリのため、あるいはローカルスコープに限って使う) -
SF.7: Don’t write
using namespace
at global scope in a header file
(ヘッダーファイルのグローバルスコープにおいてusing namespace
をしない) -
SF.8: Use
#include
guards for all.h
files
(すべての.h
ファイルにインクルードガードを書く) -
SF.9: Avoid cyclic dependencies among source files
(ソースファイルの依存関係が循環しないようにする) -
SF.10: Avoid dependencies on implicitly
#include
d names
(暗黙にインクルードされた名前への依存を避ける) -
SF.11: Header files should be self-contained
(ヘッダーファイルは自己完結すべきである) -
SF.20: Use
namespace
s to express logical structure
(論理的な構造を名前空間で表現する) -
SF.21: Don’t use an unnamed (anonymous) namespace in a header
(ヘッダーファイルで無名名前空間を使わない) -
SF.22: Use an unnamed (anonymous) namespace for all internal/nonexported entities
(内部的なものは無名名前空間に置く)
SL: The Standard library / 標準ライブラリ
-
SL.1: Use libraries wherever possible
(可能な限りライブラリを使う) -
SL.2: Prefer the standard library to other libraries
(他のライブラリより標準ライブラリを使う) -
SL.3: Do not add non-standard entities to namespace
std
(std
名前空間に非標準の要素を追加しない) -
SL.4: Use the standard library in a type-safe manner
(標準ライブラリは型安全性を守って使う)
SL.con: Containers / コンテナ
-
SL.con.1: Prefer using STL
array
orvector
instead of a C array
(C配列よりもSTLのarray
やvector
を使う) -
SL.con.2: Prefer using STL
vector
by default unless you have a reason to use a different container
(他のコンテナを使う理由がなければまずはvector
を使う) -
SL.con.3: Avoid bounds errors
(境界エラーを避ける) -
SL.con.4: don’t use
memset
ormemcpy
for arguments that are not trivially-copyable
(トリビアルコピー可能ではない型の引数にmemset
やmemcpy
を使わない)
SL.str: String / 文字列
-
SL.str.1: Use
std::string
to own character sequences
(文字列を所有するにはstd::string
を使う) -
SL.str.2: Use
std::string_view
orgsl::span<char>
to refer to character sequences
(文字列を参照するにはstd::string_view
やgsl::span<char>
を使う) -
SL.str.3: Use
zstring
orczstring
to refer to a C-style, zero-terminated, sequence of characters
(C文字列を参照するにはzstring
やczstring
を使う) -
SL.str.4: Use
char*
to refer to a single character
(1文字を参照するにはchar*
を使う) -
SL.str.5: Use
std::byte
to refer to byte values that do not necessarily represent characters
(文字とは限らない1バイトの値を参照するにはstd::byte
を使う) -
SL.str.10: Use
std::string
when you need to perform locale-sensitive string operations
(ロケール依存の文字列処理が必要ならstd::string
を使う) -
SL.str.11: Use
gsl::span<char>
rather thanstd::string_view
when you need to mutate a string
(文字列を変更する必要があるならstd::string_view
よりgsl::span<char>
を使う) -
SL.str.12: Use the
s
suffix for string literals meant to be standard-library strings
(文字列リテラルにはユーザー定義リテラルs
を付けてstd::string
であることを示す)
SL.io: Iostream / 入出力ストリーム
-
SL.io.1: Use character-level input only when you have to
(文字単位の入力は必要なときだけ使う) -
SL.io.2: When reading, always consider ill-formed input
(入力では、常に正しくないフォーマットで入力される場合を考慮する) -
SL.io.3: Prefer
iostream
s for I/O
(I/Oにはiostream
を優先的に使う) -
SL.io.10: Unless you use printf-family functions call
ios_base::sync_with_stdio(false)
(printf
系関数を使わないならios_base::sync_with_stdio(false)
を実行する) -
SL.io.50: Avoid
endl
(endl
を避ける)
SL.regex: Regex / 正規表現
未定義
SL.chrono: Time / 時間
未定義
SL.C: The C Standard Library / C標準ライブラリ
-
S.C.1: Don’t use
setjmp
/longjmp
(setjmp
/longjmp
を使わない)
A: Architectural Ideas / アーキテクチャー
-
A.1: Separate stable code from less stable code
(安定したコードと不安定なコードを分ける) -
A.2: Express potentially reusable parts as a library
(再利用できそうなものはライブラリにする) -
A.4: There should be no cycles among libraries
(ライブラリ間の依存関係が循環してはならない)
NR: Non-Rules and myths / ルールではないもの、迷信
-
NR.1: Don’t: All declarations should be at the top of a function
(NG: すべての宣言を関数の頭に置く) -
NR.2: Don’t: Have only a single return-statement in a function
(NG: return文は1つの関数につき1つまでにする) -
NR.3: Don’t: Don’t use exceptions
(NG: 例外を使わない) -
NR.4: Don’t: Place each class declaration in its own source file
(NG: 1つ1つのクラス宣言をそれ専用のソースファイルに置く) -
NR.5: Don’t: Don’t do substantive work in a constructor; instead use two-phase initialization
(NG: コンストラクタで実質的に何もせず、2段階で初期化する) -
NR.6: Don’t: Place all cleanup actions at the end of a function and goto exit
(NG: 後始末の処理を関数の最後に置き、goto exit:でジャンプする) -
NR.7: Don’t: Make all data members protected
(NG: すべてのデータメンバーをprotectedにする)
RF: References / 参考文献
(略) 参考文献の説明であり、コーディングガイドラインではない。
Pro: Profiles / プロファイル
※ プロファイルは、C++ Core Guidelinesのルールを機械的に検証しやすいように選んだサブセットであり、目的にあわせて使うことができる。
Pro.type: Type safety / 型安全性
- Type.1: Avoid casts:
(キャストを避ける)- a. Don’t use
reinterpret_cast
; A strict version of Avoid casts(ES.48) and prefer named casts(ES.49).
(reinterpret_cast
を使わない) - b. Don’t use
static_cast
for arithmetic types; A strict version of Avoid casts(ES.48) and prefer named casts(ES.49).
(算術型へのstatic_cast
を使わない) - c. Don’t cast between pointer types where the source type and the target type are the same; A strict version of Avoid casts(ES.48).
(ソースの型とターゲットの型が同じときはポインター型同士をキャストしない) - d. Don’t cast between pointer types when the conversion could be implicit; A strict version of Avoid casts(ES.48).
(変換が暗黙的になる可能性があるときは、ポインター型同士をキャストしない)
- a. Don’t use
- Type.2: Don’t use
static_cast
to downcast: Usedynamic_cast
instead(C.146).
(ダウンキャストにはstatic_cast
ではなくdynamic_cast
を使う(C.146)) - Type.3: Don’t use
const_cast
to cast away const (i.e., at all): Don’t cast away const(ES.50).
(const
を外さない) - Type.4: Don’t use C-style
(T)
expression or functionalT(expression)
casts: Prefer construction(ES.64) or named casts(ES.49).
(Cスタイルキャスト、関数スタイルのキャストを使用しない。その代わり、初期化(ES.64)や名前の付いたキャスト(ES.49)を用いる) - Type.5: Don’t use a variable before it has been initialized: always initialize(ES.20).
(変数は初期化する前に一切使わない) - Type.6: Always initialize a member variable: always initialize(ES.20), possibly using default constructors(C.43) or default member initializers(C.48).
(メンバー変数を必ず初期化する(ES.20)、特に、デフォルトコンストラクタ(C.43)またはデフォルトメンバー初期化子(C.48)を使う) - Type.7: Avoid naked
union
: Usevariant
instead(C.181).
(裸のunion
を避け、variant
を使う(C.181)) - Type.8: Avoid varargs: Don’t use
va_arg
arguments(F.55).
(可変長引数を使わない、特に、va_arg
を使わない(F.55))
Pro.bounds: Bounds safety / 境界安全性
- Bounds.1: Don’t use pointer arithmetic. Use
span
instead: Pass pointers to single objects (only)(I.13) and Keep pointer arithmetic simple.(ES.42)
(ポインターの算術演算を使わず、span
を使う。ポインターは1つのオブジェクトを表すためだけに使用する(I.13)。ポインターの演算は単純にする(ES.42)) - Bounds.2: Only index into arrays using constant expressions: Pass pointers to single objects (only)(I.13) and Keep pointer arithmetic simple.(ES.42)
(配列への添え字は定数式だけを使う。ポインターは1つのオブジェクトを表すためだけに使用する(I.13)。ポインターの演算は単純にする(ES.42)) - Bounds.3: No array-to-pointer decay: Pass pointers to single objects (only)(I.13) and Keep pointer arithmetic simple.(ES.42)
(配列からポインターへのdecayを利用しない。ポインターは1つのオブジェクトを表すためだけに使用する(I.13)。ポインターの演算は単純にする(ES.42)) - Bounds.4: Don’t use standard-library functions and types that are not bounds-checked: Use the standard library in a type-safe manner(SL.con.3).
(境界チェックのない標準ライブラリ関数と型を使用しない。標準ライブラリでの境界エラーを避ける(SL.con.3))
Pro.lifetime: Lifetime safety / ライフタイム安全性
- Lifetime.1: Don’t dereference a possibly invalid pointer: detect or avoid(ES.65).
(無効になる可能性のあるポインターをデリファレンスしない。検出するか回避する(ES.65))
GSL: Guideline support library / ガイドラインサポートライブラリ
(略) GSLの説明であり、コーディングガイドラインではない。GSLはC++ Core Guidelinesをサポートするライブラリで、ルールの中にはGSLに依存するものがある。
NL: Naming and layout / 名前付けとレイアウト
-
NL.1: Don’t say in comments what can be clearly stated in code
(コードで明確に表現できることをコメントで書かない) -
NL.2: State intent in comments
(意図をコメントに書く) -
NL.3: Keep comments crisp
(コメントは短く明快にする) -
NL.4: Maintain a consistent indentation style
(一貫したインデントスタイルを守る) -
NL.5: Avoid encoding type information in names
(型の情報を名前に埋め込まない) -
NL.7: Make the length of a name roughly proportional to the length of its scope
(名前の長さがスコープの長さにおおよそ比例するようにする) -
NL.8: Use a consistent naming style
(一貫した名前のスタイルを使う) -
NL.9: Use
ALL_CAPS
for macro names only
(すべて大文字の名前はマクロの名前だけに使う) -
NL.10: Prefer
underscore_style
names
(名前のスタイルをunderscore_style
にする) -
NL.11: Make literals readable
(リテラルを読みやすくする) -
NL.15: Use spaces sparingly
(スペースは控えめに使う) -
NL.16: Use a conventional class member declaration order
(クラスのメンバーの並びは慣習に従う) -
NL.17: Use K&R-derived layout
(K&Rから継承したレイアウトを使う) -
NL.18: Use C++-style declarator layout
(C++スタイルの宣言のレイアウトを使う) -
NL.19: Avoid names that are easily misread
(誤解を生む名前を避ける) -
NL.20: Don’t place two statements on the same line
(1行に2つの文を書かない) -
NL.21: Declare one name (only) per declaration
(1つの宣言で1つの名前だけを宣言する) -
NL.25: Don’t use
void
as an argument type
(引数リストにvoidを書かない) -
NL.26: Use conventional const notation
(const
の表記は慣習に従う)