C 指針

2018-07-04 14:29 更新

學(xué)習(xí)C - C指針

指針指向另一個(gè)值的內(nèi)存地址。

指針引用內(nèi)存中的位置,并獲取存儲(chǔ)在該位置的值稱為取消引用指針(來(lái)源:http://en.wikipedia.org/wiki/Pointer_(computer_programming))。

看下面的語(yǔ)句:

int number = 5;

分配一個(gè)內(nèi)存位置來(lái)存儲(chǔ)值為5的整數(shù),您可以使用名稱編號(hào)訪問(wèn)它。

值5存儲(chǔ)在該區(qū)域中。

計(jì)算機(jī)使用地址引用該區(qū)域。

假設(shè)地址是101。我們可以說(shuō)把價(jià)值5放入房間號(hào)101;

可以存儲(chǔ)地址的變量稱為指針。

下面的代碼定義了一個(gè)指針 number 其中包含另一個(gè)變量的地址,稱為number,它是一個(gè)包含值5的整數(shù)變量。

存儲(chǔ)在數(shù)字中的值是地址的第一個(gè)字節(jié)數(shù)。

字指針用于僅指一個(gè)地址。

int number = 5;
int *pnumber = &number;

指向char類型的值的指針指向占用1個(gè)字節(jié)的值,而指針到類型long的值通常指向占用4個(gè)字節(jié)的值的第一個(gè)字節(jié)。

每個(gè)指針將與特定的變量類型相關(guān)聯(lián),并且它只能用于指向該類型的變量。

因此,類型“指向int的指針"的指針只能指向int類型的變量,“指向浮點(diǎn)型"指針的指針只能指向float類型的變量,等等。

通常,給定類型的指針對(duì)于任何給定的類型名稱類型寫為*。

類型名稱void表示不存在任何類型,因此類型為void *的指針可以包含數(shù)據(jù)的地址任何類型的項(xiàng)目。

類型void *通常用作具有處理數(shù)據(jù)的函數(shù)的參數(shù)類型或返回值類型以類型無(wú)關(guān)的方式。

任何類型的指針可以作為類型void *的值傳遞,然后轉(zhuǎn)換為適當(dāng)類型使用時(shí)。

類型為int的變量的地址可以存儲(chǔ)在指針變量中例如,類型為void *。

當(dāng)你想訪問(wèn)存儲(chǔ)在void *指針中的地址的整數(shù)值時(shí),你必須首先將指針轉(zhuǎn)換為int *類型。



聲明指針

您可以使用以下語(yǔ)句聲明指向int類型的變量的指針:

int *pnumber;

具有名稱number的變量的類型為int *。

它可以存儲(chǔ)int類型的任何變量的地址。

注意,你也可以寫這樣的語(yǔ)句:

int* pnumber;

語(yǔ)句只是創(chuàng)建pnumber變量,但不會(huì)初始化它。

你可以初始化pnumber,使它不會(huì)通過(guò)重寫聲明來(lái)指向任何東西喜歡這個(gè):

int *pnumber = NULL;

NULL是在標(biāo)準(zhǔn)庫(kù)中定義的常量,并且對(duì)于指針等效于零。

NULL是一個(gè)值,不能指向內(nèi)存中的任何位置。

如果要使用變量的地址初始化變量pnumber你已經(jīng)聲明,你使用運(yùn)算符的地址&:

int number = 5;
int *pnumber = &number;

現(xiàn)在,number的初始值是變量的地址。

您可以在中聲明常規(guī)變量和指針同樣的語(yǔ)句,例如:

double value, *pVal, fnum;

此語(yǔ)句聲明兩個(gè)雙精度浮點(diǎn)變量,值和fnum,以及變量pVal類型“指針加倍。


例子

為了獲得變量的內(nèi)存地址,我們可以使用& 句法。


  #include <stdio.h> 

  int main(int argc, const char* argv[]) { 

    int n; 
    n = 10; 

    printf("value n: %d \n",n); 
    printf("address n: %x \n",&n); 

    return 0; 
  } 

上面的代碼生成以下結(jié)果。

注意

要聲明一個(gè)特定數(shù)據(jù)類型的指針,我們可以使用 * 語(yǔ)法。

此變量由我們的指針變量的內(nèi)存地址。


  #include <stdio.h> 

  int main(int argc, const char* argv[]) { 

    int n; 
    int* nPtr; 

    n = 10; 
    nPtr = &n; 

    printf("value n: %d \n",n); 
    printf("address n: %x \n",(unsigned int)&n); 

    printf("value nPtr: %x \n",(unsigned int)nPtr); 
    printf("address nPtr: %x \n",(unsigned int)&nPtr); 
    printf("value pointer nPtr: %d \n",*nPtr); 

    return 0; 
  } 

你可以看到nPtr的值是變量n的內(nèi)存地址。

如果n設(shè)置為10,那么指針nPtr的值,我們聲明為* nPtr是與變量n的值相同的值。

上面的代碼生成以下結(jié)果。

通過(guò)指針訪問(wèn)值

使用間接運(yùn)算符*來(lái)訪問(wèn)指針指向的變量的值。

這個(gè)操作符也是稱為解引用運(yùn)算符,因?yàn)槟褂盟鼇?lái)“解引用"指針。

