1 using System;
2 using System.Collections.Generic;
3 using System.IO;
4 using System.Linq;
5 using System.Text;
6
7 namespace ClrVarCSharp.C12Generic
8 {
9 class Program
10 {
11 public static void Main(string[] args)
12 {
13 //A.Test1();
14 //B.Test2();
15 //C.Test2();
16 //Test3();
17 //Test4();
18 //Test5();
19
20 }
21
22 //12.2.1 开放类型和封闭类型
23 public sealed class DictionaryStringKey<TValue> : Dictionary<string, TValue> { }
24 public static class A
25 {
26 public static void Test1()
27 {
28 object o = null;
29
30 Type t = typeof(Dictionary<,>);
31 o = CreateInstance(t); //创建开放类型实例失败
32 Console.WriteLine();
33
34 t = typeof(DictionaryStringKey<>); //开放类型
35 o = CreateInstance(t);
36 Console.WriteLine();
37
38 t = typeof(DictionaryStringKey<Guid>);
39 o = CreateInstance(t);
40 Console.WriteLine(o.GetType());
41
42 }
43
44 private static object CreateInstance(Type t)
45 {
46 object o = null;
47 try
48 {
49 o = Activator.CreateInstance(t);
50 Console.WriteLine("已创建 {0} 的实例。", t.ToString());
51 }
52 catch (ArgumentException e)
53 {
54 Console.WriteLine(e.Message);
55 }
56 return o;
57 }
58 }
59
60 //12.2.2 泛型类型和继承
61 //该链表只能接受一种类型
62 class B
63 {
64 sealed class Node<T>
65 {
66 public T m_data;
67 public Node<T> m_next;
68 public Node(T data) : this(data, null)
69 {
70
71 }
72 public Node(T data, Node<T> next)
73 {
74 m_data = data;
75 m_next = next;
76 }
77 public override string ToString()
78 {
79 return m_data.ToString() +
80 ((m_next != null) ? m_next.ToString() : string.Empty);
81 }
82 }
83 public static void Test2()
84 {
85 Node<char> head = new Node<char>('C');
86 head = new Node<char>('B', head);
87 head = new Node<char>('A', head);
88 Console.WriteLine(head.ToString());
89 }
90 }
91 //该链表可接受不同的类型
92 class C
93 {
94 class Node
95 {
96 protected Node m_next;
97 public Node(Node next)
98 {
99 m_next = next;
100 }
101 }
102 sealed class TypeNode<T> : Node
103 {
104 public T m_data;
105 public TypeNode(T data) : this(data, null)
106 {
107
108 }
109 public TypeNode(T data, Node next) : base(next)
110 {
111 m_data = data;
112 }
113 public override string ToString()
114 {
115 return m_data.ToString() +
116 ((m_next != null) ? m_next.ToString() : string.Empty);
117 }
118 }
119 public static void Test2()
120 {
121 Node head = new TypeNode<char>('.');
122 head = new TypeNode<DateTime>(DateTime.Now, head);
123 head = new TypeNode<string>("Today is ", head);
124 Console.WriteLine(head.ToString());
125 }
126 }
127
128 //12.2.3 泛型类型同一性
129 List<DateTime> dt1 = new List<DateTime>();
130 internal sealed class DateTimeList : List<DateTime> { /* 内部无需任何代码 */ } //DateTimeList与DateTime是两个不同的类型
131 //using DateTimeList = System.Collections.Generic.List<System.DateTime>; //简化代码又保证是同一类型
132 static void Test3()
133 {
134 DateTimeList dt2 = new DateTimeList(); //通过以上定义,简化了<>
135 bool sameType = (typeof(List<DateTime>) == typeof(DateTimeList));
136 Console.WriteLine(sameType);
137 }
138
139 //12.6 泛型方法
140 sealed class GenericType<T>
141 {
142 private T m_value;
143 public GenericType(T value) { m_value = value; }
144 public TOutput Converter<TOutput>()
145 {
146 TOutput result = (TOutput)Convert.ChangeType(m_value, typeof(TOutput));
147 return result;
148 }
149 }
150
151 private static void Swap<T>(ref T o1, ref T o2)
152 {
153 T temp = o1;
154 o1 = o2;
155 o2 = temp;
156 }
157
158 //12.8 可验证性和约束
159 public static T Min<T>(T o1, T o2) where T : IComparable<T>
160 {
161 if (o1.CompareTo(o2) < 0)
162 return o1;
163 return o2;
164 }
165
166 static void Test4()
167 {
168 object o1 = "X2009";
169 object o2 = "abc";
170 //object oMin = Min<object>(o1, o2); //编译错误
171 }
172
173 //泛型类型/方法重载
174 //只能定义基于参数数量的重载
175 sealed class AType { }
176 sealed class AType<T> { }
177 sealed class AType<T1, T2> { }
178 //不能定义仅基于约束的重载
179 //sealed class AType<T> where T : IComparable<T> { }
180 //不能定义基于名称的重载
181 //sealed class AType<T3, T4> { }
182
183 //12.8.1 主要约束,约束为非密封类的一个引用类型
184 sealed class PrimaryConstraintOfStream<T> where T : Stream
185 {
186 public void M(T stream)
187 {
188 stream.Close();
189 }
190 }
191 //12.8.2 次要约束,约束为接口类型
192
193 //用一个泛型来约束另一个泛型:指定参数是约束类型或其派生类型
194 static List<T2> ConvertIList<T1, T2>(IList<T1> list) where T1 : T2
195 {
196 List<T2> baseList = new List<T2>(list.Count);
197 for (int index = 0; index < list.Count; index++)
198 {
199 baseList.Add(list[index]);
200 }
201 return baseList;
202 }
203
204 static void Test5()
205 {
206 IList<string> ls = new List<string>();
207 ls.Add("A String");
208
209 //IList<string>转换为IList<object>
210 IList<object> lo = ConvertIList<string, object>(ls);
211
212 IList<IComparable> lc = ConvertIList<string, IComparable>(ls);
213
214 IList<IComparable<string>> lcs = ConvertIList<string, IComparable<string>>(ls);
215
216 IList<string> ls2 = ConvertIList<string, string>(ls);
217
218 //IList<Exception> le = ConvertIList<string, Exception>(ls);
219 }
220
221 //12.8.3 构造器约束
222 sealed class ConstructorConstraint<T> where T : new()
223 {
224 public static T Factory()
225 {
226 return new T();
227 }
228 }
229
230 //12.8.4 其他可验证性问题
231 //1). 泛型的类型转换
232 static void Test6<T>(T obj)
233 {
234 //编译错误
235 //int x = (int)obj;
236 //string s = (string)obj;
237 }
238
239 static void Test7<T>(T obj)
240 {
241 //可通过编译,但可能出现运行时异常
242 int x = (int)(object)obj;
243 string s = (string)(object)obj;
244 }
245
246 static void Test8<T>(T obj)
247 {
248 //无错误
249 string s = obj as string;
250 }
251
252 //2). 泛型初始化
253 static void Test9<T>()
254 {
255 //T temp = null;
256 T temp = default(T);
257 }
258
259 }
260 }