欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

一篇文章帶你入門C語(yǔ)言:數(shù)組

 更新時(shí)間:2021年08月03日 15:32:00   作者:AKA你的閨蜜  
這篇文章主要介紹了C語(yǔ)言中數(shù)組的一些基本知識(shí)小結(jié),其中重點(diǎn)是對(duì)于數(shù)組的內(nèi)存分配相關(guān)方面的知識(shí)整理,需要的朋友可以參考下

數(shù)組

一維數(shù)組

創(chuàng)建 定義

數(shù)組是一組相同類型的元素的集合。那數(shù)組的語(yǔ)法形式:

type_t arr_name [const_n]
//如:
int arr[10];

type_t 指的是數(shù)組元素的類型。

const_n 指的是一個(gè)常量表達(dá)式,用來(lái)指定數(shù)組的大小。

此時(shí)運(yùn)行程序的話,系統(tǒng)會(huì)報(bào)一個(gè)警告:未初始化變量。打開調(diào)試就會(huì)發(fā)現(xiàn)系統(tǒng)默認(rèn)填入一些無(wú)意義的數(shù)據(jù)。

系統(tǒng)默認(rèn)未初始化值

當(dāng)然全局?jǐn)?shù)組的話,系統(tǒng)默認(rèn)初始化為0;

int arr[10];// 0 0 ... 0
int main(){
  return 0;
}

創(chuàng)建實(shí)例

//1.	
int arr[10];
//2.
int count = 10;
int arr2[count];//這樣的創(chuàng)建數(shù)組可不可以呢?
//3.
float arr3[20];//浮點(diǎn)型數(shù)組
char ch[10];

數(shù)組的創(chuàng)建必須要[]使用常量,不能使用變量。(ps:雖然C99支持變長(zhǎng)數(shù)組,但一般用常數(shù)創(chuàng)建就已經(jīng)夠用了)同樣,我雖然用const_n表示常量,但可千萬(wàn)不要誤會(huì)為const修飾的變量哦。

為什么呢?

因?yàn)閿?shù)組控制不好容易越界訪問(wèn)非法內(nèi)存,用變量的話風(fēng)險(xiǎn)太大,所以一直以來(lái)都是用常量創(chuàng)建數(shù)組的。

初始化

初始化,顧名思義,在創(chuàng)建數(shù)組的同時(shí)給予一些合理的初識(shí)值。如:

int arr[10] = { 1,2,3 };//不完全初始化

這種是不完全初始化,剩余的元素默認(rèn)是0

int arr2[] = { 1,2,3,4 };//利用初始化內(nèi)容,指定數(shù)組大小

這種是省略數(shù)組的const_n常量表達(dá)式

由初始化內(nèi)容指定數(shù)組的大小

那下面這三個(gè)有什么不同呢?

/字符串?dāng)?shù)組初始化示

第一種是用字符串初始化數(shù)組,字符串有\(zhòng)0作為結(jié)束標(biāo)志,雖不算字符串內(nèi)容,但是可以說(shuō)是字符串與生俱來(lái)的,所以它也被初始化作為數(shù)組內(nèi)容。a b c \0

第二種和第三種是一樣的,因?yàn)閿?shù)組元素類型是字符型,且字符'b'的ACSII碼值是98,自動(dòng)將98解析為字符。a b c

使用

數(shù)組的訪問(wèn)是通過(guò)下標(biāo)來(lái)訪問(wèn)的,默認(rèn)下標(biāo)是從0開始。通過(guò)下標(biāo)引用操作符[]我們可以訪問(wèn)到數(shù)組元素。

int arr[10] = { 1,2,3,4,5,6,7,8,9,10 };
//數(shù)組的下標(biāo)是從0開始的0~9
int sz = sizeof(arr) / sizeof(arr[0]);//10
for (int i = 0; i < sz; i++)
{
    printf("%d ", arr[i]);
}
//1 2 3 4 5 6 7 8 9 10

對(duì)于sizeof操作符,sizeof(arr),即sizeof+數(shù)組名,指的是計(jì)算整個(gè)數(shù)組的大小,算出來(lái)是40,然后sizeof(arr[0])是計(jì)算數(shù)組首元素的大小為4,這樣一除就是元素個(gè)數(shù)啦。

使用變量sz,可以靈活的改變數(shù)組的大小,就不用再更改循環(huán)條件了。

總結(jié):

  • 數(shù)組是通過(guò)下標(biāo)訪問(wèn)的,下標(biāo)從0開始
  • 數(shù)組的大小可以通過(guò)計(jì)算得到

內(nèi)存存儲(chǔ)

在這里插入圖片描述

