2017-09-22 5 views
3

私はAudioRequestまたはVideoRequestのオブジェクトを持っています。どちらのクラスもRequestから継承します。私はこのクラスを持っている:パラメータのタイプに基づいた呼び出し方法

public static DoThings 
{ 
    public static void HandleRequest(AudioRequest r) 
    { 
     // Do things. 
    } 

    public static void HandleRequest(VideoRequest r) 
    { 
     // Do things. 
    } 
} 

私はrVideoRequestまたはAudioRequestのいずれであってもよく、それが正しいものを呼び出すことができますどこDoThings.HandleRequest(r)を呼び出すことができるようにしたいです。それは可能ですか?私は*Requestクラスを制御できないので、何もできません。私はクラスとHandleRequestというコードを管理しています。これは、それを呼び出すコードで、それはWebAPIのである:

public Response Post(Request input) 
{ 
    return DoThings.HandleRequest(input); 
} 

上記のコードはエラーArgument 1: cannot convert from 'Request' to 'AudioRequest'を与えます。

私が掃除された元のコードは、この持っていた:

if (input.GetType() == typeof(AudioRequest)) 
{ 
    var audioRequest = (AudioRequest)input; 
    DoThings.HandleRequest(audioRequest); 
} 
else if (input.GetType() == typeof(VideoRequest)) 
{ 
    var videoRequest = (VideoRequest)input; 
    DoThings.HandleRequest(videoRequest); 
} 

をしかし、私はこれを行うにはクリーンな方法があった考え出しました。

+1

オーバーロードには、AudioRequest型のパラメータと、VideoRequest型のパラメータを持つパラメータが必要です。 – EvilTak

+2

確かにそれは2つの同じ機能を持つタイプミスですか?そのうちの1人は 'VideoRequest'引数を受け入れます。そうしないと、コンパイルエラーが発生します。 –

+0

おっと、私の間違いです。はい、もう1つはVideoRequestです。 – vkapadia

答えて

1

これまでにご提供いただいた情報に基づいて、ご質問はHow to call a function dynamically based on an object typeと重複しているようです。私は答えに同意する、あなたがこれをしたいという事実は、あなたがデザインを再考すべきであることを示唆している。しかし、dynamicを使って、あなたが望むものを達成することができます。ここで

は、基本的な考え方を示し、単純なコンソールプログラムです:

class Program 
{ 
    static void Main(string[] args) 
    { 
     A b = new B(), c = new C(); 

     M(b); 
     M(c); 
    } 

    static void M(A a) 
    { 
     WriteLine("M(A)"); 
     M((dynamic)a); 
    } 

    static void M(B b) 
    { 
     WriteLine("M(B)"); 
    } 

    static void M(C c) 
    { 
     WriteLine("M(C)"); 
    } 
} 

class A { } 
class B : A { } 
class C : A { } 

出力は次のようになります。そして、あなたが見ることができるように、それぞれの場合にM(A)メソッドが最初に呼び出され

M(A) 
M(B) 
M(A) 
M(C)

、および適切なM(B)またはM(C)のオーバーロードは、M(A)から呼び出されます。あなた自身の例では

、これは次のようになります:dynamicは、実行時のコスト、方法が与えられ、実行時の型と呼ばれ、特に最初の時間を招くないこと

public static DoThings 
{ 
    public static void HandleRequest(Request r) 
    { 
     // Dynamic dispatch to actual method: 
     HandleRequest((dynamic)r); 
    } 

    public static void HandleRequest(AudioRequest r) 
    { 
     // Do things. 
    } 

    public static void HandleRequest(VideoRequest r) 
    { 
     // Do things. 
    } 
} 

注意を。しかし、これらの「要求」の頻度と複雑さに応じて、dynamicを使用すると、現在の状況から最もきれいな方法になる可能性があります。

+0

これは最もクリーンな方法のようです。私はオーバーヘッドが私の場合には関連しているとは思っていません。かなりボリュームの小さいサービスです。私は '動的な 'こと、あるいは一連のif/else文を実行します。ありがとう! – vkapadia

0

C#は、引数とその型に一致する適切な関数を呼び出します。 あなたの機能の両方がAudioRequestを受け入れていると言われていますが、そのうちの1つはVideoRequestを受け入れるべきだと思います。何らかの理由であなただけのAudioRequestを取る2つの異なる機能を持っている必要があります場合は、追加のパラメータを持つ2つの機能の間

public static DoThings 
{ 
    public static void HandleRequest(AudioRequest r) 
    { 
     // Do things. 
    } 

    public static void HandleRequest(VideoRequest r) 
    { 
     // Do things. 
    } 
} 
+0

あなたはそれを信じる理由がありますか?パラメータのコンパイル時の型は実際にオブジェクトの種類によって異なりますか?あるいは、基本クラスの 'Request'よりも何か_ –

+0

@PeterDunihoこれは、AudioRequestやVideoRequest以外の何ものでもありません。基本リクエストでもありません。 – vkapadia

+0

@JoshuaWaring私はそれを試しました、それは決定しない、私にエラーを与える(ちょうど上記の質問にエラーを入れてください)。 – vkapadia

-2

区別することができます

public static class DoThings 
{ 
    public static void HandleRequest(AudioRequest r) 
    { 
     // Do things. 
    } 

    public static void HandleRequest(AudioRequest r, bool UseAlternativeMethod) 
    { 
     // Do other things. 
    } 
} 

単純にかかわらず、第二の方法を呼び出す二番目のパラメータを持ちますそれは価値です。

正確な方法名の名前を正確に変更して区別するのがベストプラクティスの解決策ではありませんが、実際には必ずしも選択肢がありません。

+1

この問題は、私が想定している機能が、関数を呼び出すことができ、インタプリタが手動で呼び出す代わりにどの関数を呼び出すかを決定できることです。 それ以外の場合、ソリューションは異なる関数名を使用する場合と同じくらい単純になります。 –

+0

私の間違いでした。 2番目のHandleRequestはVideoRequestオブジェクトを取り込む必要があります。 – vkapadia

関連する問題