2017-07-31 10 views
3
私は2013年

のstd ::移動(STD ::配列)G ++ VSビジュアルC++

だから私が試したVisual Studioで私のプロジェクトでの移動の私のstd内の要素のコンストラクタ::配列を実装するいくつかの問題を抱えていた

私がg ++ 5.3.0でコンパイルしたnotepad ++の最小限の例を作っています。

#include <iostream> 
#include <array> 

using namespace std; 

struct A{ 
    A() = default; 
    A(const A&) 
    { 
     cout << "copy constructed" << endl; 
    } 
    A(A&&) 
    { 
     cout << "move constructed" << endl; 
    } 
}; 

class B{ 
public: 
    B(array<A, 2>&& a) 
     : m_a(std::move(a)) 
    {} 
private: 
    array<A, 2> m_a; 
}; 

int main(){ 
    A foo; 
    cout << "=========1===========" << endl; 
    array<A, 2> a = { { foo, std::move(foo) } }; 
    cout << "=========2===========" << endl; 
    B b(std::move(a)); 
    cout << "=========3===========" << endl; 
    array<A, 2> a_second = std::move(a); 
    return 0; 
} 

出力:だけ私は

例G ++しようとしていたものを行うことができ++グラムのそれを見つけるため

========= 1 === ========
コピー
移動が
動きがを構築
========= 2 ===========を構築構築 動きは同じ
動きは私が(実際に)しようとしたとき
移動が

を構築構築
========= 3 ===========を構築しましたVisual Studioでコード2013、結果は違っていた:

出力:

========= 1 ===========
コピーがを構築 動きは
を構築 ========= 2 ===========
コピー
コピー
========= 3を構築構築=== ========
コピーはどのように視覚的なCに移動コンストラクタを使用することができ++、なぜここに彼を使用することを拒否Visual C++にはありません

を構築
コピーを構築しましたか?

+0

OT、本当に不要な 'stdafx.h'と' _tmain'のために2つのコードサンプルを投稿する必要がありましたか? – LogicStuff

+1

[Off Topic] 'B(配列&a):m_a(std :: move(a))'は、何かをオブジェクトに移動する方法ではありません。コールサイト内のオブジェクトは、それが何の指示もなく移動したままになります。 – NathanOliver

+0

@LogicStuff私は何か違うことをしていないことを示したかったのです。 – turoni

答えて

4

これはMSVS 2013のバグです.MSVS 2013 does not generate implicit move constructors。 MSVS 2015または2017で実行すると、同じ出力が得られます。


私はまた、あなたがBにオブジェクトを移動する方法を

B(array<A, 2>& a) : m_a(std::move(a)) 

ではないことを指摘したいと思います。あなたはBは、配列を引き継ぐようにしたい場合は、この代わりに

B b(a); 

を使用してのあなたは

B b(std::move(a)); 

を使用する必要があり、今あなたがはっきりすることを見ることができることを意味し

B(array<A, 2>&& a) : m_a(std::move(a)) 

を持つべきですamainから移動されました。

+0

Bのためのより良いコンストラクタで編集しました。 MSV2013で同じ結果を得る方法はありますか? – turoni

+1

@ turoni残念ながらいいえ。それはちょうど正しく動作するように作られていません。 – NathanOliver

+0

@turoni継承のように 'std :: array'をラップする型を記述し、手動で移動コンストラクタを実装することができます。 MSVC2013はあなたのために適切な移動コードを書くことは決してありませんし、 'noexcept'を許可しません。 MSVC2017は適切な 'noexcept'が' std :: vector'で正しく動作することを要求します。それは大きな痛みです。 – Yakk

2

Visual Studio 2013はC++ 11と完全に互換性がありません。 stdコンテナの移動サポートは、「完全実装されていない」パーツの1つです。 あなたの例はVS2017の最新バージョンについては問題ありません。at Rextesterを参照してください。

P.S. Hereでは、さまざまなコンパイラでC++機能のサポートに関する詳細情報を得ることができます。

関連する問題