通過(guò)printf("&arr[%d]=%p\n", i,&arr[i]);這樣的語(yǔ)句我們可以看到該數(shù)組在內(nèi)存中的存儲(chǔ)情況。

很明顯的是,數(shù)組在內(nèi)存中是連續(xù)存放的。

在這里插入圖片描述

右邊是十六進(jìn)制的內(nèi)存編號(hào),可以看見(jiàn)每一個(gè)元素之間都相差4個(gè)字節(jié),而一個(gè)整型元素正好占4個(gè)字節(jié)。

所以數(shù)組在內(nèi)存中是連續(xù)存放的,隨著數(shù)組下標(biāo)的增長(zhǎng),地址也在增長(zhǎng),這也正是為什么指針變量+1,可以訪問(wèn)到下一個(gè)數(shù)組元素。

所以數(shù)組的本質(zhì)是什么?

一組內(nèi)存中連續(xù)存放的相同類型的元素。

二維數(shù)組

創(chuàng)建

type_t arr_name[const_n][const_n]
//
int arr[3][5];//3行5列
char ch[4][7];//4行5列
double arr2[2][4]//2行4列

如上述代碼所示:二維數(shù)組的語(yǔ)法結(jié)構(gòu)就是,類型+數(shù)組名+[行][列]。

二維數(shù)組描述示意圖

如圖所示,二維數(shù)組在理解上就是這樣的3行5列類似于表格的東西。就像線性代數(shù)里的矩陣,矩陣的定義就是一組數(shù)組成數(shù)表。

初始化

//1.
int arr1[3][5] = { 1,2,3,4,5,6,7,8,9,10,11 };
//2.
int arr2[3][5] = { {1,2},{3,4},{5,6,7} };
第一種初始化,先一行一行填入,第一行是1 2 3 4 5,第二行是6 7 8 9 10,第三行不夠就補(bǔ)零11 0 0 0 0 。第二種的話,把每一行看成一個(gè)一維數(shù)組,不夠的話還是補(bǔ)零,即第一行1 2 0 0 0,第二行3 4 0 0 0,第三行5 6 7 0 0 。

二維數(shù)組初始化示意

char ch1[2][4] = { 'a','b' };
char ch2[2][4] = { {'a'},{'b'} };
char ch3[3][4] = { "abc","def","gh" };

當(dāng)然用字符串去初始化二維數(shù)組的話,也是需要注意\0的問(wèn)題。

第一行:a b c \0;第二行:d e f \0;第三行:g h \0 0

省略

int arr2[][5] = { {1,2},{3,4},{5,6,7} };

像這樣省略行可以,但是不能省略列。

行數(shù)可以根據(jù)初始化內(nèi)容來(lái)規(guī)定,但如果列省略了就會(huì)造成歧義。

當(dāng)然,省略必須在已經(jīng)初始化的前提之下,不然行和列一概不知,怎么分配空間呢?

使用

當(dāng)然二維數(shù)組同樣是用下標(biāo)訪問(wèn)數(shù)組內(nèi)容的,也是從0開始。如:

二維數(shù)組下標(biāo)示意

我們要去訪問(wèn)這個(gè)二維數(shù)組的話,我們當(dāng)然是用兩次循環(huán)遍歷這個(gè)數(shù)組。

循環(huán)遍歷二維數(shù)組示例

內(nèi)存存儲(chǔ)

當(dāng)然我們也可以用同樣的辦法打印出每個(gè)元素的地址,如:

二維數(shù)組內(nèi)存存儲(chǔ)地址示例

我們還是能發(fā)現(xiàn)每一個(gè)元素都是在內(nèi)存中連續(xù)存放的。

這樣的話,二維數(shù)組在內(nèi)存中的存儲(chǔ)形式便是大家想象中的二維的形式,把每一行理解為一個(gè)一維數(shù)組,這樣的話二維數(shù)組在內(nèi)存中的存儲(chǔ)形式還是一維的。如下圖的對(duì)比:

二維數(shù)組存儲(chǔ)形式對(duì)比示意圖

從這里我們也可以理解到,二維數(shù)組的初始化里,為什么可以省略行不能省略列。

把行省略了,但是我們知道列,一個(gè)一個(gè)填滿就是了,能填到多少行就有多少行。

理解方式

對(duì)于二維數(shù)組,我們可以理解為每一行為一個(gè)元素的一維數(shù)組,該一維數(shù)組的每一個(gè)元素又是一個(gè)一維數(shù)組。

如數(shù)組arr[3][5] ,是有3個(gè)元素的一維數(shù)組,每個(gè)元素是一個(gè)有5個(gè)元素的一維數(shù)組。

指向二維數(shù)組的指針+1,指向的是下一行。

對(duì)于二維數(shù)組在內(nèi)存存儲(chǔ)形式的理解還是很重要的,有了這樣的思想,我們就可以通過(guò)指針遍歷得到數(shù)組元素,如:

int arr[3][5] = { {1,2,3},{4,5,6},{7,8} };
int* p = &arr[0][0];
for (int i = 0; i < 15; i++)
{
    printf("%d ", *p++);//1 2 3 0 0 4 5 6 0 0 7 8 0 0 0
}

數(shù)組越界問(wèn)題

定義

數(shù)組通過(guò)下標(biāo)訪問(wèn),那么下標(biāo)也就可以控制數(shù)組的訪問(wèn)范圍。在數(shù)組前后進(jìn)行訪問(wèn)的話,就是非法訪問(wèn)內(nèi)存,即數(shù)組越界。

//1 2 3 4 5 -858993460
int arr[5] = { 1,2,3,4,5 };
for (int i = 0; i <= 5; i++)//越界訪問(wèn)到第6個(gè)
{
    printf("%d ", arr[i]);
}

數(shù)組越界訪問(wèn)到最后一個(gè)元素之后的一塊內(nèi)存,這就屬于越界訪問(wèn),-858993460是vs2019自動(dòng)生成的隨機(jī)值。

一般編譯器是不會(huì)去檢查數(shù)組越界訪問(wèn)的情況(vs2019太先進(jìn)),所以我們就要有意識(shí)的主動(dòng)檢查。如果編譯器提示這樣的錯(cuò)誤信息,那么一般就是數(shù)組越界了:

數(shù)組越界訪問(wèn)報(bào)錯(cuò)示例

數(shù)組作函數(shù)參數(shù)

在寫代碼時(shí),我們經(jīng)常會(huì)將數(shù)組作為參數(shù),比如接下來(lái)的兩個(gè)應(yīng)用實(shí)例,那么我們這里以冒泡排序的實(shí)現(xiàn)作為案例。

排序算法一般有四種:冒泡排序、選擇排序、插入排序和快速排序。

冒泡排序的核心思想:兩兩相鄰的元素進(jìn)行比較。

  • 一趟冒泡排序搞定一個(gè)數(shù)字,讓其來(lái)到最終的位置上。
  • n n n 個(gè)元素,則總共需要 n − 1 n-1 n−1 趟冒泡排序,每一趟排序需要進(jìn)行 n − 1 − i n-1-i n−1−i 次判斷大小。

如分析圖所示:

冒泡排序示意圖

void Print(int* arr, int sz)
{
	for (int i = 0; i < sz; i++)
	{
		printf("%d ", *arr++);
	}
}
void Sort(int arr[],int sz)//int* arr
//數(shù)組作形參本質(zhì)是指針
{
	//int sz = sizeof(arr) / sizeof(arr[0]);//err//用指針的sizeof值除以另一個(gè)值 = 4 / 4 = 1
	for (int i = 0; i < sz - 1; i++)//n-1趟
	{
		for (int j = 0; j < sz - 1 - i; j++)//n-1-i次
		{
			if (arr[j] > arr[j + 1])//目標(biāo)升序
			{
				//交換
				int tmp = arr[j];
				arr[j] = arr[j + 1];
				arr[j + 1] = tmp;
			}
		}
	}
}
int main()
{
	int arr[] = { 1,4,6,3,7,9,3,2,8,5 };
	int sz = sizeof(arr) / sizeof(arr[0]);
	//數(shù)組名單獨(dú)放在sizeof中,表示整個(gè)數(shù)組
	//排序
	Sort(arr,sz);
	//打印
	Print(arr,sz);
	return 0;
}

1.定義數(shù)組作形參時(shí),本質(zhì)上是指針。

void Sort(int *arr,int sz)本質(zhì)上就是void Sort(int arr[],int sz)

所以Sort()函數(shù)內(nèi),sizeof(arr)也算的就是指針arr的大小,所以只能傳參進(jìn)去。

2.數(shù)組名arr何時(shí)代表整個(gè)數(shù)組何時(shí)代表數(shù)組首元素地址呢?

  • 代表整個(gè)數(shù)組的情況:

單獨(dú)放在sizeof操作符內(nèi)部時(shí),如sizeof(arr); 。

寫出&arr時(shí),代表的是整個(gè)數(shù)組,但表面仍為首元素地址。

  • 代表首元素地址的情況:

除上面兩以外其他都是代表首元素的地址。

應(yīng)用實(shí)例

筆者實(shí)在沒(méi)時(shí)間寫兩個(gè)應(yīng)用實(shí)例的博客,所以在此將思維導(dǎo)圖奉上,一般照著思維導(dǎo)圖寫就沒(méi)問(wèn)題了。感謝李姐和支持~

