我愛學習網-上傳
當前位置: 主頁 > 文庫 > C++ >

c/c++中的指針的應用及注意問題

時間:2018-11-24 21:41來源:我愛學習網 作者:布丁點兒 點擊:

  指針是c/c++學習一個比較讓人頭痛的問題,在程序設計過程中,指針也往往是產生隱含bug的原因。下面就來

  談談指針的應用以及需要注意的一些問題,里面也許就有你平時沒有注意到的問題,希望能幫

  助各位讀者理解好指針。

  一、我們先來回憶一下指針的概念吧,方便下面的介紹

  指針是存放地址值的變量或者常量。例如:int a=1;&a就表示指針常量(“&”表示

  取地址運算符,也即引用)。int *b,b表示的是指針變量(注意,是b表示指針變量而

  不是*b),*表示要說明的是指針變量。大家注意int *b[2]和int(*b)[2]是不同的,

  int *b表示一個指針數組,而int (*b)[2]表示含有兩個元素的int指針,這里要注意

  運算優先級問題,有助于理解指針問題。

  在這里大概介紹基本概念就夠了,至于具體使用方法,如賦值等,很多書都有介紹

  ,我就不多說了。

  二、應用以及注意的問題

  1、 理解指針的關鍵所在——對指針類型和指針所指向的類型的理解

  ①、 指針類型:可以把指針名字去掉,剩下的就是這個指針

  例如:int *a;//指針類型為int *

  int **a;//指針類型為int **

  int *(*a)[8];//指針類型為 int *(*)[8]

  ②、 指針所指向的類型:是指編譯器將把那一片內存所看待成的類型。這里只要把

  指針聲明語句中的指針名字和名字右邊的“*”號去掉就可以了,剩下的就是指針所指向

  的類型。

  我之所以把他們放在第一位,是因為弄清楚他們是學c/c++指針的重點,正確理解他

  們才能使你打好c/c++的編程基礎。

  2、 指針的應用——傳遞參數。

  其實它可以相當于隱式的返回值,這就比return的方法更加靈活了,可以返回更多

  的值,看看下面的例子自然就明白了:

  #include "iostream.h"

  void example(int *a1,int &b1,int c1)

  {

  *a1*=3;

  ++b1;

  ++c1;

  }

  void main()

  {

  int *a;

  int b,c;

  *a=6;

  b=7;c=10;

  example(a,b,c);

  cout 《"*a="《*a<

  cout 《"b="<

  cout 《"c="<

  }

  

  輸出:*a=18

  b=8

  c=10

  注意到沒有,*a和b的值都改變了,而c沒有變。這是由于a1是指向*a(=6)的指針

  ,也即與a是指向同一個地址,所以當a1指向的值改變了,*a的值也就改變了。在函數中

  的參數使用了引用(int &b1),b1是b的別名,也可以把它當作特殊的指針來理解,所

  以b的值會改變。函數中的參數int c1只是在函數中起作用,當函數結束時候便消失了,

  所以在main()中不起作用。

  3、 關于全局變量和局部變量的一個問題

  先不廢話了,先看看程序:

  #include “iostream.h”

  int a=5;

  int *example1(int b)

  {

  a+=b;

  return &a;

  }

  int *example2(int b)

  {

  int c=5;

  b+=c;

  return &b;

  }

  void main()

  {

  int *a1=example1(10);

  int *b1=example2(10);

  cout 《”a1=”《*a1<

  cout 《”b1=”《*b1<

  }

  輸出結果:

  a1=15

  b1=4135

  *b1怎么會是4135,而不是15呢?是程序的問題?沒錯吧?

  由于a是全局變量,存放在全局變量的內存區,它一直是存在的;而局部變量則是存

  在于函數的棧區,當函數example2()調用結束后便消失,是b指向了一個不確定的區域

  ,產生指針懸掛。

  下面是對example1()和example2()的反匯編(用TC++ 3.0編譯):

  

  example1():

  push bp;入棧

  mov bp,sp

  mov ax,[bp+04];傳遞參數

  add [00AA],ax;相加

  mov ax,00AA ;返回了結果所在的地址

  pop bp;恢復棧,出棧

  ret;退出函數

  example2():

  push bp;入棧

  mov bp,sp

  sub sp,02

  mov word ptr [bp-02],0005

  mov ax,[bp-02];傳遞參數

  add [bp+04],ax;相加

  lea ax,[bp+04];問題就出在這里

  mov sp,bp

  pop bp;恢復棧,出棧

  ret;退出函數

  對比之后看出來了吧?ax應該是存儲的是結果的地址。而在example2()中,返回

  的卻是[bp+04]的內容,因此指針指向了一個不確定的地方,由此產生的指針懸掛。exa

  mple1()中,ax返回了正確的結果的地址。

  4、 內存問題:使用指針注意內存的分配和邊界。

  使用指針過程中應該給變量一個適當的空間,以免產生不可見的錯誤。

  請看以下代碼:

  #include “iostream.h”

  void main()

  {

  char *a1;

  char *a2;

  cin 》a1;

  cin 》a2;

  cout 《”a1=”<

  cout 《”a2=”<

  }

  

------分隔線----------------------------
    ?分享到??
看看啦
主站蜘蛛池模板: 国产微拍精品一区二区| 97久久精品无码一区二区天美| 狠狠色婷婷久久一区二区| 日韩熟女精品一区二区三区| 国产一区在线电影| 国产一区二区三区高清视频 | 亚洲视频在线一区| 91精品一区二区三区在线观看| 中文字幕日韩一区二区三区不卡| 最新欧美精品一区二区三区| 国模视频一区二区| 久久精品国产一区二区三区不卡| 亚洲电影一区二区| 国产天堂在线一区二区三区| 国产日韩一区二区三免费高清| 麻豆高清免费国产一区| 日本精品视频一区二区三区 | 亚洲一区二区中文| 成人丝袜激情一区二区| 精品视频一区二区三区四区五区| 久久一区二区精品| av一区二区三区人妻少妇| 精品一区二区三区色花堂| AA区一区二区三无码精片| 国产高清精品一区| 国产精品视频分类一区| 亚洲国产成人精品久久久国产成人一区二区三区综 | 亚洲av乱码一区二区三区| 狠狠爱无码一区二区三区| 无码人妻少妇色欲AV一区二区| 亚洲国产欧美日韩精品一区二区三区| 国产精品自在拍一区二区不卡| 精品人妻一区二区三区浪潮在线| 国产婷婷一区二区三区| 免费无码一区二区三区蜜桃大| 中文字幕在线观看一区二区| 国产99视频精品一区| 中文字幕一区二区免费| 日本一区视频在线播放| 精品无码日韩一区二区三区不卡| 亚洲一区二区三区在线视频|