Successfully reported this slideshow.
We use your LinkedIn profile and activity data to personalize ads and to show you more relevant ads. You can change your ad preferences anytime.

One-Phase Construction

788 views

Published on

  • Be the first to comment

One-Phase Construction

  1. 1. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 . ...... One-Phase Construction hatsusato 京都大学理学部 2 回生 2013 年 10 月 3 日 1 / 23
  2. 2. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. 自己紹介 @hatsusato のプロフィール 理学部数学系志望 C++一筋 アニメ好き作画オタク 2 / 23
  3. 3. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. 目次 ...1 emplace、使ってますか? ...2 one-phase construction とは? ...3 one-phase construction 教の夢 3 / 23
  4. 4. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. emplace、使ってますか? ...1 emplace、使ってますか? ...2 one-phase construction とは? ...3 one-phase construction 教の夢 4 / 23
  5. 5. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. emplace C++11 以降、標準コンテナの多くが emplace や emplace back といった名前のメンバ関数を持つように なった。 これらはコンテナに要素を追加するメンバ関数なのだが、 一体どういう機能を持っているのか。 同じく要素を追加する insert や push back とは何が違 うのか。 // 従 来 の 要 素 を 追 加 す る メ ン バ 関 数 iterator insert( const_iterator pos , const T& value ); void push_back(const T& value ); // e m p l a c e の シ グ ネ チ ャ template <class ... Args > iterator emplace( const_iterator pos , Args &&... args ); // e m p l a c e _ b a c k の シ グ ネ チ ャ template <class ... Args > void emplace_back (Args &&... args ); 5 / 23
  6. 6. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. emplace insert や push back は T 型のオブジェクトを引数にと る。新しくオブジェクトを作って追加したい時は、一時 オブジェクトをコンストラクトして引数に渡してやる必 要がある。 emplace や emplace back はその代わりに T のコンストラ クタ引数を受け取り、オブジェクトのコンストラクトを コンテナへの追加と同時に行うことができる。 // 従 来 の 要 素 を 追 加 す る メ ン バ 関 数 iterator insert( const_iterator pos , const T& value ); void push_back(const T& value ); // e m p l a c e の シ グ ネ チ ャ template <class ... Args > iterator emplace( const_iterator pos , Args &&... args ); // e m p l a c e _ b a c k の シ グ ネ チ ャ template <class ... Args > void emplace_back (Args &&... args ); 6 / 23
  7. 7. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. emplace struct X { X(int) { std :: cout << " Constructor ." << std:: endl; } X(const X&) { std :: cout << "Copy constructor ." << std :: endl; } X(X&&) { std :: cout << "Move constructor ." << std :: endl; } }; int main () { std :: vector <X> vec; vec.reserve (2); vec.push_back(X(42)); // Constructor . // Move constructor . vec. emplace_back (42); // Constructor . return 0; } 7 / 23
  8. 8. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. emplace insert や push back の場合、コンストラクタ 1 回とコ ピーコンストラクタ 1 回とが実行される。 C++11 以降はムーブの仕組みがあるため、T 型が MoveConstructable なら、コンストラクタ 1 回とムーブ コンストラクタ 1 回とが実行される。 emplace や emplace back の場合、コンストラクタ 1 回の みが実行される。 std :: vector <X> vec; vec.reserve (2); vec.push_back(X(42)); // Constructor . // Move constructor . vec. emplace_back (42); // Constructor . 8 / 23
  9. 9. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. piecewise construct C++11 から新しく std::piecewise construct t 型の std::piecewise construct という constexpr 定数が追 加され、それに伴い std::pair に新しいコンストラクタ が追加されました。 std::piecewise construct はタグとして機能し、以降の 引数の std::tuple を first と second のコンストラクタ 引数として利用することを明示します。 このタグがないと tuple の pair が作れない。 // p a i r の 新 し い コ ン ス ト ラ ク タ の シ グ ネ チ ャ template <class ... Args1 , class ... Args2 > pair(std :: piecewise_construct_t , // タ グ std ::tuple <Args1 ...> first_args , // 引 数 の tuple std ::tuple <Args2 ...> second_args ); // 引 数 の tuple 9 / 23
  10. 10. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. piecewise construct // std :: piecewise_constructの 利 用 例 struct Unmovable { template <class ... Args > Unmovable(Args ...) {} Unmovable(Unmovable &&) = delete; Unmovable& operator =( Unmovable &&) = delete; }; std ::map <std :: string , Unmovable > map; // std ::map :: value_typeはstd ::pair <const Key , T> // e m p l a c e は v a l u e _ t y p e の コ ン ス ト ラ ク タ 引 数 を 引 数 に 取 る map.emplace(std :: piecewise_construct , // 引 数 を t u p l e に し て 転 送 std :: forward_as_tuple (10, ’a’), std :: forward_as_tuple (1, 2, 3, 4)); 10 / 23
  11. 11. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. one-phase construction とは? ...1 emplace、使ってますか? ...2 one-phase construction とは? ...3 one-phase construction 教の夢 11 / 23
  12. 12. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. one-phase construction とは? http://bit.ly/95tgcT → http://www.boost.org/doc/libs/1_54_0/libs/utility/in_place_factories.html http://bit.ly/9r8QCH → http://www.boost.org/doc/libs/1_54_0/libs/serialization/doc/serialization.html#const 12 / 23
  13. 13. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. one-phase construction とは? one-phase construction とは、 コンストラクト時に「コンストラクタ 引数のオブジェクト」の代わりに「引 数のオブジェクトのコンストラクタ引 数」を受け取り、適切に引数の転送を することでコンストラクトを遅延し、 余分な一時オブジェクトの生成を抑制 する機構のことである。 先の emplace と piecewise construct はその一例。 これにより従来潜在的に存在した余分な実行時コスト (中 間オブジェクトの生成と破棄) を削減し、さらに高速な コードの生成が可能になる。 13 / 23
  14. 14. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. ムーブがあるんだし、それで十分じゃないの? 14 / 23
  15. 15. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. ムーブがあるんだし、それで十分じゃないの? 確かに、ほとんどの場合、ムーブコンストラクタは十分 に高速なので、そのムーブコンストラクタ呼び出しを省 略したところで実行時速度はあまり変わらない。 しかし、ムーブが高速でないクラス (ムーブ=コピーかつ コピーが重たいクラスなど) や、Copyable でも Movable でもないクラス (mutex など) も高速に構築できる点で one-phase construction は優れている。 one-phase construction はコピーおよびムーブを行わな いので、オブジェクトのアドレスは変化しない。した がってオブジェクトのアドレスの不変性が重要な mutex や atomic オブジェクトでもコンテナに格納することがで きる。 14 / 23
  16. 16. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. ムーブがあるんだし、それで十分じゃないの? struct Unmovable { Unmovable () = default; Unmovable(Unmovable &&) = delete; Unmovable& operator =( Unmovable &&) = delete; }; struct HeavyToMove { HeavyToMove () = default: HeavyToMove ( HeavyToMove &&) = default; HeavyToMove & operator =( HeavyToMove &&) = default; HeavyToCopy data [1024]; // コ ピ ー が 重 た い ク ラ ス }; // Unmovableはstd :: l i s t で 保 持 す る 必 要 が あ る std ::list <Unmovable > list; list. emplace_back (); // ム ー ブ し て い な い の で 構 築 可 能 std :: vector <HeavyToMove > vector; vector. emplace_back (); // ム ー ブ し て い な い の で 高 速 15 / 23
  17. 17. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. そんなに速くなってどうするの? 16 / 23
  18. 18. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. そんなに速くなってどうするの? C++er にそんなことを言ってはいけません。 速ければ速い方がいいのです。 16 / 23
  19. 19. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. one-phase construction 教の夢 ...1 emplace、使ってますか? ...2 one-phase construction とは? ...3 one-phase construction 教の夢 17 / 23
  20. 20. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. 構築と初期化の一体化 引数の tuple から one-phase でオブジェクト構築できる なら、それを入れ子にすることでより複雑なオブジェク トでも one-phase で構築できるのでは? つまり、引数リストの木をコンストラクタ引数にとるこ とで、一瞬でオブジェクトを構築できるのでは? 18 / 23
  21. 21. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. 構築と初期化の一体化 // こ ん な 感 じ struct A {}; struct B {}; struct C { C(const A&, const B&) {} }; struct D {}; struct E { E(const D&) {} }; struct F { F(const E&) {} }; struct X { X(const C&, const F&) {} }; X x{{{} , {}}, {{{}}}}; // R V O が 働 い て い る ? // X x{C{A{}, B{}}, F{E{D{}}}}; 19 / 23
  22. 22. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. 構築と初期化の一体化 one-phase construction は無条件に利用できるわけでは なく、標準の emplace や piecewise construct をタグに 取るコンストラクタと同様の実装を、ユーザ定義クラス のコンストラクタでも行う必要がある。可変長テンプ レートと Perfect Forwarding のある現在においてその実 装はそれほど困難ではないが、すべてのユーザ定義クラ スにわたってそのようなコンストラクタを提供するのは 大きなコストである。 もし、言語機能として one-phase construction をユーザ 定義クラスにおいても非侵入的に提供することが出来れ ば、オブジェクトの構築と初期化が一体化したより最適 化された理想郷の恩恵を、より広い範囲にわたって受け ることができるだろう。 20 / 23
  23. 23. emplace、使ってますか? one-phase construction とは? one-phase construction 教の夢 .. 構築と初期化の一体化 21 / 23
  24. 24. 参考文献 .. 参考文献 . N3059 - Togetter .. ......http://togetter.com/li/17236 . One-Phase Construction 入門 ∼ Constructor run once. - 野 良 C++er の雑記帳 .. ......http://d.hatena.ne.jp/gintenlabo/20101210/1291914878 . rvalue-reference で one-phase construction - 野良 C++er の 雑記帳 .. ......http://d.hatena.ne.jp/gintenlabo/20101211/1292088788 22 / 23
  25. 25. 参考文献 .. 参考文献 . pair の piecewise construction - Faith and Brave - C++で遊 ぼう .. ......http://d.hatena.ne.jp/faith_and_brave/20100428/1272422821 . c++ - When to make a type non-movable in C++11? - Stack Overflow .. ...... http://stackoverflow.com/questions/14302834/ when-to-make-a-type-non-movable-in-c11 23 / 23

×