Ответ 1
OpenGenericWithOpenService<T>
не реализует только произвольное IGenericService<>
- он реализует IGenericService<T>
для того же T
как класс.
Лучший способ показать это - слегка изменить класс:
public class OpenGenericWithOpenService<T1, T2> : IGenericService<T1> {}
Теперь важно, что, когда вы спрашиваете, что для интерфейсов, которые он реализует, вы знаете, что можете преобразовать в IGenericService<T1>
, но (совпадение в сторону), а не IGenericService<T2>
или любую другую реализацию.
Другими словами, он не полностью открыт - он привязан к аргументу того же типа, что и у класса.
Я никогда не был очень хорош с терминологией дженериков, но надеюсь, вы понимаете, что я имею в виду. IGenericService<>
- тип, ожидающий ввода аргумента типа; в этом случае у вас есть аргумент типа - это просто другой параметр типа!
Здесь пройдет тест, который пройдет:
[TestMethod]
public void can_get_open_generic_interface_off_of_implementor()
{
Type[] typeParams = typeof(OpenGenericWithOpenService<>).GetGenericArguments();
Type constructed = typeof(IGenericService<>).MakeGenericType(typeParams);
typeof(OpenGenericWithOpenService<>).GetInterfaces().First()
.ShouldEqual(constructed);
}
Если вы измените класс для реализации (скажем) IGenericService<int>
вместо этого, он будет терпеть неудачу.