6

我想这更像是一种公开的咆哮,但为什么我不能让 c# 来推断我的 ID 类型?

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

以及一个以 Guid 作为 Id 的已定义 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

很难说你只给出了两个声明,而不是你如何使用它们。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

如果您的方法签名如下所示:

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

编译器将有一些东西可以使用......

然后你调用 get 类似的东西:

编辑(我错了):产品 p = Get(id);

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

乔恩用他的帖子在顶部确定了这个答案,所以我会闭嘴并爬回我的洞里。

于 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 回答