假設(shè)您聲明以下變量:

int number = 15;
int *pointer = &number;
int result = 0;

指針變量包含變量號(hào)的地址,因此可以在表達(dá)式中使用此變量計(jì)算結(jié)果的新值,如下所示:

result = *pointer + 5;

表達(dá)式*指針將計(jì)算存儲(chǔ)在指針中包含的地址處的值。

這是值存儲(chǔ)在數(shù)字,15,因此結(jié)果將設(shè)置為15 + 5,這是20。

下面的代碼聲明一個(gè)變量和一個(gè)指針,然后輸出它們的地址和值。


    #include <stdio.h>

    int main(void)
    {
      int number = 0;                 // A variable of type int initialized to 0
      int *pnumber = NULL;            // A pointer that can point to type int

      number = 5;
      printf("number"s address: %p\n", &number);               // Output the address
      printf("number"s value: %d\n\n", number);                // Output the value

      pnumber = &number;              // Store the address of number in pnumber

      printf("pnumber"s address: %p\n", (void*)&pnumber);      // Output the address
      printf("pnumber"s size: %zd bytes\n", sizeof(pnumber));  // Output the size
      printf("pnumber"s value: %p\n", pnumber);                // Output the value (an address)
      printf("value pointed to: %d\n", *pnumber);              // Value at the address
      return 0;
    }

上面的代碼生成以下結(jié)果。

指針用法

因?yàn)槟梢酝ㄟ^(guò)指針pnumber訪問(wèn)數(shù)字的內(nèi)容,您可以在算術(shù)語(yǔ)句中使用取消引用的數(shù)值類型的指針。

例如:

*pnumber += 5;

此語(yǔ)句將當(dāng)前所有地址變量pnumber的值遞增5。

*表示正在訪問(wèn)名為pnumber的變量所指向的內(nèi)容。

變量pnumber可以存儲(chǔ)int類型的任何變量的地址。

這意味著您可以將pnumber指向的變量更改為:

int value = 9;
pnumber = &value;

假設(shè)您重復(fù)以前使用的相同語(yǔ)句:

*pnumber += 5;

語(yǔ)句將使用新的變量,值操作,因此值的新內(nèi)容將為14。

指針可以包含適當(dāng)類型的任何變量的地址,因此可以使用一個(gè)指針變量來(lái)更改值許多不同的變量,只要它們的“re"類型與指針類型兼容即可。

此示例使用指針修改存儲(chǔ)在一些其他變量中的值。


    #include <stdio.h>

    int main(void)
    {
      long num1 = 1L;
      long num2 = 1L;
      long *pnum = NULL;

      pnum = &num1;                                 // Get address of num1
      *pnum = 2L;                                   // Set num1 to 2
      ++num2;                                       // Increment num2
      num2 += *pnum;                                // Add num1 to num2

      printf("num1 = %ld  num2 = %ld  *pnum = %ld  *pnum + num2 = %ld\n",
                                          num1, num2, *pnum, *pnum + num2);
      return 0;
    }

上面的代碼生成以下結(jié)果。

例2

以下代碼顯示了如何在 scanf 函數(shù)中使用指針變量。

當(dāng)您使用scanf()輸入值時(shí),您已經(jīng)使用&運(yùn)算符來(lái)獲取要接收輸入的變量的地址。

當(dāng)你有一個(gè)指針時(shí),可以使用指針名稱作為參數(shù)。


    #include <stdio.h>
    int main(void)
    {
      int value = 0;
      int *pvalue = &value;                     // Set pointer to refer to value

      printf ("Input an integer: ");
      scanf(" %d", pvalue);                   // Read into value via the pointer

      printf("You entered %d.\n", value);       // Output the value entered
      return 0;
    }

上面的代碼生成以下結(jié)果。

以上內(nèi)容是否對(duì)您有幫助:
在線筆記
App下載
App下載

掃描二維碼

下載編程獅App

公眾號(hào)
微信公眾號(hào)

編程獅公眾號(hào)