6

これはもっと公的な暴言だと思いますが、なぜc#でIDのタイプを推測できないのですか?

public EntityT Get<EntityT>(IdT id) where EntityT : EntityObject<IdT>

次のように、IDとしてGuidを持つ定義済みのEntityObject:

public Foo : EntityObject<Guid>

次のように定義された抽象EntityObjectクラスから継承します。

public abstract class EntityObject<IdT>
{
    public IdT id { get; set; }
}

getメソッドの使用法は次のようになります。

IRepository repository = new Repository();
var hydratedFoo = repository.Get<Foo>(someGuidId);

さらに明確にするために編集されました。

4

4 に答える 4

3

どのように使用しているかではなく、2 つの宣言しか与えていないことを考えると、言うのは難しいです。IdT は別の型パラメータですか? (それがTIdである場合、それはそうであることが示唆されます-しかし、EntityT慣習に反して、別の型パラメーターに使用しているという事実は、おそらくIdT同様であることを示唆しています...)

IdTさて、あなたの場合が実際にあると仮定Guidすると、コンパイラはどのように機能するのFooでしょうか? から派生した他のタイプが存在する可能性がありますEntityObject<Guid>

要するに、確実に何かを伝えるのに十分な情報を提供していませんが、基本的にコンパイラに対して不当な要求をしているように思えます。

編集:さて、通常の命名規則を使用して、あなたが持っているものについての私の推測は次のとおりです:

public interface IRepository
{
    TEntity Get<TEntity, TId>(TId id) where TEntity : EntityObject<TId>
}

public abstract class EntityObject<TId>
{
    public IdT id { get; set; }
}

public class Foo : EntityObject<Guid> {} 

あなたがしたい:

IRepository repository = GetRepositoryFromSomewhere();
Foo foo = repository.Get<Foo>(someGuid);

現在、あなたがしなければならないのは:

Foo foo = repository.Get<Foo, Guid>(someGuid);

はい、コンパイラは必要以上に少し難しくしています。言語をより単純にし、型推論のルールを理解しやすくするために、6 文字を追加しました。

基本的に、型推論はすべてか無かの問題です -すべての型パラメータが推論されるか、どれも推論されないかのどちらかです。これにより、どれが指定されていてどれが指定されていないかを判断する必要がないため、シンプルに保たれます。それは問題の一部であり、他の部分は、メソッドの型パラメーターに対してのみ制約を表現できることです。次のことはできません。

class Repository<TEntity>
{
    TEntity Get<TId>(TId id) where TEntity : EntityObject<TId>
}

それは制約TEntityであり、ではありませんTId。繰り返しますが、この種のことは型推論をより簡単にします。

これで、潜在的に次のように書くことができます:

Foo foo = repository.Get(someGuid).For<Foo>();

適切なGetメソッドと追加のインターフェースを使用します。私は個人的にはただ使用することを好むと思いGet<Foo, Guid>ます。

于 2009-08-11T17:40:10.213 に答える
0

If your method signature looked like this:

public TEntity Get<TEntity, TId>(TId id) where TEntity : EntityObject<TId>

The compiler would have something to work with...

You then call get with something like:

EDIT (I was wrong): Product p = Get(id);

Product p = Get<Product, Guid>(id);

Jon's nailed this answer with his post up top so I'll shut up and crawl back in my hole.

于 2009-08-11T18:13:31.567 に答える
0

みたいな宣言

public EntityT Get<EntityT>(IdT id) where EntityT : EntityObject<IdT>

IdT が具象型であることを要求します。IdT もパラメータ化する場合は、使用する必要があります

public EntityT Get<EntityT, IdT>(IdT id) where EntityT : EntityObject<IdT>

しかし、それはおそらくあなたが望むものではありません。

于 2009-08-11T18:18:46.160 に答える
0

これが、一般的なエンティティを持つ一般的なキーの種類をあきらめた理由です。私は、エンティティに一般的なキー タイプを持たせる方法を理解できませんでした。今、私は整数キーに落ち着きました(とにかくどこにでもあります)が、それは間違っていると感じています。

于 2009-08-11T18:20:21.600 に答える