2017-10-03 14 views
14

vector<bool> vec_boolがある場合、|=割り当て演算子を使用してベクトルの内容を変更することはできません。ラインなぜ離接代入演算子| =はboolのベクトルでは機能しないのですか?

bool a = false; 
a |= true; 
a |= vec_bool[0]; 
vec_bool[0] = vec_bool[0] | vec_bool[1]; 
vec_bool[0] = vec_bool[0] || vec_bool[1]; 

vector<int> vec_int(3); 
vec_int[0] |= vec_int[1]; 

がいないのに対し、ライン

vec_bool[0] |= true; 
vec_bool[0] |= vec_bool[1]; 

所与のコンパイルエラーです。これの理由は何ですか?

(GCCによって)指定されたエラーがある:それはstd::vectorの主要専門のためのものであるように

test.cpp:21:17: error: no match for ‘operator|=’ (operand types are ‘std::vector::reference {aka std::_Bit_reference}’ and ‘bool’)

+14

['std :: vector '](http://en.cppreference.com/w/cpp/container/vector_bool)は*普通の*ベクトルではないことに注意してください。これは 'bool'の実際のベクトルではありませんが、C++仕様で実装が指定されていないビットのベクトルによく似ています。 –

+2

[なぜstd :: vector に.data()がないのですか?](https://stackoverflow.com/questions/46115669/why-does-stdvectorbool-has-no-data) –

+2

それについての詳細はhttp://en.cppreference.com/w/cpp/container/vector_boolをご覧ください。 – cbuchart

答えて

18

std::vector<bool>operator[]から返さreferenceは、bool&の別名ではありません。むしろC++ standard as thisによって指定されています

// bit reference: 
class reference { 
    friend class vector; 
    reference() noexcept; 
public: 
    ~reference(); 
    operator bool() const noexcept; 
    reference& operator=(const bool x) noexcept; 
    reference& operator=(const reference& x) noexcept; 
    void flip() noexcept;  // flips the bit 
}; 

そして、あなたが見ることができるように、宣言されたoperator |=はありません。したがって、vec_bool[0]から返された参照には適用できません。

vec_bool[0] = vec_bool[0] | vec_bool[1];が動作する理由は、上記のオーバーロードがそれを容易にするであるということです。 operator bool()は、組み込みの|の2つのオペランドをboolの値に変換します。そして、代入演算子referenceは、結果をvec_bool[0]に戻します。

C++標準で指定されているように、std::vector<bool>は特に優れた抽象化ではありません。

+0

ありがとう! 'ベクトル'がベクタータイプの '標準的な'実装から逸脱している唯一のタイプのベクターであるかどうか教えてください。 –

+6

@MeesdeVries - これは、C++標準が主宣言から逸脱することを義務づけている唯一のものです。他のすべてのものは、プライマリテンプレートのものとみなすことができます。 – StoryTeller

+3

...言い換えれば、パフォーマンスの理由から特殊化されているものもありますが、ポータブルコードでは検出できません。 – MSalters

関連する問題