C #.Возможно иметь статический универсальный класс с ограничением базового типа, у которого есть метод с дополнительным ограничением базового типа - PullRequest
3 голосов
/ 13 августа 2010

Я хотел бы иметь возможность создавать статический универсальный тип с ограничением базового типа, например

public static class Manager<T> where T : HasId
{
    public static T GetSingleById(ref List<T> items, Guid id)
    {
        // the Id is a property provided by HasId
        return (from i in items where i.Id == id select i).SingleOrDefault();
    }
}

Затем добавьте еще один метод

...
    public static IEnumerable<T> GetManyByParentId(ref List<T> items, Guid parentId) where T : HasIdAndParentId
    {
        // the parentId is a property of HasIdAndParentId which subclasses HasId
        return from i in items where i.ParentId == parentId select i;
    }
...

Поскольку HasIdAndParentId подклассов HasId, ограничение T: HasId выполнено, но компилятор не примет ограничение метода базового типа where для метода.

Есть идеи?

Ответы [ 3 ]

7 голосов
/ 13 августа 2010

В этом случае вы не переопределяете параметр типа в методе, поэтому вы не можете применять какие-либо новые ограничения. Вы должны быть в состоянии сделать это так:

public static IEnumerable<T2> GetManyByParentId<T2>(
    ref List<T2> items, Guid parentId) 
    where T2 : T, HasIdAndParentId { .. } 
1 голос
/ 13 августа 2010

Сделать сам метод GetManyByParentId универсальным и связать его универсальный параметр с T:

public static IEnumerable<R> GetManyByParentId<R>(
                                    ref List<R> items, Guid parentId) 
       where R : T, HasIdAndParentId 
0 голосов
/ 13 августа 2010

Пример кода Бена М не будет компилироваться, если только HasIdAndParentId не является типом интерфейса, а это не так, судя по названию.

Создание самого второго метода универсальным и привязка его к своему параметру типаиз T) предоставит вам желаемое ограничение.

public static IEnumerable<T1> GetManyByParentId<T1>(ref List<T1> items, Guid parentId) where T1 : HasIdAndParentId
{
    // the parentId is a property of HasIdAndParentId which subclasses HasId
    return from i in items where i.ParentId == parentId select i;
}
...