名前空間
変種
操作

std::variant<Types...>::valueless_by_exception

From cppreference.com
< cpp‎ | utility‎ | variant
 
 
ユーティリティライブラリ
言語サポート
型のサポート (基本型、RTTI)
ライブラリ機能検査マクロ (C++20)
プログラムユーティリティ
可変引数関数
コルーチンサポート (C++20)
契約サポート (C++26)
三方比較
(C++20)
(C++20)(C++20)(C++20)  
(C++20)(C++20)(C++20)

汎用ユーティリティ
関係演算子 (C++20で非推奨)
 
 
constexpr bool valueless_by_exception() const noexcept;
(C++17以降)

バリアントが値を保持している場合にのみ false を返します。

[編集] 注釈

バリアントは、次のような状況で保持する値を初期化する際に値を持たない状態になることがあります。

  • (保証) ムーブ代入中に例外がスローされた場合
  • (オプション) コピー代入中に例外がスローされた場合
  • (オプション) 型を変更する 代入中に例外がスローされた場合
  • (オプション) 型を変更する emplace中に例外がスローされた場合

バリアントは動的メモリを割り当てることは許可されていないため、これらの状況では以前の値は保持できず、したがって復元もできません。「オプション」のケースでは、型が例外をスローしないムーブを提供しており、実装が最初に新しい値をスタック上に構築してからバリアントにムーブする場合、例外のスローを回避できます。

これは、クラス型以外のバリアントにも適用されます。

struct S
{
    operator int() { throw 42; }
};
std::variant<float, int> v{12.f}; // OK
v.emplace<1>(S()); // v may be valueless

値を持たない状態(例外により値を持たない状態)、すなわち、上記にリストされた状況のいずれかからの以前の例外により値を持っていないバリアントは、無効な状態にあると見なされます。

[編集]

#include <cassert>
#include <iostream>
#include <stdexcept>
#include <string>
#include <variant>
 
struct Demo
{
    Demo(int) {}
    Demo(const Demo&) { throw std::domain_error("copy ctor"); }
    Demo& operator= (const Demo&) = default;
};
 
int main()
{
    std::variant<std::string, Demo> var{"str"};
    assert(var.index() == 0);
    assert(std::get<0>(var) == "str");
    assert(var.valueless_by_exception() == false);
 
    try
    {
        var = Demo{555};
    }
    catch (const std::domain_error& ex)
    {
        std::cout << "1) Exception: " << ex.what() << '\n';
    }
    assert(var.index() == std::variant_npos);
    assert(var.valueless_by_exception() == true);
 
    // Now the var is "valueless" which is an invalid state caused
    // by an exception raised in the process of type-changing assignment.
 
    try
    {
        std::get<1>(var);
    }
    catch (const std::bad_variant_access& ex)
    {
        std::cout << "2) Exception: " << ex.what() << '\n';
    }
 
    var = "str2";
    assert(var.index() == 0);
    assert(std::get<0>(var) == "str2");
    assert(var.valueless_by_exception() == false);
}

実行結果の例

1) Exception: copy ctor
2) Exception: std::get: variant is valueless

[編集] 関連項目

インデックスまたは型(型が一意である場合)を指定して variant の値を読み取る。エラーの場合は例外をスローする
(function template) [編集]
variant が保持する代替型のゼロから始まるインデックスを返す
(public member function) [編集]
variant の値への不正なアクセス時にスローされる例外
(class) [編集]
English 日本語 中文(简体) 中文(繁體)