C#泛型与非泛型性能比较 类型安全的实例代码

发布时间:2019-08-15编辑:脚本学堂
本文详细介绍下,C#中泛型与非泛型在性能方面的比较,以及c#泛型类型安全的代码,帮助大家深入学习C#泛型相关内容。有需要的朋友,参考下吧。

例1,C#泛型与非泛型性能比较
 

复制代码 代码示例:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections;
namespace ConsoleApplication
{
class Program
{
static int length = 1000 * 1000;
static void Main(string[] args)
{
int iteration=10;//方法执行次数
CodeTimer.Time("值类型处理-泛型方法", iteration, Test1);
CodeTimer.Time("值类型处理-非泛型方法", iteration, Test2);
//CodeTimer.Time("引用类型处理-泛型方法", iteration, Test3);
//CodeTimer.Time("引用类型处理-非泛型方法", iteration, Test4);
Console.ReadKey();
}
/// <summary>
/// 值类型泛型方法
/// </summary>
static void Test1()
{
List<int> l = new List<int>();
for (int i = 0; i < length; i++)
{
l.Add(i);
int a = l[i];
}
l = null;
}
/// <summary>
/// 值类型非泛型方法
/// </summary>
static void Test2()
{
ArrayList a = new ArrayList();
for (int i = 0; i < length; i++)
{
a.Add(i);
int s = (int)a[i];
}
a = null;
}
/// <summary>
/// 引用类型泛型方法
/// </summary>
static void Test3()
{
List<string> l = new List<string>();
for (int i = 0; i < length; i++)
{
l.Add("l");
string s = l[i];
}
}
/// <summary>
/// 引用类型的非泛型方法
/// </summary>
static void Test4()
{
ArrayList a = new ArrayList();
for(int i=0;i<length;i++)
{
a.Add("a");
string s = (string)a[i];
}
a = null;
}
}
}

值类型的泛型与非泛型的性能比较,方法执行10次,由此可见
c#泛型

使用泛型要比非泛型的效率高很多。
c#泛型

例2,c#泛型类型安全与性能提高的实例
 

复制代码 代码示例:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Collections;

namespace 泛型
{
    class Program
    {
        static void Main(string[] args)
        {
 // 泛型解决的问题:

 //一 避免拆箱与装箱
 //例: 在写一个方法时如果有这样的需求,传一个参数,这个参数可以是int或者string,或者其他的自定义的对象,或者结构,这时有两种做法,1分别写2个方法做重载,2用object做参数。。

 //1分别写2个方法做重载,增加了代码量,而且方法内好多代码是相同的,不推荐
 //2用object做参数。。 这样必定在方法体内有大量的装箱拆箱,类型转换,影响性能,不推荐

 //例:非泛型ArrayList
 ArrayList arr = new ArrayList();
 arr.Add(100);
 //public virtual int Add(object value); 我们看add方法的定义,是以object value做参数的
 //所以在Add传入值类型(100)时,必然会产生隐式装箱
 //然后我们在读取值时:必须这样写
 int value = (int)arr[0]; //在此处,为了读取出我们的值类型数据,又出现了拆箱操作。
 Console.WriteLine( value );
 //以上操作频繁拆箱装箱,不推荐 !

 //下面演示一下泛型集合类的操作
 List<int> list = new List<int>();
 list.Add(100);
 int value2 = list[0];
 Console.WriteLine( value2 );
 //以上操作中,泛型定义为int,是在JIT编译器动态生成类中使用,不会产生装箱与拆箱操作。

 //二,类型安全
 //如果没有泛型,我们之前的ArrayList中是用object做参数,那么就是说,可以添加int也可以是string
 ArrayList arr3 = new ArrayList();
 arr3.Add(100);
 arr3.Add( "100");
 //以上代码是不会在编译时报错的
 //然后我们跌代输出
 foreach (int i in arr3)
 {
     Console.WriteLine(i);
 }
 //运行时出错了,呵呵,到底是按int处理,还是string谁知道?
 //虽然我们可以手动避免这种问题,我add时注意不就行了吗?
 //但这样是类型不安全的,泛型做了一种强制安全

 List<int> list2 = new List<int>();
 list2.Add(100);
 //list2.Add("100"); //编译时报错

 Console.ReadLine();
        }
    }
}

对c#拆装箱的性能分析(泛型)

c#中,数据类型主要分为2种,分别为值类型和引用类型。把值类型转换为引用类型称为装箱,把引用类型转换为值类型称为拆箱。在c#中,值类型是在堆栈上分配内存的,而引用类型是在堆上分配内存的。装箱的时候,CLR会为堆上的对象创建一个临时的引用类型“box”。