yohhoyの日記

技術的メモをしていきたい日記

Effective C++11(の種)

Scott Meyers氏によるEffective C++11ネタ集を見つけたのでInitial Thoughts on Effective C++11より抄訳。

2014-03-23追記:本記事の内容はBook Report: New Title, New TOC, New Sample Itemにてアップデートされている。(2013-03-25 Effective C++11: Content and Status

2013-04-18追記:並行/並列関連だけ詳細化された姉妹版→Effective C++11/Concurrency関連の目次草案

  • 明示的な型宣言よりもautoを使おう
  • オブジェクトの生成では () と {} を区別しよう
  • ただしauto + { expr } == std::initializer_listは忘れずに(auto x{1};/auto x={1};ではstd::initializer_list<int>型、auto x(1);/auto x=(1);ではint型。)
    • 2014-12-08追記:C++1z(C++17?)ではauto x{1};はint型、auto x={1};のみstd::initializer_list<int>型と推論されるよう言語仕様が変更される。
  • メンバ関数版よりも非メンバ関数begin/endを使おう
  • std::threadメンバの宣言はクラス末尾に置こう(メンバ変数初期化順序に起因するバグ回避のためと思われる。)
  • メンバ関数の外に出すラムダ式のデフォルトキャプチャモードに注意(特にthisのdangling pointer化。)
  • コンテナにはInsertion(挿入)よりもEmplacement(直接構築)を使おう
  • 非同期処理が必須ならstd::launch::asyncポリシーを指定しよう(→id:yohhoy:20120203)
  • 弱いatomic変数の利用は最小限に(既定値std::memory_order_seq_cst以外のatomic変数アクセスは極力避ける。)
  • Universal ReferenceとRvalue Referenceを区別しよう(→Universal References in C++11)((関数テンプレートtemplate<class T> void f(T&&)におけるT&&と、それ以外における型Tのrvalue参照型T&&の違い))
  • ムーブ操作は存在するわけでもないし低コストなわけでもないと想定しよう(意図不明。「いつでも低コストでムーブできると思うな」ということ?)
  • バインダよりもラムダ式を使おう
  • スレッディング関数には可変個引数よりもラムダ式を渡そう(意図不明。おそらくstd::threadコンストラクタ引数の話。)
  • オーバーサブスクリプションに気を付けよう(システム並列度を上回るスレッドを作り過ぎないこと。)
  • Universal Referenceで引数を渡すときはstd::forwardの適用を(いわゆる“Perfect Forwarding”)
  • 組込み配列よりもstd::arrayを使おう
  • 出来る限りstd::make_sharedを使おう(→id:gintenlabo:20091214:1260804379)
  • std::shared_ptr型では値渡しよりもconst参照渡しを使おう(→C++のshared_ptrを関数への引数として渡す場合はconst参照で
  • 引数のコピーが必要なら値渡しを使おう(コピーが必要なら関数呼び出しと同時に行えばよい。)
  • Wideインタフェースの関数では無暗にnoexceptとしない(おそらく→N3248 noexcept Prevents Library Validation
  • コピー可能な型では、ムーブは最適化コピーと考えよう
  • 列挙型(enum)よりも型付き列挙型(enum class)を使おう
  • NULLや定数0よりもnullptrを使おう
  • std::enable_if, static_assert, =deleteを区別しよう