各位同學,你覺得你數組學會了嗎?不妨看看下面的問題,你能看一眼程序就回答上來嗎?
引子:觀察下面的程序,這個程序有安全隱患嗎?
<code>#include<stdio.h>
intmain(){
intx=0;
doublesum=0;
intnumber[100]={0};
intcnt=0;
scanf("%d",&x);
while(x!=-1){
number[cnt]=x;
sum+=x;
cnt++;
scanf("%d",&x);
}
if(cnt>0){
inti=0;
doubleaverage=sum/cnt;
for(i=0;iif(number[i]>average) /<stdio.h>/<code>
printf("number%d:%d\\n",i,number[i]);
}
}
}
答案是有的 while循環種沒有限制 cnt 有可能導致 數組越界!
不能快速找到錯誤和找不到錯誤其實是一樣的,因為不能快速找到這個錯誤說明你沒有深刻的理解數組。這種基礎的概念如果沒有滲透到你的腦中,並不能說自己學好了數組吧!我學了一學期C,課設1000行代碼都是自己獨立完成的。依然沒有立刻看出這個問題來,我也是自愧沒有學好啊!
數組特性與一個注意
1.數組是一種容器(放東西的東西)2.基本特點是:
其中所有元素具有相同的數據類型一旦創建,不能改變大小在內存中連續依次排列
3.注意:數組作為函數參數時,往往必須再用另一個參數來傳入數組的大小我們常用sizeof(arr) / sizeof(arr[0])來判斷數組元素個數但是這種情況下不能在函數中用sizeof(arr)判斷數組大小
例1
//寫一個程序,輸入數量不確定的【0 ~ 9】範圍內的整數,統計每一種數字出現的次數,輸入 -1 表示結束
方法一:先看一個基礎做法
<code>#include<stdio.h>
intmain(){
constintnumber=10;//記錄數組元素。用const修飾,數組大小規定後不可改變
intcount[10]={0};
inti=0;
intinput=1;
while(input+1){//避免輸入0時退出,-1+1=0剛好滿足退出要求
printf("inputanumber\\n");
scanf("%d",&input);
switch(input){
case0:
count[0]++;
break;
case1:
count[1]++;
break;
case2:
count[2]++;
break;
case3:
count[3]++;
break;
case4:
count[4]++;
break;
case5:
count[5]++;
break;
case6:
count[6]++;
break;
case7:
count[7]++;
break;
case8:
count[8]++;
break;
case9:
count[9]++;
break;
default:
break;
}
for(i=0;i<10;i++)
printf("%d:%dtimes\\n",i,count[i]);
return0;
}
/<stdio.h>/<code>
方法2
當我們要統計的數是像 0 ~ 9 這樣連續的數時,我們可以把數組下標與這些數一一對應起來,可以更方便,快捷
<code>#include<stdio.h>
intmain(){
intcount[10]={0};
inti=0;
intinput=1;
interror=0;
//更簡單的方法:
while(input+1){
printf("inputanumber\\n");
scanf("%d",&input);
if(input>=0&&input<=9)
count[input]++;
if(input==-1)
break;
}
for(i=0;i<10;i++){
printf("%d:%dtimes\\n",i,count[i]);
}
return0;
}
/<stdio.h>/<code>
思考一下:字符常量可以做數組下標嗎?例如,形如arr['a'] 可以嗎?
如果可以,那麼當我們想要統計字符串種某個字母(或者任何ASCII碼錶上存在的字符)的具體個數時,就會很方便。可以自己嘗試著寫一下哦~思路和上面的數字判斷差不多。我寫的供大家參考:https://github.com/hairrrrr/win.ccode/blob/master/Pactise/2020WinterVacation/Array/%E7%BB%9F%E8%AE%A1%E6%AF%8F%E4%B8%AA%E5%AD%97%E6%AF%8D%E5%87%BA%E7%8E%B0%E7%9A%84%E6%AC%A1%E6%95%B0%EF%BC%88%E5%8F%AF%E6%8B%93%E5%B1%95%E5%88%B0%E7%BB%9F%E8%AE%A1%E6%89%80%E6%9C%89ascii%E8%A1%A8%E5%86%85%E5%87%BA%E7%8E%B0%E7%9A%84%E5%AD%97%E7%AC%A6%E6%AC%A1%E6%95%B0%EF%BC%89.c
例2
<code>#include<stdio.h>
#defineN10//數組元素個數
intsearch(intwant,intlenth,int*arr){
intright=lenth-1;
intleft=0;
intmid=0;
intret=0;
while(right>=left){
mid=(right+left)/2;
if(want>arr[mid])
left=mid+1;
if(wantright=mid-1; /<stdio.h>/<code>
if(want==arr[mid]){
ret=mid;
break;
}
}
if(right<left>return-1;
else
returnret;
}
intmain(){
intarr[N]={1,2,3,4,5,6,7,8,9,10};
intlenth=sizeof(arr)/sizeof(arr[0]);//計算數組大小
intwant=0;
intindex=0;
printf("inputthenumberyouwanttosearch\\n");
scanf("%d",&want);
index=search(want,lenth,arr);//切記:數組作為函數參數時,往往必須再用另一個參數來傳入數組的大小
if(index==-1)
printf("Can'tfind!\\n");
else
printf("theindexof%d:%d\\n",want,index);
return0;
}
/<left>
二維數組
1.初始化
int a[][3] = {{1, 1, 1}, {2, 2, 2}, {3},}1.列數必須給出,行數可以空出2.每行都有有一個單獨的大括號 { }(可以不寫,建議寫上)3.最後的逗號可以寫上,老一代程序員們約定俗成的經驗(如果你寫上,可以裝裝逼)4.缺省表示補零5.強烈推薦的另一種書寫方式:
int a[][3] = { {1, 1, 1}, {2, 2, 2}, {3}, }
這樣寫的好處不言而喻,更加形象立體
練習題
1.
若有定義:int a[2][3].則下列不越界的正確訪問有:A: a[2][0]B: a[2][3]C: a[1 > 2][0]D: a[0][3]
2.
以下程序片段輸出的結果是:
<code>intm[][3]={1,4,7,2,5,8,3,6,9,}
inti,j,k=2;
for(i=0;i<3;i++){
printf("%d",m[k][j]);
}
/<code>
A: 369B: 不能通過編譯C:789D:能編譯,但是數組下標越界了
3
若有int a[][3] = {{0}, {1}, {2}};a[1][2] 的值是?
答案:C A 0
歡迎大家在留言區題問,我看到都會回覆的
閱讀更多 編程反思錄 的文章