- ベストアンサー
関数名、パラメータは同じで、戻り値によって異なる処理?
戻り値というより、受け側によって関数の振る舞いを変えたいのですが、 C++では、同名、同パラメータはC2556のコンパイルエラーになります。 Perlでいうリスト値を返すかスカラー値を返すかは呼び出し側によるようなことをしたいのですが、C++では無理でしょうか? 下の例では、//...部分は戻り値によって異なるのでC++のテンプレート?では無理そうですが、そんなことはC++でできるのでしょうか? 似たようなテクニックでも構いませんので、知識の豊富な方、教えてください。 #include <iostream> #include <string> using namespace std; class A { public: A(){} ~A(){} int test(int x, int y){ //... return 0; } string test(int x, int y){ // ... return ""; } }; void main(void){ A a; int ret1 = a.test(1,2); string ret2 = a.test(1,2); cout << endl << "End..." << endl; }
- みんなの回答 (4)
- 専門家の回答
質問者が選んだベストアンサー
決してお勧めはしませんが... class A { public: class B { A* a_; int x_, y_; public: explicit B(A* a, int x, int y) : a_(a), x_(x), y_(y) {} template <class T> operator T() const; }; B test(int x, int y) { return B(this, x, y); } }; template<> A::B::operator int() const { return 0; } template<> A::B::operator std::string() const { return ""; } int main() { A a; int i = a.test(1, 2); std::string s = a.test(1, 2); } とすれば解決できそうです。GCCではコンパイルできました。 (移植性があるかどうかは未確認)
その他の回答 (3)
- 麻野 なぎ(@AsanoNagi)
- ベストアンサー率45% (763/1670)
お勧めできるかどうかは別として、見かけが、普通の関数に見える方法としては、zwi さんのお書きになっている2)を準用すると。 class func() { public: func(int a, int b) { // コンストラクタ // ここで初期的に必要な処理 } operator int() { // 返値が int の場合(実際には、int への型変換関数) return 0; } operator string() { // 同じく string 用 return ""; } }; 等とできます。 これで、 int ret1 = func(1,2); string ret2 = func(1,2); は、ちゃんと、それなりの動きをします。 動作としては、返値の型を変えているのではなくて、func というクラスのインスタンスを生成して、それを、int なり string に型変換したというものです。
- koko_u_
- ベストアンサー率18% (459/2509)
普通に考えて int test(int, int) std::string test(int, int) の両方が定義できてしまうと、 ret1 = a.test(1, 2); が「正当な」代入であるか判断できませんよね。 ret1 = a.test<std::string>(1, 2); とできるように template<typename T> T test(int, int) { ... } とするとか?
- zwi
- ベストアンサー率56% (730/1282)
方法は3つですかね。 (1)戻り値は諦めて、パラメータ参照渡しにして関数自身をオーバーロードする。 (2)関数の結果を直接返さずに、クラス内に保持させて別関数で返すか、型変換のオーバーロードを使用する。 (3)完全にコンパイラをだます方法としては、パラメータが違えばオーバーロードできるので、ダミーのパラメータを片方につける。 って(3)は、だまし討ちなのでお勧めしませんが。