2

私は次のようなインターフェース契約を結んでいます:

ICollection<FooBar> FindByPredicate(Expression<Func<FooBar,bool>> predicate);
ICollection<Foo> FindByPredicate(Expression<Func<Foo,bool>> predicate);
ICollection<Bar> FindByPredicate(Expression<Func<Bar,bool>> predicate);

FooとBarは、FooBar抽象クラスを継承する具象クラスです。

これらのメソッドを呼び出そうとすると、問題が発生します。

var foo = myService.FindByPredicate(f => f.UserId == 1);

プロパティ「UserId」が抽象「FooBar」タイプに存在するため(したがって、FooとBarにも存在するため)、「あいまいな呼び出し」エラーが発生します。これは理にかなっています。

だから、どうすればこれを克服できますか?

呼び出し元のコードからのインテリセンスの観点から、メソッド名は1つしかないため、インターフェイス(オーバーロードされた述語メソッド)の外観が気に入っています。

なぜ私はそのような私のインターフェースを持っているのですか?「Foo」または「Bar」のみを返したいシナリオもあれば、混合バッグが必要なシナリオもあるので、抽象型を返す必要があります。意味がありますか?

とにかく、明らかな質問に-これを回避する方法はありますか?(インターフェイスメソッドの名前を変更する以外)?(したがって、単純さを損なう)

4

2 に答える 2

1

fを推測するのではなく、ラムダでのタイプを宣言できます。そうすれば、1つのオーバーロードのみが適用されます。

var foo = myService.FindByPredicate((Foo f) => f.UserId == 1);
var bar = myService.FindByPredicate((Bar f) => f.UserId == 1);
var foobar = myService.FindByPredicate((FooBar f) => f.UserId == 1);
于 2010-09-07T01:13:23.407 に答える
1

メソッドをジェネリックとして宣言すると、必要なメソッドは1つだけになります。

public interface IFooBarService
{
    ICollection<T> FindByPredicate<T>(Expression<Func<T, bool>> predicate)
        where T : FooBar;
}

そして、あなたはそれをこのように呼ぶことができます:

var foo = myService.FindByPredicate<Foo>(f => f.UserId == 1);
于 2010-09-07T02:13:03.547 に答える