數(shù)組的應(yīng)用實(shí)例1:三子棋

三子棋腦圖

數(shù)組的應(yīng)用實(shí)例2:掃雷游戲

掃雷腦圖

總結(jié)

本篇文章就到這里了,希望能給你帶來(lái)幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!

相關(guān)文章

  • C語(yǔ)言的運(yùn)算符你了解嗎

    C語(yǔ)言的運(yùn)算符你了解嗎

    這篇文章主要介紹了C語(yǔ)言中的運(yùn)算符,本文給大家介紹的非常詳細(xì),具有參考借鑒價(jià)值,需要的朋友可以參考下,希望能給你帶來(lái)幫助
    2021-08-08
  • C++編寫實(shí)現(xiàn)圖書管理系統(tǒng)

    C++編寫實(shí)現(xiàn)圖書管理系統(tǒng)

    這篇文章主要為大家詳細(xì)介紹了C++編寫實(shí)現(xiàn)圖書管理系統(tǒng),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-03-03
  • 基于C語(yǔ)言實(shí)現(xiàn)簡(jiǎn)單掃雷游戲

    基于C語(yǔ)言實(shí)現(xiàn)簡(jiǎn)單掃雷游戲

    這篇文章主要為大家詳細(xì)介紹了基于C語(yǔ)言實(shí)現(xiàn)簡(jiǎn)單掃雷游戲,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2021-11-11
  • 如何用C++實(shí)現(xiàn)A*尋路算法

    如何用C++實(shí)現(xiàn)A*尋路算法

    尋路是游戲比較重要的一個(gè)組成部分。因?yàn)椴粌HAI還有很多地方(例如RTS游戲里操控人物點(diǎn)到地圖某個(gè)點(diǎn),然后人物自動(dòng)尋路走過(guò)去)都需要用到自動(dòng)尋路的功能。本文將介紹一個(gè)經(jīng)常被使用且效率理想的尋路方法-A*尋路算法,并且提供額外的優(yōu)化思路
    2021-06-06
  • C字符串與C++中string的區(qū)別詳解

    C字符串與C++中string的區(qū)別詳解

    以下是對(duì)C字符串與C++中string的區(qū)別進(jìn)行了詳細(xì)的分析介紹,需要的朋友可以過(guò)來(lái)參考下
    2013-09-09
  • C++實(shí)現(xiàn)通訊錄功能

    C++實(shí)現(xiàn)通訊錄功能

    這篇文章主要為大家詳細(xì)介紹了C++實(shí)現(xiàn)通訊錄功能,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-06-06
  • makefile如何調(diào)用靜態(tài)庫(kù)的方法實(shí)現(xiàn)

    makefile如何調(diào)用靜態(tài)庫(kù)的方法實(shí)現(xiàn)

    這篇文章主要介紹了makefile如何調(diào)用靜態(tài)庫(kù)的方法實(shí)現(xiàn),文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧
    2020-12-12
  • 利用簡(jiǎn)潔的C語(yǔ)言代碼解決跳臺(tái)階問(wèn)題與約瑟夫環(huán)問(wèn)題

    利用簡(jiǎn)潔的C語(yǔ)言代碼解決跳臺(tái)階問(wèn)題與約瑟夫環(huán)問(wèn)題

    這篇文章主要介紹了利用簡(jiǎn)潔的C語(yǔ)言代碼解決跳臺(tái)階問(wèn)題與約瑟夫環(huán)問(wèn)題的方法,跳臺(tái)階問(wèn)題與約瑟夫環(huán)問(wèn)題是常見(jiàn)的基礎(chǔ)算法題目,需要的朋友可以參考下
    2016-02-02
  • C++實(shí)現(xiàn)高校教室管理系統(tǒng)

    C++實(shí)現(xiàn)高校教室管理系統(tǒng)

    這篇文章主要為大家詳細(xì)介紹了C++實(shí)現(xiàn)高校教室管理系統(tǒng),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下
    2022-03-03
  • C++讀取訪問(wèn)權(quán)限沖突引發(fā)異常問(wèn)題的原因分析

    C++讀取訪問(wèn)權(quán)限沖突引發(fā)異常問(wèn)題的原因分析

    C語(yǔ)言是一門通用計(jì)算機(jī)編程語(yǔ)言,廣泛應(yīng)用于底層開發(fā),最近在用C++寫代碼時(shí)經(jīng)常會(huì)遇到“引發(fā)了異常: 讀取訪問(wèn)權(quán)限沖突,所以這篇文章主要給大家介紹了關(guān)于C++讀取訪問(wèn)權(quán)限沖突引發(fā)異常問(wèn)題的相關(guān)資料,需要的朋友可以參考下
    2021-07-07

最新評(píng)論