8

C++11 の可変個引数テンプレートを使用して、以下を完成させることはできますか/* ??? */?

template<bool...v> struct var_and { static bool constexpr value = /* ??? */; };

コンパイル時にブール値パックをvar_and<v...>::value提供しますか?&&v

struct var_or<v...>に対しても同じことができます||か?

短絡評価(両方とも)は使えますか?

編集:受け入れられた回答への更新により、 C ++ 17の折りたたみ式が有効になることが追加されました

template<bool... v> constexpr bool var_and = (v && ...);
template<bool... v> constexpr bool var_or  = (v || ...);

パラメータパックベースのアプローチでは、制限されたタイプの「短絡評価」のみが可能であるようです:var_or<true,foo(),bar()>呼び出しを 1 回だけインスタンス化しながら、と||の両方も呼び出します。foobar

4

2 に答える 2

11

valueあなたはtypedefになりたくありません。

template<bool head, bool... tail>
struct var_and {
    static constexpr bool value = head && var_and<tail...>::value;
};

template<bool b> struct var_and<b> {
    static constexpr bool value = b;
};

に対しても同じことができることは明らかです||

これは副作用のない定数式のみを扱うため、短絡評価は重要ではありません。

これは、偽の値を見つけるとすぐに型の再帰的な生成を停止し、一種の短絡をエミュレートする別の方法です。

template<bool head, bool... tail>
struct var_and { static constexpr bool value = false; };

template<bool... tail> struct var_and<true,tail...> {
    static constexpr bool value = var_and<tail...>::value;
};

template<> struct var_and<true> {
    static constexpr bool value = true;
};

C++17 の更新: フォールド式を使用すると、これがはるかに簡単になります。

template<bool...v> struct var_and {
    static constexpr bool value = (v && ...);
};

または、enobayram が示唆するようにテンプレート変数を使用することもできます。

template<bool... b> constexpr bool var_and = (b && ...);
于 2012-08-09T22:20:03.517 に答える