Asa*_*sad 114 .net c# generics open-generics
我正在通过Asp.Net MVC课程并了解到,对于一种方法来确定控制器的动作,
我对某些泛型有所了解并在某种程度上使用它们,但是:
Meh*_*ari 189
C#语言将open类型定义为类型参数或使用未知类型参数定义的泛型类型:
所有类型都可以分为开放类型或封闭类型.一个开放式的,涉及类型参数的类型.进一步来说:
- 类型参数定义开放类型.
- 当且仅当其元素类型是开放类型时,数组类型才是开放类型.
- 甲构造类型是开放型,当且仅当其类型参数中的一个或多个是一个开放型.甲构造嵌套类型是开放型,当且仅当其类型参数或包含它的类型的类型参数中的一个或多个是开放类型.
一个封闭式是一种类型,是不是开放类型.
因此T,List<T>和Dictionary<string,T>,Dictionary<T,U>都是开放类型(T并且U是类型参数),List<int>而且Dictionary<string,int>是封闭类型.
有一个相关的概念:未绑定的泛型类型是具有未指定类型参数的泛型类型.未绑定的类型不能在除以外的表达式中使用typeof(),您无法实例化它或调用其方法.例如,List<>并且Dictionary<,>是未绑定的类型.
澄清开放类型和未绑定类型之间的细微区别:
class Program {
static void Main() { Test<int>(); }
static void Test<T>() {
Console.WriteLine(typeof(List<T>)); // Print out the type name
}
}
Run Code Online (Sandbox Code Playgroud)
如果您运行此代码段,它将打印出来
System.Collections.Generic.List`1[System.Int32]
Run Code Online (Sandbox Code Playgroud)
这是CLR的名称List<int>.在运行时很清楚类型参数是System.Int32.这使得List<T>一个结合开放式.
在运行时,您可以使用反射将类型参数绑定到未绑定泛型类型的未指定类型参数,Type.MakeGenericType方法如下:
Type unboundGenericList = typeof(List<>);
Type listOfInt = unboundGenericList.MakeGenericType(typeof(int));
if (listOfInt == typeof(List<int>))
Console.WriteLine("Constructed a List<int> type.");
Run Code Online (Sandbox Code Playgroud)
您可以检查类型是否是未绑定的泛型类型(泛型类型定义),您可以使用该Type.IsGenericTypeDefinition属性构造绑定类型:
Console.WriteLine(typeof(Dictionary<,>).IsGenericTypeDefinition); // True
Console.WriteLine(typeof(Dictionary<int,int>).IsGenericTypeDefinition); // False
Run Code Online (Sandbox Code Playgroud)
要在运行时从构造类型获取未绑定类型,可以使用该Type.GetGenericTypeDefinition方法.
Type listOfInt = typeof(List<int>);
Type list = listOfInt.GetGenericTypeDefinition(); // == typeof(List<>)
Run Code Online (Sandbox Code Playgroud)
请注意,对于泛型类型,您可以具有完全未绑定的类型定义或完全绑定的定义.您无法绑定某些类型参数并使其他参数保持未绑定状态.例如,你不能拥有Dictionary<int,>或Dictionary<,string>.
只是添加:
Dictionary<string, T>(或更确切地说Dictionary<string,>)仍然是开放式的.
例:
void Foo<T>(Dictionary<string,T> dic) { ... }
Run Code Online (Sandbox Code Playgroud)
"开放泛型类型"只是一种尚未指定其类型的泛型类型(例如CargoCrate<T>).一旦分配了具体类型(例如CargoCrate<Widget>),它就变为"关闭" .
例如,假设你有这样的事情:
public class Basket<T> {
T[] basketItems;
}
public class PicnicBlanket<T> {
Basket<T> picnicBasket; // Open type here. We don't know what T is.
}
// Closed type here: T is Food.
public class ParkPicnicBlanket : PicnicBlanket<Food> {
}
Run Code Online (Sandbox Code Playgroud)
这里picnicBasket的类型是开放的:尚未分配任何内容T.当您使用特定类型创建具体类型的PicnicBlanket时(例如,通过编写)PicnicBlanket<Food> p = new PicnicBlanket<Food>(),我们现在将其称为已关闭.
通用类型有三种.简而言之,在此(简化)声明中:
public class Dictionary<TKey, TValue> : IEnumerable<KeyValuePair<TKey, TValue>>
Run Code Online (Sandbox Code Playgroud)
Dictionary<TKey, TValue>是一种无界的泛型类型.
KeyValuePair<TKey, TValue>在这种情况下,是一个开放构造的通用类型.它有一些类型参数,但它们已在别处定义(在本例中为Dictionary).
Dictionary<string, int>将是一个封闭的构造泛型类型.
| 归档时间: |
|
| 查看次数: |
33012 次 |
| 最近记录: |