您的位置:首页 > 编程语言 > C#

C# ref和out关键

2012-02-10 16:57 155 查看
今天在看一段C#代码的时候,发现对ref和out两个关键不了解,所以就查阅了C#语言相关的教程,深入的学习了一下。

ref关键字的作用是使参数按引用类型传递,这样控制权传递给调用方法时,在方法中对参数所做的任何更改都将反映在该变量中。

这里提到了引用类型,其实在C#中共有两种类型,一种是值类型(结构体、数值类型、bool型、枚举、可空类型),另一种是引用类型(自定义类、接口、委托、数组、字符串类型、object)。值类型和引用类型的区别在于以下几点:

1、值类型直接存储其值,变量本身就包含了实例数据,而引用类型保存的只是实例数据的内存引用。因此,一个值类型变量就永远不会影响到其他的值类型变量,而两个引用类型变量则很有可能指向同一地址,从而发生相互影响。

2、从内存分配上来看,值类型通常分配在线程的堆栈上,作用域结束时,所占空间自行释放,效率高,无需进行地址转换,而引用类型通常分配在托管堆上,由GC来控制其回收,需要进行地址转换,效率降低,这也正是c#需要定义两种数据类型的原因之一。

3、值类型均隐式派生自System.ValueType,而System.ValueType又直接派生于 System.Object,每种值类型均有一个隐式的默认构造函数来初始化该类型的默认值,注意所有的值类型都是密封(sealed)的,所以无法派生 出新的值类型。而且System.ValueType本身是一个类类型,而不是值类型,因为它重写了object的Equals()方法,所以对值类型将 按照实例的值来比较,而不是比较引用地址。

4、C# 的统一类型系统,使得值类型可以转化为对象来处理,这就是常说的装箱和拆箱。由于装拆箱需要装建全新对象或做强制类型转换,这些操作所需时间和运算要远远大于赋值操作,因此不提倡使用它,同时也要尽量避免隐式装拆箱的发生。

注:栈是操作系统分配的一个连续的内存区域,用于快速访问数据。因为值类型的容量是已知的,因此它可存储在栈上。而托管堆是CLR在应用程序启动时为应用程序预留的一块连续内存区,是用于动态内存分配的内存区,引用类型的容量只有到运行时才能确定,所有用堆来存储引用类型。理解了C#中值类型与引用类型的区别再来看ref关键字就会非常简单了。下面通过一个小例子来说明ref关键字的作用。

下面这段代码的功能是实现两个整数按由小到大的顺序进行排序。

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

namespace ref1
{
class Program
{

/// <summary>
/// 从小到大进行排序
/// </summary>
/// <param name="a"></param>
/// <param name="b"></param>
public static void sawp(int a, int b)
{
int c = 0;
if (a > b)
{
c = a;
a = b;
b = c;
}
Console.WriteLine("a的值为:{0},b的值为:{1}", a, b);
}

static void Main(string[] args)
{
int x = 6;
int y = 4;
sawp(x, y);
Console.WriteLine("x的值为:{0},y的值为:{1}", x, y);
Console.ReadLine();
}
}
}运行结果如下:

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

namespace ref1
{
class Program
{

/// <summary>
/// 返回数组的最大值及最大值的索引值
/// </summary>
/// <param name="m_Array">数组</param>
/// <param name="m_Index">最大值的索引值</param>
/// <returns>数组中的最大值</returns>
static int MaxIndex(int[] m_Array, ref int m_Index)
{
m_Index = 0;
int m_Max = m_Array[0];
for (int i = 0; i < m_Array.Length; i++)
{
if (m_Array[i] > m_Max)
{
m_Max = m_Array[i];
m_Index = i;
}
}
return m_Max;
}
static void Main(string[] args)
{
int[] Array = new int[5] { 12, 22, 55, 44, 11 };
int maxIndex=0;//使用ref关键字,此处需要初始化
Console.WriteLine("数组中最大的值是:{0}", MaxIndex(Array, ref maxIndex));
Console.WriteLine("最大数的索引号是:{0}", maxIndex + 1);
Console.ReadLine();
}
}
} 运行结果如下:

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: