程序師世界是廣大編程愛好者互助、分享、學習的平台,程序師世界有你更精彩!
首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫知識
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
 程式師世界 >> 編程語言 >> C語言 >> 關於C語言 >> 指針與數組(一)

指針與數組(一)

編輯:關於C語言

變量在內存存放是有地址的,數組在內存存放也同樣具有地址。對數組來說,數組名就是數組在內存安放的首地址。指針變量是用於存放變量的地址,可以指向變量,當然也可存放數組的首址或數組元素的地址,這就是說,指針變量可以指向數組或數組元素,對數組而言,數組和數組元素的引用,也同樣可以使用指針變量。下面就分別介紹指針與不同類型的數組。

6.4.1指針與一維數組

假設我們定義一個一維數組,該數組在內存會有系統分配的一個存儲空間,其數組的名字就是數組在內存的首地址。若再定義一個指針變量,並將數組的首址傳給指針變量,則該指針就指向了這個一維數組。我們說數組名是數組的首地址,也就是數組的指針。而定義的指針變量就是指向該數組的指針變量。對一維數組的引用,既可以用傳統的數組元素的下標法,也可使用指針的表示方法。

int a[10],*ptr;/*定義數組與指針變量*/

做賦值操作:

ptr=a;或ptr=&a[0];

則ptr就得到了數組的首址。其中,a是數組的首地址,&a[0]是數組元素a[0]的地址,由於a[0]的地址就是數組的首地址,所以,兩條賦值操作效果完全相同。指針變量ptr就是指向數組a的指針變量。

若ptr指向了一維數組,現在看一下C規定指針對數組的表示方法:

1)ptr+n與a+n表示數組元素a[n]的地址,即&a[n]。對整個a數組來說,共有10個元素,n的取值為0~9,則數組元素的地址就可以表示為ptr+0~ptr+9或a+0~a+9,與&a[0]~&a[9]保持一致。

2)知道了數組元素的地址表示方法,*(ptr+n)和*(a+n)就表示為數組的各元素即等效於a[n]。

3)指向數組的指針變量也可用數組的下標形式表示為ptr[n],其效果相當於*(ptr+n)。

[例6-5]/*以下標法輸入輸出數組各元素。

下面從鍵盤輸入10個數,以數組的不同引用形式輸出數組各元素的值。

#include <stdio.h>
main()
{
int n,a[10],*ptr=a;
for(n=0;n<=9;n++)
scanf("%d",&a[n]);
printf("1------output!\n");
for(n=0;n<=9;n++)
printf("%4d",a[n]);
printf("\n");
}

運行程序:

RUN
1234567890¿
1------output!
1234567890

[例6-6]采用指針變量表示的地址法輸入輸出數組各元素。

#include <stdio.h>
main()
{
int n,a[10],*ptr=a;/*定義時對指針變量初始化*/
for(n=0;n<=9;n++)
scanf("%d",ptr+n);
print f("2------output!\n");
for(n=0;n<=9;n++)
print f("%4d",*(ptr+n));
print f("\n");
}

運行程序:

RUN
1234567890¿
2------output!
1234567890

[例6-7]采用數組名表示的地址法輸入輸出數組各元素。

main()
{
int n,a[10],*ptr=a;
for(n=0;n<=9;n++)
scanf("%d",a+n);
print f("3------output!\n");
for(n=0;n<=9;n++)
print f("%4d",*(a+n));
print f("\n");
}

運行程序:

RUN
1234567890¿
3------output!
1234567890

[例6-8]用指針表示的下標法輸入輸出數組各元素。

main()
{
int n,a[10],*ptr=a;
for(n=0;n<=9;n++)
scanf("%d",&ptr[n]);
print f("4------output!\n");
for(n=0;n<=9;n++)
print f("%4d",ptr[n]);
print f("\n");
}

運行程序:

RUN
1234567890
4----output!
1234567890

[例6-9]利用指針法輸入輸出數組各元素。

main()
{
int n,a[10],*ptr=a;
for(n=0;n<=9;n++)
scanf("%d",ptr++);
print f("5------output!\n");
ptr=a;/*指針變量重新指向數組首址*/
for(n=0;n<=9;n++)
print f("%4d",*ptr++);
print f("\n");
}

運行程序:

RUN
1234567890¿
5-----output!
1234567890

在程序中要注意*ptr++所表示的含義。*ptr表示指針所指向的變量;ptr++表示指針所指向的變量地址加1個變量所占字節數,具體地說,若指向整型變量,則指針值加2,若指向實型,則加4,依此類推。而print f(“%4d”,*ptr++)中,*ptr++所起作用為先輸出指針指向的變量的值,然後指針變量加1。循環結束後,指針變量指向如圖6-6所示:

指針變量的值在循環結束後,指向數組的尾部的後面。假設元素a[9]的地址為1000,整型占2字節,則ptr的值就為1002。請思考下面的程序段:

main()
{
int n,a[10],*ptr=a;
for(n=0;n<=9;n++)
scanf("%d",ptr++);
print f("4------output!\n");
for(n=0;n<=9;n++)
print f("%4d",*ptr++);
print f("\n");
}

程序與例6-9相比,只少了賦值語句ptr=a;程序的運行結果還相同嗎?

6.4.2 指針與二維數組

定義一個二維數組:

int a[3][4];

表示二維數組有三行四列共12個元素,在內存中按行存放,存放形式為圖6-7:

其中a是二維數組的首地址,&a[0][0]既可以看作數組0行0列的首地址,同樣還可以看作是二維數組的首地址,a[0]是第0行的首地址,當然也是數組的首地址。同理a[n]就是第n行的首址;&a[n][m]就是數組元素a[n][m]的地址。

既然二維數組每行的首地址都可以用a[n]來表示,我們就可以把二維數組看成是由n行一維數組構成,將每行的首地址傳遞給指針變量,行中的其余元素均可以由指針來表示。下面的圖6-8給出了指針與二維數組的關系:

我們定義的二維數組其元素類型為整型,每個元素在內存占兩個字節,若假定二維數組從1000單元開始存放,則以按行存放的原則,數組元素在內存的存放地址為1000~1022。

用地址法來表示數組各元素的地址。對元素a[1][2],&a[1][2]是其地址,a[1]+2也是其地址。分析a[1]+1與a[1]+2的地址關系,它們地址的差並非整數1,而是一個數組元素的所占位置2,原因是每個數組元素占兩個字節。

對0行首地址與1行首地址a與a+1來說,地址的差同樣也並非整數1,是一行,四個元素占的字節數8。

由於數組元素在內存的連續存放。給指向整型變量的指針傳遞數組的首地址,則該指針指向二維數組。

int *ptr,a[3][4];

若賦值:ptr=a;則用ptr++就能訪問數組的各元素。

[例6-10]用地址法輸入輸出二維數組各元素。

#include<stdio.h>
main()
{
int a[3][4];
int i,j;
for(i=0;i<3;i++)
for(j=0;j<4;j++)
scanf("%d",a[i]+j);/*地址法*/
for(i=0;i<3;i++)
{
for(j=0;j<4;j++)
printf("%4d",*(a[i]+j));/**(a[i]+是j地)址法所表示的數組元素*/
printf("\n");
}
}

運行程序:

RUN
1 2 3 4 5 6 7 8 9 10 11 12
1 2 3 4
5 6 7 8
9 10 11 12

  1. 上一頁:
  2. 下一頁:
Copyright © 程式師世界 All Rights Reserved