web-dev-qa-db-ja.com

演算子を使用した関数テンプレート

C++では、クラスにテンプレート化された演算子を含めることができますか?そのようです:

class MyClass {
public:
    template<class T>
    T operator()() { /* return some T */ };
}

これは実際には問題なくコンパイルされているように見えますが、どのように使用するかで混乱が生じます。

MyClass c;
int i = c<int>(); // This doesn't work
int i = (int)c(); // Neither does this*

それがまったくコンパイルされるという事実は、それが実行可能であることを私に示唆しています、私はそれをどのように使用するかについて途方に暮れています!何か提案がありますか、それともこの使用方法は初心者ではありませんか?

31
Toji

Tを指定する必要があります。

int i = c.operator()<int>();

残念ながら、この場合、関数呼び出し構文を直接使用することはできません。

編集:ああ、クラス定義の先頭にpublic:がありません。

44
avakar

あなたは基本的に正しいです。テンプレート化された演算子を定義することは合法ですが、明示的なテンプレート引数を使用して直接呼び出すことはできません。

この演算子がある場合:

_template <typename T>
T operator()();
_

あなたの例のように、それはこのようにのみ呼び出すことができます:

_int i = c.operator()<int>();
_

もちろん、テンプレートの引数を引数から推測できる場合でも、通常の方法で呼び出すことができます。

_template <typename T>
T operator()(T value);

c(42); // would call operator()<int>
_

別の方法として、引数を参照にして、出力を返す代わりにそこに格納することもできます。

_template <typename T>
void operator()(T& value);
_

したがって、これの代わりに:

_int r = c.operator()<int>();
_

あなたができる

_int r;
c(r);
_

あるいは、演算子を使用する代わりに、単純なget<T>()関数を定義する必要があるかもしれません。

18
jalf

あなたは考えていませんか

class Foo {
    public:
    template<typename T>
    operator T() const { return T(42); }
};

Foo foo;

int i = (int) foo; // less evil: static_cast<int>(foo);

実例 。これは、受け入れられた回答の主張にもかかわらず、テンプレート引数を指定する必要がないことを証明しています。

4
MSalters