设为首页 加入收藏

TOP

7.8 引用与指针
2013-10-07 01:11:58 来源: 作者: 【 】 浏览:71
Tags:7.8 引用 指针

7.8  引用与指针

引用就是别名或同义词,它是同一块内存单元的不同名称。常用于替代传值方式,传递参数和返回值。具有指针的特点,可节省内存复制带来的开销。它的定义格式如下所示。

  1. type &ref=var; 

其中,type是类型名称,&是引用的说明符,ref是引用的名称,var是与引用同类型的变量名称。该式表示定义一个引用,该引用是var的别名,与var使用同样的内存单元。引用与指针的区别是:

(1)引用只是变量的别名,不开辟新的空间,与原变量使用同一块内存单元。指针则是一个新的变量,有自己的存储空间。

【示例7-19】 测试引用与变量是否使用同一块内存单元。

  1. int main(void)  
  2. {  
  3.     short x=100;  
  4.     short &ref=x;           //ref引用x  
  5.     short *pShort1=&x;      //pShort1指向x  
  6.     short *pShort2=&ref;    //pShort2指向ref  
  7.     cout<<pShort1<<endl;    //输出地址  
  8.     cout<<pShort2<<endl;    //输出地址  
  9.     cout<<*pShort1<<endl;   //输出内容  
  10.     cout<<*pShort2<<endl;   //输出内容  
  11.     return 0;  

分析:该示例中,ref引用了x,指针p1指向x,p2指向ref。输出结果如下所示。

  1. 0x22ff76  
  2. 0x22ff76  
  3. 100  
  4. 100 

从输出可以看出,变量x和其引用ref使用的内存单元是一样的。而且最后一条语句的输出也表明ref与x是一样的,p2和p1都指向x。

(2)引用必须在声明时就初始化,指针则可在任何时候初始化。例如示例7-19中,如果希望ref引用变量x,就必须在定义ref时用语句int &ref=x实现,而不能声明后,再用"ref=x"或其他形式实现。ref=x这种形式是在给引用赋值,但此时ref还没有引用任何变量,因此给其赋值是不合逻辑的。实际上,如果引用在定义时悬空,编译器将报错。

(3)引用不能为空,必须总是引用一个对象。而指针则可以为空,不指向任何地方。

【示例7-20】 给引用和指针赋空。

  1. int &ref=NULL;  
  2. *p=NULL; 

分析:其中,语句int &ref=NULL是不允许的。而int *p=NULL是允许的,表示p什么都不指。

(4)引用一旦被初始化,就不能再引用其他对象。而指针如果没有用const修饰,就可以重新指向不同的变量。例如示例7-19中,ref=x这样的语句只能在初始化时出现。因此,即使想改变引用的对象,也不会有机会去实现。

(5)如果引用被const修饰,则可以直接在初始化时赋常量。而指针除了0以外,什么时候都不能直接赋未经转换的常量。此时,引用的语义是创建一个临时的对象,并用该常量来初始化,然后对其引用,直到销毁引用才销毁该临时对象。而指针则意味着直接赋予一个地址,这是不允许的。

【示例7-21】 用常量给引用赋值。

  1. int main(void)  
  2. {  
  3.     /*用常量初始化引用*/ 
  4.     const int &ref2=0;  
  5.     const int &ref3=1234;  
  6.     int * p=0;              //初始化为空  
  7.     cout<<ref2<<endl;     
  8.     cout<<ref3<<endl;  
  9.     return 0;  

分析:该示例中,引用ref2直接赋值为0,这表示创建一个临时整型对象0,并用ref2引用它,其值为0。而p被赋为0,表示将p初始化为空。因此,可能的输出如下所示。

  1. 0  
  2. 1  
  3. 1234 

需要注意的是,如果没有用const修饰引用,则不能直接赋常量。

(6)引用声明时用&作为标识,使用时像变量一样直接使用。而指针则用*作为标识,使用时也要用*间接访问。

(7)sizeof操作施加到引用上时,测试的是被引用对象的宽度。而用于指针时,则是测试指针本身的宽度(同一种机型上,它总是定值)。

【示例7-22】 测试了用型变量和指针型变量在sizeof运算下的不同。

  1. int main(void)  
  2. {  
  3.     short sVal=100;  
  4.     short &ref1=sVal;               //引用  
  5.     short *pShort=&sVal;            //指针  
  6.     char cVal='a';  
  7.     char &ref2=cVal;  
  8.     char *pChar=&cVal;  
  9.  
  10.     cout<<sizeof(sVal)<<endl;         
  11.     cout<<sizeof(ref1)<<endl;       //计算被引用对象的宽度  
  12.     cout<<sizeof(pShort)<<endl;     //计算指针本身的宽度  
  13.     cout<<sizeof(cVal)<<endl;  
  14.     cout<<sizeof(ref2)<<endl;  
  15.     cout<<sizeof(pChar)<<endl;  
  16.     return 0;  

分析:该示例分别定义了两种类型的变量、引用和指针,并分别输出其所占的字节数。其输出如下所示。

  1. 2  
  2. 2  
  3. 4  
  4. 1  
  5. 1  

分析:从输出中可以看出,两个引用变量中与其被引用对象占据相同的字节数。这是因为两者实际上就是使用同一内存单元。两个指针则与被指对象无关,总是4。这是因为32位机型上,指针的占4字节存储单元。

引用与指针的共同点:

引用的本质也是指针,但是编译器在编译阶段进行了转换。

指针与引用都是间接引用其他对象。指针是通过地址间接访问指向的对象,引用是用别名去直接访问被引用对象。

技巧:当不能决定是选择指针还是选择引用时,可以简单地参照下述两条原则:若指向没有命名的对象,或不恒指向同一个对象,则使用指针;若总是指向同一个对象,则使用引用。

【责任编辑:云霞 TEL:(010)68476606】

回书目   上一节   下一节

】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇7.7.2 *操作符 下一篇7.9.2 空指针

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容: