㈠ 存在的變數為什麼加下標
代表起始地址。
針經常與下標配合使用,形同數組。這才讓很多人把數組與指針混淆了。而指針變數加上下標,代表的意義就是指針中的值就是起始地址,下標則是從指針中存儲的地址作為起始地址開始偏移的。
㈡ 數組下標用變數
對於ANSI 標准C及C++,這都是標准沒有定義的,也就是說,最好認為不可以用變數代入數組個數
C99標准中加入了這個特性,但C99標准還未流行。
對於C++編譯器,gcc擴充了這個功能,但是它未被標准支持所以這樣的程序是不具備編譯可移植性的。早期的vc++6.0不支持此特性。
但是你若在c++中定義const int n = 5;
則可以int a[n];
因為c++中,const型變數是作為編譯時常量的。
但在ANSI C中卻不行,因為C中const型變數是作為只讀的變數出現的,所以不能用其定義數組個數
雖然在匯編的角度看,int a[n];這種語句即使n是變數,也是很好實現的,但c/c++出於多種考慮(例如n的不確定性以及樓上提到的一點原因)拒絕了它
要模擬動態數組,最好使用new,malloc類似函數動態分配內存,這樣的程序才是最安全的
-----------------------------------------------------------------
樓主,我看大師Steve Summit的書,他告訴我說去在意不同的編譯器之間的對標準的支持程度的不同是沒多大意義的。我們只需知道ANSI C/C++兩者的標準定義行為,對未定義行為及不確定行為不同的編譯器有不同的實現與擴展,也盡量不要去用,盡管某些編譯器出於好意擴展了某些行為
-------------------------------------------------------------
這里看到了對宏的討論。宏是預處理器管的范疇,而非編譯器的范疇
要想真正理解以上所有這些,請看大師的書:《C Programming FAQs》與《C++ Primer》,前者對應C,後者對應C++。
單在這里討論是理解不了的
㈢ C語言中每個變數或者元素都有下標,下標的作用是什麼謝謝
C語言中變數或者元素都有下標,是因為表示數組的某個元素,比如a[4],表示數組的第5個元素,數組元素下標是從0開始的。
㈣ 在C語言中,數組定義時的下標不能用變數表示(即使它已經被賦值),如int [n];為什麼能把變數的定義過程詳...
在編譯的時候,數組需要一個指定的大小。n必須是常數,而你說的賦值在編譯的時候編譯器並不知道n到底是多少,運行時候才知道,所以編譯不通過。
若要動態開辟內存,可用malloc,用完之後用free釋放即可。
㈤ 如何在C/C++中數組的下標使用變數
對於ANSI 標准C及C++,這都是標准沒有定義的,也就是說,最好認為不可以用變數代入數組個數
C99標准中加入了這個特性,但C99標准還未流行。
對於C++編譯器,gcc擴充了這個功能,但是它未被標准支持所以這樣的程序是不具備編譯可移植性的。早期的vc++6.0不支持此特性。
但是你若在c++中定義const int n = 5;
則可以int a[n];
因為c++中,const型變數是作為編譯時常量的。
但在ANSI C中卻不行,因為C中const型變數是作為只讀的變數出現的,所以不能用其定義數組個數
雖然在匯編的角度看,int a[n];這種語句即使n是變數,也是很好實現的,但c/c++出於多種考慮(例如n的不確定性以及樓上提到的一點原因)拒絕了它
要模擬動態數組,最好使用new,malloc類似函數動態分配內存,這樣的程序才是最安全的。
數組的引用下標可以是變數常量
㈥ 關於C語言編程 的下標是指什麼
在C語言中,下標用於數組的訪問(讀或寫)。
當定義一個數組時,形式為
TYPE array_name[NUM];
即定義一個元素類型為TYPE,共計NUM個元素的數組,名為array_name。
對於標准C語言(ANSI C), 數組長度NUM必須為常量,但是目前大多數編譯器均擴展到可以支持變數。
當訪問數組元素時,就需要使用下標,格式為
array_name[index]
其中[index]就是數組的下標,含義為數組array_name的第index元素。
在C語言中,index是從0開始計數的,所以對於NUM個元素的數組,合法下標范圍為0~NUM-1。
㈦ 如何使用一個變數表達出三維數據的每一個下標
《C++語言程序設計》課程輔導二(2.1)
------數組和字元串
一、數組的概念
在程序設計中存儲單個數據時,需要根據數據的類型定義相應的變數來保存。如存儲一個整數時需要定義一個整數變數來保存,存儲一個實數時需要定義一個單精度或雙精度變數來保存,存儲含有多個成分的一個記錄數據時,需要定義該類型的一個結構變數來保存。
若在程序設計中需要存儲同一數據類型的、彼此相關的多個數據時,如存儲數學上使用的一個數列或一個矩陣中的全部數據時,顯然採用定義簡單變數的方法是不行的,這就要求定義出能夠同時存儲多個值的變數,這種變數在程序設計中稱為數組。
在實際應用中,一組相關的數據之間可能存在著一維關系,也可能存在著二維關系,等等。一個數列中的數據若是一維關系,則它除第一個數據外,每個數據只有一個直接前驅;除最後一個數據外,每個數據只有一個直接後繼。假定一個數列為(38,42,25,60),則每個數的後一個數就是它的直接後繼,每一個數的前一個數就是它的直接前驅,如42的直接前驅為38,直接後繼為25。一個矩陣中的數據若二維關系,則它除第一行和第一列上的所有數據外,每個數據在行和列的方向上各有一個直接前驅;除最後一行和最後一列上的所有數據外,每個數據在行和列的方向上各有一個直接後繼。假定一個矩陣為:
2 6 9 12
8 4 7 3
5 1 6 8
則每一個元素均處於相應行和列的交點位置上,雖然有的元素值相同,但由於所處的位置不同,所以是不同的元素。
在程序設計中,用一維數組表示和存儲一維相關的數據,用二維數組表示和存儲二維相關的數據,用三維數組表示和存儲三維相關的數據,等等。假定一個數列為a1,a2,...,an,則需要用一個一維數組來存儲,假定仍用a作為數組名,則a中應至少包含有n個元素,每個元素用來存儲數列中一個相應的數據。若a中正好包含有n個元素,則這n個元素依次表示為a[0],a[1],...,a[n-1],用a[0]存儲數列中的第一個數據a1,用a[1]存儲數列中的第二個數據a2,依次類推。假定一個矩陣為:
a11 a12 ... a1n
a21 a22 ... a2n
...
am1 am2 ... amn
則需要用一個二維數組來存儲,假定二維數組名用b表示,則b中應至少包含mn個元素,也就是說,第一維尺寸至少為m,第二維尺寸至少為n,該數組b中的每個元素用來存儲矩陣中的一個相應的數據。
二、數組的定義
2.1 一維數組
1. 定義格式
一維數組同簡單變數一樣,也是通過變數定義語句定義的。其定義格式為:
<類型關鍵字> <數組名> [<常量表達式>] [={<初值表>}];
<類型關鍵字>為已存在的一種數據類型,<數組名>是用戶定義的一個標識符,用它來表示一個數組,<常量表達式>的值是一個整數,由它標明該數組的長度,即數組中所含元素的個數,每個元素具有<類型關鍵字>所指定的類型,<常量表達式>兩邊的中括弧是語法所要求的符號,不是標明其內容為可選而使用的符號,<初值表>是用逗號分開的一組表達式,每個表達式的值將被賦給數組中的相應元素。
當數組定義中包含有初始化選項時,其<常量表達式>可以被省略,此時所定義的數組的長度將是<初值表>中所含的表達式的個數。
一個數組被定義後,系統將在內存中為它分配一塊含有n個(n為數組長度)存儲單元的存儲空間,每個存儲單元包含的位元組數等於元素類型的長度。如對於一個含有10個int型元素的數組,它將對應10*4=40個位元組的存儲空間。
定義了一個數組,就相當於同時定義了它所含的每個元素。數組中的每個元素是通過下標運算符[]來指明和訪問的,具體格式為:「<數組名>[<下標>]」,這與數組的定義格式相同,但出現的位置是不同的,當出現在變數定義語句時則為數組定義,而當出現在表達式中時則為一個元素。
對於一個含有n個元素的數組,C++語言規定:它的下標依次為0,1,2,...,n-1,因此全部n個元素依次為a[0],a[1],a[2],...,a[n-1],其中假定a為數組名。
2. 格式舉例
(1) int a[20];
(2) double b[MS]; //假定MS為已定義的整型常量
(3) int c[5]={1,2,3,4,0};
(4) char d[]={'a','b','c','d'};
(5) int e[8]={1,4,7};
(6) char f[10]={'B','A','S','I','C'};
(7) bool g[2*N+1]; //假定N為已定義的整型常量
(8) float h1[5], h2[10];
(9) short x=1, y=2, z, w[4]={25+x, -10, x+2*y, 44};
(10) int p[];
第一條語句定義了一個元素為int型、數組名為a、包含20個元素的數組,所含元素依次為a[0],a[1],...,a[19],每個元素同一個int型簡單變數一樣,佔用4個位元組的存儲空間,用來存儲一個整數,整個數組佔用80個位元組的存儲空間,用來存儲20個整數。
第二條語句定義了一個元素類型為double、數組長度為MS的數組b,該數組佔用MS*8個位元組的存儲空間,能夠用來存儲MS個雙精度數,數組b中的元素依次為b[0],b[1],...,b[MS-1]。
第三條語句定義了一個整型數組c,即元素類型為整型的數組c,它的長度為5,所含元素依次為c[0],c[1],c[2],c[3]和c[4],並相應被初始化為1,2,3,4和0。
第四條語句定義了一個字元數組d,由於沒有顯式地給出它的長度,所以隱含為初值表中表達式的個數4,該數組的4個元素d[0],d[1],d[2]和d[3]依次被初始化為』a』,』b』,』c』,和』d』。注意若沒有給出數組的初始化選項,則表示數組長度的常量表達式不能省略。
第五條語句定義了一個含有8個元素的整型數組e,它的初始化數據項的個數為3,小於數組中元素的個數8,這是允許的,這種情況的初始化過程為:將利用初始化表對前面相應元素進行初始化,而對後面剩餘的元素則自動初始化為常數0。數組e中的8個元素被初始化後得到的結果為:e[0]=1, e[1]=4, e[2]=7, e[3]e[7]=0。
第六條語句定義了一個字元數組f,它包含有10個字元元素,其中前5個元素被初始化為初值表所給的相應值,後5個元素被初始化為字元』\0』,對應數值為0。
第七條語句定義了一個布爾型數組g,它的數組長度為2*N+1,每個元素沒有被初始化。
第八條語句定義了兩個單精度型一維數組h1和h2,它們的數組長度分別為5和10。在一條變數定義語句中,可以同時定義任意多個簡單變數和數組,每兩個相鄰定義項之間必須用逗號分開。
第九條語句定義了三個短整型簡單變數x,y和z,其中x和y被初始化為1和2,定義了一個短整型數組w,它包含有四個元素,其中w[0]被初始化為25+x的值,即26,w[1]被初始化為-10,w[2]被初始化為x+2*y的值,即5,w[3]被初始化為44。
第十條語句是錯誤的數組定義,因為它既省略了數組長度選項,又省略了初始化選項,使系統無法確定該數組的大小,從而無法分配給它確定的存儲空間。
3. 數組元素的訪問
通過變數定義語句定義了一個數組後,用戶便可以隨時使用其中的任何元素。數組元素的使用是通過下標運算符[]指明和訪問的,其中運算符左邊為數組名,中間為下標。一個數組元素又稱為下標變數,所使用的下標可以為常量,也可以為變數或表達式,但其值必須是整數,否則將產生編譯錯誤。
假定a[n]為一個已定義的數組,則下面都是訪問該數組的下標變數的合法格式:
(1) a[5] //下標為一個常數
(2) a[i] //下標為一個變數
(3) a[j++] //下標為後增1表達式
(4) a[2*x+1] //下標為一般表達式
假定在上述每個變數的下標表達式中,所使用的變數i,j和x的值分別為2,3和4,則a[i]對應的數組元素為a[2],a[j++]對應的數組元素為a[3],同時j的值被修改為4,a[2*x+1]對應的數組元素為a[9]。
使用一個下標變數同使用一個簡單變數一樣,可以對它賦值,也可以取出它的值。如:
(1) int a[5]={0,1,2,3,8}; //定義數組a並進行初始化
(2) a[0]=4; //把4賦給a[0]
(3) a[1]+=a[0]; //把a[0]的值4累加到a[1],使a[1]的值變為5
(4) a[3]=3*a[2]+1; //把賦值號右邊表達式的值7賦給a[3]
(5) cout<<a[a[0]]; //因a[0]=4,所以a[a[0]]對應的元素為a[4],
//該語句輸出a[4]的值8
C++語言對數組元素的下標值不作任何檢查,也就是說,當下標值超出它的有效變化范圍0n-1(假定n為數組長度)時,也不會給出任何出錯信息。為了防止下標值越界(即小於0或大於n-1),則需要編程者對下標值進行有效性檢查。如:
(1) int a[5];
(2) for(int i=0; i<5; i++) a[i]=i*i;
(3) for(i=0; i<5; i++) cout<<a[i]<<』 』;
第一條語句定義了一個數組a,其長度為5,下標變化范圍為04。第二條語句讓循環變數i在數組a下標的有效范圍內變化,使下標為i的元素賦值為i的平方值,該循環執行後數組元素a[0],a[1],a[2],a[3]和a[4]的值依次為0,1,4,9和16。第三條語句控制輸出數組a中每一個元素的值,輸出語句中下標變數a[i]中的下標i的值不會超出它的有效范圍。如果在第三條語句中,用做循環判斷條件的<表達式2>不是i<5,而是i<=5,則雖然a[5]不屬於數組a的元素,但也同樣會輸出它的值,而從編程者角度來看是一種錯誤。由於C++系統不對元素的下標值進行有效性檢查,所以用戶必須通過程序檢查,確保其下標值有效。
4. 程序舉例
(1) #include<iostream.h>
void main()
{
int i, a[6];
for(i=0;i<6;i++) cin>>a[i];
for(i=5;i>=0;i--) cout<<a[i]<<' ';
cout<<endl;
}
在程序的主函數中首先定義了一個int型簡單變數i和一個含有6個int型元素的數組a,接著使數組a中的每一個元素依次從鍵盤上得到一個相應的整數,最後使數組a中的每一個元素的值按下標從大到小的次序顯示出來,每個值之後顯示出一個空格,以便使相鄰的元素值分開。
若程序運行時,從鍵盤上輸入3,8,12,6,20,15這6個整數,則得到的輸入和運行結果為:
3 8 12 6 20 15
15 20 6 12 8 3
(2) #include<iostream.h>
void main()
{
int a[8]={25,64,38,40,75,66,38,54};
int max=a[0];
for(int i=1;i<8;i++)
if(a[i]>max) max=a[i];
cout<<"max:"<<max<<endl;
}
在這個程序的主函數中,第一條語句定義了一個整型數組a[8],並對它進行了初始化;第二條語句定義了一個整型變數max,並用數組a中第一個元素a[0]的值初始化;第三條語句是一個for循環,它讓循環變數i從1依次取值到7,依次使數組a中的每一個元素a[i]同max進行比較,若元素值大於max的值,則就把它賦給max,使max始終保存著從a[0]a[i]元素之間的最大值,當循環結束後,max的值就是數組a中所有元素的最大值;第四條語句輸出max的值。
在該程序的執行過程中,max依次取a[0],a[1]和a[4]的值,不會取其他元素的值。程序運行結果為:
max:75
(3) #include<iostream.h>
const int N=7;
void main()
{
double w[N]={2.6,7.3,4.2,5.4,6.2,3.8,1.4};
int i,x;
cout<<"輸入一個實數:";
cin>>x;
for(i=0;i<N;i++)
if(w[i]>x) cout<<"w["<<i<<"]="<<w[i]<<endl;
}
此程序的功能是從數組a[N]中順序查找出比x值大的所有元素並顯示出來。若從鍵盤上輸入的x值為5.0,則得到的程序運行結果為:
輸入一個實數:5.0
w[1]=7.3
w[3]=5.4
w[4]=6.2
(4) #include<iostream.h>
const int M=10;
void main()
{
int a[M+1];
a[0]=1; a[1]=2;
int i;
for(i=2;i<=M;++i)
a[i]=a[i-1]+a[i-2];
for(i=0;i<M;++i)
cout<<a[i]<<',';
cout<<a[M]<<endl;
}
該程序首先定義數組a,並分別為數組元素a[0]和a[1]賦值1和2,接著依次計算出a[2]至a[M]的值,每個元素值均等於它的前兩個元素值之和,最後按照下標從小到大的次序顯示出數組a中每個元素的值。該程序運行結果為:
1,2,3,5,8,13,21,34,55,89,144
㈧ C語言下標和指針的關系
指針與數組是C語言中很重要的兩個概念,它們之間有著密切的關系,利用這種關系,可以增強處理數組的靈活性,加快運行速度,本文著重討論指針與數組之間的聯系及在編程中的應用。
1.指針與數組的關系
當一個指針變數被初始化成數組名時,就說該指針變數指向了數組。如:
char str[20], *ptr;
ptr=str;
ptr被置為數組str的第一個元素的地址,因為數組名就是該數組的首地址,也是數組第一個元素的地址。此時可以認為指針ptr就是數組str(反之不成立),這樣原來對數組的處理都可以用指針來實現。如對數組元素的訪問,既可以用下標變數訪問,也可以用指針訪問。
2.指向數組元素的指針
若有如下定義:
int a[10], *pa;
pa=a;
則p=&a[0]是將數組第1個元素的地址賦給了指針變數p。
實際上,C語言中數組名就是數組的首地址,所以第一個元素的地址可以用兩種方法獲得:p=&a[0]或p=a。
這兩種方法在形式上相像,其區別在於:pa是指針變數,a是數組名。值得注意的是:pa是一個可以變化的指針變數,而a是一個常數。因為數組一經被說明,數組的地址也就是固定的,因此a是不能變化的,不允許使用a++、++a或語句a+=10,而pa++、++pa、pa+=10則是正確的。由此可見,此時指針與數組融為一體。
3.指針與一維數組
理解指針與一維數組的關系,首先要了解在編譯系統中,一維數組的存儲組織形式和對數組元素的訪問方法。
一維數組是一個線形表,它被存放在一片連續的內存單元中。C語言對數組的訪問是通過數組名(數組的起始地址)加上相對於起始地址的相對量(由下標變數給出),得到要訪問的數組元素的單元地址,然後再對計算出的單元地址的內容進行訪問。通常把數據類型所佔單元的位元組個數稱為擴大因子。
實際上編譯系統將數組元素的形式a[i]轉換成*(a+i),然後才進行運算。對於一般數組元素的形式:<數組名>[<下標表達式>],編譯程序將其轉換成:*(<數組名>+<下標表達式>),其中下標表達式為:下標表達式*擴大因子。整個式子計算結果是一個內存地址,最後的結果為:*<地址>=<地址所對應單元的地址的內容>。由此可見,C語言對數組的處理,實際上是轉換成指針地址的運算。
數組與指針暗中結合在一起。因此,任何能由下標完成的操作,都可以用指針來實現,一個不帶下標的數組名就是一個指向該數組的指針。
4.指針與多維數組
用指針變數可以指向一維數組,也可以指向多維數組。但在概念上和使用上,多維數組的指針比一維數組的指針要復雜一些。
例如,在一個三維數組中,引用元素c[i][j][k]的地址計算最終將換成:*(*(*(c+i)+j)+k)。了解了多維數組的存儲形式和訪問多維數組元素的內部轉換公式後,再看當一個指針變數指向多維數組及其元素的情況。
1 指向數組元素的指針變數
若有如下說明:
int a[3][4];
int *p;
p=a;
p是指向整型變數的指針;p=a使p指向整型二維數組a的首地址。
*(*(p+1)+2)表示取a[1][2]的內容;*p表示取a[0][1]的內容,因為p是指向整型變數的指針;p++表示p的內容加1,即p中存放的地址增加一個整型量的位元組數2,從而使p指向下一個整型量a[0][1]。
2 指向由j個整數組成的一維數組的指針變數
當指針變數p不是指向整型變數,而是指向一個包含j個元素的一維數組。如果p=a[0],則p++不是指向a[0][1],而是指向a[1]。這時p的增值以一維數組的長度為單位。
5.指針與字元數組
C語言中許多字元串操作都是由指向字元數組的指針及指針的運算來實現的。因為對於字元串來說,一般都是嚴格的順序存取方式,使用指針可以打破這種存取方式,更為靈活地處理字元串。
另外由於字元串以′\0′作為結束符,而′\0′的ASCII碼是0,它正好是C語言的邏輯假值,所以可以直接用它作為判斷字元串結束的條件,而不需要用字元串的長度來判斷。C語言中類似的字元串處理函數都是用指針來完成,使程序運行速度更快、效率更高,而且更易於理解。
㈨ C語言中數組元素的下標可不可以是數組元素,另外··
C語言程序運行時,數組的存在形式是內存中的一塊連續地址空間。而訪問數組元素時,計算機會將下標做為空間首地址的偏移量來進行定址,所以當然可以是任何整形數。
比如int array[10],array的地址是0x7FFFFF00,那麼在訪問array[3]時,計算機是這樣計算的:
每個整形數大小為4個位元組,所以用array的地址加上3乘以4,得到0x7FFFFF0C,那麼從0x7FFFFF0C到0x7FFFFF0F這4個位元組的值就是array[3]的值。
所以無論傳入的下標是什麼,理論上都可以計算得到一個地址,但是這個地址不一定是有效的。如果地址無效,就會發生段錯誤(segmentation fault),也即數組越界/地址訪問越界。現在的編譯器會認為只要下標是個整型變數,就是可以的,但是執行的時候操作系統仍然會進行監測,否則會影響其他程序的運行。
比如說a = {1, 2, 4, 5, 7}, b = { 1, 2, 3, 4, 5, 6, 7, 8 },那麼b[a[3]] = b[5]=6,這個是可以允許的。
㈩ 數組什麼是下標變數
比如有一個數組:arr[5]={6,7,8,9,10};
當你要用到這個數組第二個元素時,你就可以用arr[1]來代表第二個元素7,這里的1就是下標變數。變數與下標變數的區別在於:下標變數只能是一個非負的整型值,而變數即可以表示正數也可以表示負數。第二,變數表示的數值可以很大,但下標變數表示的值是有一定范圍的。比如說上面這個數組,它的下標的范圍就只能是0-4,如果你要用6作這它的下標,就會出現錯誤。因為編譯器在這個數組里找不到這個元素。記住:在C/C++里所有數組的下標都是從0開始的