3、泛型的使用:
  (1)泛型方法的使用:这也是博主使用多的用法之一,像这种泛型方法一般是一些static的通用方法,例如原来项目中用到的一个将DataGridViewRow对象转换成对应的实体Model的方法如下:
public static T ToObject<T>(DataGridViewRow item) where T:class
{
var model = item.DataBoundItem as T;
if (model != null)
return model;
var dr = item.DataBoundItem as System.Data.DataRowView;
model = (T)typeof(T).GetConstructor(new System.Type[] { }).Invoke(new object[] { });
//反射得到泛型类的实体
PropertyInfo[] pro = typeof(T).GetProperties(BindingFlags.Instance | BindingFlags.Public);
Type type = model.GetType();
foreach (PropertyInfo propertyInfo in pro)
{
if (Convert.IsDBNull(dr[propertyInfo.Name]))
{
continue;
}
if (!string.IsNullOrEmpty(Convert.ToString(dr[propertyInfo.Name])))
{
var propertytype = propertyInfo.PropertyType;
if (propertytype == typeof(System.Nullable<DateTime>) || propertytype == typeof(DateTime))
{
type.GetProperty(propertyInfo.Name).SetValue(model, Convert.ToDateTime(dr[propertyInfo.Name]), null);
}
else if (propertytype == typeof(System.Nullable<decimal>) || propertytype == typeof(decimal))
{
type.GetProperty(propertyInfo.Name).SetValue(model, Convert.ToDecimal(dr[propertyInfo.Name]), null);
}
else if (propertytype == typeof(System.Nullable<int>) || propertytype == typeof(int))
{
type.GetProperty(propertyInfo.Name).SetValue(model, Convert.ToInt32(dr[propertyInfo.Name]), null);
}
else if (propertytype == typeof(System.Nullable<double>) || propertytype == typeof(double))
{
type.GetProperty(propertyInfo.Name).SetValue(model, Convert.ToDouble(dr[propertyInfo.Name]), null);
}
else
{
type.GetProperty(propertyInfo.Name).SetValue(model, dr[propertyInfo.Name], null);
}
}
}
return model;
}
  使用泛型方法的注意事项:
  泛型方法的重载:public void Fun1<T>(T a);和public void Fun1<U>(U a);是无法重载的,这其实很好理解,因为T和U其实都是泛型的一个代表符号而已;
  泛型方法的重写:下面的方法重写FuncA的重写是正确的,FuncB的重写不正确,因为约束被默认继承,不用再写。
  abstract class BaseClass
  {
  public abstract T FuncA<T,U>(T t,U u) where U:T;
  public abstract T FuncB<T>(T t) where T:IComparable;
  }
  class ClassA:BaseClass
  {
  public override X FuncA<X,Y>(X x,Y y){...}
  public override T FuncB<T>(T t) where T:IComparable{...}
  }
  (2)泛型类的使用:
  public class Class_Base<DTO, T>
  {}
  使用这个类的时候必须要指定两个泛型类。
  (3)泛型接口以及泛型继承的使用:
  泛型接口的类型参数要么已实例化,要么来源于实现类声明的类型参数
  public interface Interface_Base<T>
  {}
  public class Class_Base<DTO, T> : Interface_Base<DTO>
  {}
  DTO来源于实现类Class_Base
  (4)泛型委托的使用:其实这种用法博主真的用得很少,只是原来见到过大牛们类似的代码。
  定义泛型委托:
  public delegate void MyDelegate<T>(T obj);
  泛型委托的使用:
  public delegate void MyDelegate<T>(T obj);
  static void Main(string[] args)
  {
  var method = new MyDelegate<int>(printInt);
  method(1);
  Console.ReadKey();
  }
  static void printInt(int i)
  {
  Console.WriteLine(i);
  }
  (5)泛型约束:用来约束泛型类型有那些特性。常见的泛型约束也那么几类:
  泛型约束的格式
  public class Imps_Base<DTO, T> : Ifs_Base<DTO>
  where T : BaseEntity
  where DTO : class
  {
  }