java泛型:Visual C#泛型学习的泛型介绍

  什么是泛型

  种类型占位符或称的为类型参数我们知道在个思路方法中个变量值可以作为参数但其实这个变量类型本身也可以作为参数泛型允许我们在时候再指定这个类型参数是什么在.net中泛型能够给我们带来两个明显好处是——类型安全和减少装箱、拆箱

  类型安全和装箱、拆箱

  作为种类型参数泛型很容易给我们带来类型安全而在以前在.net1.1中我们要实现类型安全可以这样做 :

  //假设你有个人员集合
public Person{
 private _name;
 public Name
 { get { _name; }
  { _name = value;}}
}
//假设你有个人员集合
public PersonCollection : IList
{
 ...
 private ArrayList _Persons = ArrayList;
 public Person this[ index]
 { get { (Person)_Persons[index]; } }
 public Add(Person item)
 { _Persons.Add(item);
   _Persons.Count - 1;}
 public void Remove(Person item)
 { _Persons.Remove(item); }
 object IList.this[ index]
 { get { _Persons[index]; }
  { _Persons[index] = (Person)value; }}
  IList.Add(object item)
 { Add((Person)item); }
 void IList.Remove(object item)
 { Remove((Person)item); }
  ...
}


  上述代码主要采用了显性接口成员(explicit erface member implementation)技术能够实现类型安全但问题是:

  ·产生重复代码假设你还有个Dog类集合其功能相同但为了类型安全你必须要Copy份代码这样便使重复代码增加当面对变化时候更难维护

  public DogCollection : IList
{
 ...
 private ArrayList _Dogs = ArrayList;
 public Dog this[ index]
 { get { (Dog)_Dogs[index]; } }
 public Add(Dog item)
 { _Dogs.Add(item);
   _Dogs.Count - 1;}
 public void Remove(Dog item)
 { _Dogs.Remove(item); }
 object IList.this[ index]
 { get { _Dogs[index]; }
  { _Dogs[index] = (Dog)value; }}
  IList.Add(object item)
 { Add((Dog)item); }
 void IList.Remove(object item)
 { Remove((Dog)item); }
  ...
}


  如果在泛型中要实现类型安全你不需要拷贝任何代码你仅仅需要这样做:

  List<Person> persons = List<Person>;
persons.Add( Person);
Person person = persons[0];
List<Dog> dogs = List<Dog>;
dogs.Add( Dog);
Dog dog = dogs[0];


  ·对于值类型对象还是需要额外装箱、拆箱其实对于传统集合来说只要其中包含内容涉及到值类型就不可避免需要装箱、拆箱请看下面例子

  public IntCollection : IList
{
 ...
 private ArrayList _Ints = ArrayList;
 public this[ index]
 { get { ()_Ints[index]; } }
 public Add( item)
 { _Ints.Add(item);
   _Ints.Count - 1;}
 public void Remove( item)
 { _Ints.Remove(item); }
  object IList.this[ index]
  { get { _Ints[index]; }
   { _Ints[index] = ()value; }}
  IList.Add(object item)
 { Add(()item); }
 void IList.Remove(object item)
 { Remove(()item); }
  ...
 }
  void Main( args)
 { IntCollection s = IntCollection;
  s.Add(5); //装箱
   i = s[0]; //拆箱
 }


  少量装箱、拆箱对性能影响不大但是如果集合数据量非常大对性能还是有定影响泛型能够避免对值类型装箱、拆箱操作您可以通过分析编译后IL得到印证

   void Main
{
 List<> s = List<>;
 s.Add(5); //不用装箱
  i = s[0]; //不用拆箱
}


  泛型实现

  ·泛型思路方法

   void Swap<T>(ref T a, ref T b)
{ Console.WriteLine("You sent the Swap method a {0}",
 typeof(T));
 T temp;
 temp = a;
 a = b;
 b = temp;
}


  ·泛型类、结构

  public Po<T>
{
 private T _x;
 private T _y;
 public T X
 { get { _x; }
   { _x = value; }}
 public T Y
 { get { _y; }
   { _y = value; }}
 public override
 { .Format("[{0}, {1}]", _x, _y); }
}


  泛型Where

  泛型Where能够对类型参数作出限定有以下几种方式

  ·where T : struct 限制类型参数T必须继承自.ValueType

  ·where T : 限制类型参数T必须是引用类型也就是不能继承自.ValueType

  ·where T : 限制类型参数T必须有个缺省构造

  ·where T : NameOfClass 限制类型参数T必须继承自某个类或实现某个接口

  以上这些限定可以组合使用比如: public Po<T> where T : , IComparable,



  泛型机制

  ·机制:

  C#泛型代码在被编译为IL代码和无数据时采用特殊占位符来表示泛型类型并用专有IL指令支持泛型操作而真正泛型例子化工作以"on-demand"方式发生在JIT编译时

  ·编译机制:

  1. 第轮编译时编译器只为Stack<T>(栈算法)类型产生“泛型版”IL代码和元数据-----并不进行泛型类型例子化T在中间只充当占位符

  2. JIT编译时当JIT编译器第次遇到Stack<>时将用替换“泛型版”IL代码和元数据中T---进行泛型类型例子化CLR为所有类型参数为“引用类型”泛型类型产生同份代码;但如果类型参数为“值类型”对每个区别“值类型”CLR将为其产生份独立代码

  泛型些问题

  ·不支持操作符重载我只知道这么多了

  范型意义

  泛型意义何在?类型安全和减少装箱、拆箱并不是泛型意义而是泛型带来两个好处而已(或许在.net泛型中这是最明显好处了)泛型意义在于——把类型作为参数它实现了代码的间很好横向联系我们知道继承为代码提供了种从上往下纵向联系但泛型提供了方便横向联系(从某种程度上说它和AOP在思想上有相通的处)在PersonCollection例子中我们知道Add思路方法和Remove思路方法参数类型相同但我们明确无法告诉我们泛型提供了种机制知道这些道理虽然简单但这样机制或许能给我们带来些深远变化吧



Tags:  泛型编程与stl 泛型编程 .net泛型 java泛型

延伸阅读

最新评论

发表评论