回答の過程で別の質問std::vector::erase()
との表現が少し異なることに気づきましたstd::deque::erase()
。
std::deque::erase
C++14 では( [deque.modifiers]/4-6
、強調は筆者による)について次のように述べています。
効果:...
複雑:デストラクタの呼び出し回数は削除される要素の数と同じですが、代入演算子消去された要素の前の要素数と消去された要素の後の要素数のうち小さい方の数以下になります。
スロー:のコピー コンストラクター、移動コンストラクター、代入演算子、または移動代入演算子によって例外がスローされない限り、何も起こりません
T
。
そして、std::vector::erase
([vector.modifiers]/3-5
)については次のように書かれています。
効果:...
複雑:のデストラクタは、
T
削除された要素の数と同じ回数だけ呼び出されますが、移動代入演算子は、T
消去された要素の後のベクトルの要素の数に等しい回数と呼ばれます。スロー:のコピー コンストラクター、移動コンストラクター、代入演算子、または移動代入演算子によって例外がスローされない限り、何も起こりません
T
。
ご覧のとおり、両方の例外仕様は同じですが、std::vector
移動代入演算子が呼び出されることが明示的に記載されています。
との両方で動作するためにT
が である必要もあります(表 100)。ただし、これは移動代入演算子の存在を意味するものではありません。コピー代入演算子を定義し、移動代入演算子を定義しない場合、このクラスは になります。MoveAssignable
erase()
std::vector
std::deque
MoveAssignable
念のため、GCCとClangで確認したところ、std::vector::erase()
移動代入演算子がない場合はコピー代入演算子を呼び出し、std::deque::erase()
同じことを行います(デモ)。
そこで質問ですが、私が何かを見逃したのか、それともこれは標準の(編集上の)問題なのでしょうか?
アップデート:私は提出しましたLWG 問題 #2477。
ベストアンサー1
レネクサ会議で問題即時ステータスを取得提案された決議:
この文言は N4296 に関連しています。
23.3.3.4 [deque.modifiers]/5 を次のように変更します。
-5-複雑: デストラクタの呼び出し回数の
T
削除された要素の数と同じだが、代入演算子の呼び出し回数はのT
消去された要素の前の要素の数と消去された要素の後の要素の数のうち小さい方の数以下になります。23.3.6.5 [vector.modifiers]/4 を次のように変更します。
-4-複雑: のデストラクタは
T
消去された要素の数に等しい回数呼び出されますが、 の移動代入演算子はT
消去された要素の後のベクトルの要素の数に等しい回数呼び出されます。
つまり、この解決策が受け入れられれば、 の移動割り当てについては特に言及されなくなりstd::vector::erase
、 の文言もstd::deque::erase
少し明確化されることになります。