国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

【C的葵花寶典進階篇】之指針進階(一)

這篇具有很好參考價值的文章主要介紹了【C的葵花寶典進階篇】之指針進階(一)。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。


【C語言進階技巧】指針掌握之道:解密指針的奇妙世界(第一部))
【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft

??博客主頁: 小鎮(zhèn)敲碼人
?? 歡迎關(guān)注:??點贊 ????留言 ??收藏
??回來4天了,加油?。。??????
??當你的能力匹配不上你的夢想,當你需要實現(xiàn)的目標匹配不上你的圈子的時候,你就會出現(xiàn)錯位。當我們的能力還匹配不上我們的夢想時,我們就需要沉淀學習。??????

【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft

1. 字符指針

字符指針,就是儲存字符變量地址的指針,這是一種指針的類型。

  • 通常我們字符指針有如下兩種用途
  1. 通過字符指針間接改變字符的值
    int main()
    {
      char ch = 'c';
     // ch = 'a';//直接通過變量賦值更改ch的值
      char *p = &ch;//將字符ch的地址存入p中
      //*p = 'a';//通過對p里面的地址解引用找到ch,間接的改變ch的值
    }
  1. 借助字符指針對字符串進行儲存和打印
 int main()
 {
   const char* ptr = "abcdef";
   printf("%s\n",ptr);
   return 0;
 }
  • const修飾字符串表示"abcdef"不可修改,為常量字符串
  • 字符指針變量ptr只儲存了字符'a'的地址。 (可類比字符數(shù)組理解,實際上字符串是字符數(shù)組的一種形式,在C語言中,字符串是由字符數(shù)組表示的,以空字符(‘\0’)作為字符串的結(jié)束標志,又因為數(shù)組名表示首元素地址,所以字符指針也只儲存了首元素的地址)

2. 指針數(shù)組

??????指針數(shù)組是由指針組成的數(shù)組。在C和C++等編程語言中,指針是一個變量,用于存儲內(nèi)存地址。指針數(shù)組是一個數(shù)組,其每個元素都是指針類型。
????int *arr1[10];????整形指針數(shù)組
????char *arr2[10];??一級字符指針的數(shù)組
????char **arr3[10];?二級字符指針的數(shù)組

2.1 整形指針數(shù)組

int main()
{
    int a = 0;
        int b = 1;
    int c = 2;
    int* arr[] = { &a,&b,&c };
    for (int i = 0; i < 3; i++)
    {
        printf("%d ", *arr[i]);
    }
}

2.2 用指針數(shù)組模擬二維數(shù)組

int main()
{
	int arr1[] = { 1,2,3,4,5 };//arr1-int*
	int arr2[] = { 2,3,4,5,6 };//arr2-int*
	int arr3[] = { 3,4,5,6,7 };//arr3-int*
   //指針數(shù)組
	int* p[] = { arr1,arr2,arr3 };
	for (int i = 0; i < 3; i++)
	{
		for (int j = 0; j < 5; j++)
		{
		  //這兩種方式打印都可以,兩者擇一
			printf("%d ", *(*(p + i) + j));
            printf("%d ",p[i][j]);
		}
		printf("\n");
	}
}

3. 數(shù)組指針

我們可以通過類比來理解

整型指針:int * a;能夠指向整形數(shù)據(jù)的指針
浮點型指針:float* b;能夠指向浮點型數(shù)據(jù)的指針。
那么數(shù)組指針應該是:能夠指向數(shù)組的指針。

3.1 數(shù)組指針的表示方法

數(shù)組的類型表示是什么?通過簡單的類比可以知道。

  1. int a = 3;類型為除變量名以外的部分int就是整形的類型表示形式。
  2. char b = 'a';類型為除變量名以外的部分char就是字符類型的的表示形式。
  3. int arr[10] = {0};類型為除變量名以外的部分int [10]就是這個數(shù)組的變量類型表示形式。
  4. 而數(shù)組指針的類型是指針,指針的類型是數(shù)組,通過前面的學習我們知道,變量類型+變量名為一個變量,所以一個數(shù)組指針變量就是,指向數(shù)組的指針變量,int [10] *p = &arr;,看起來似乎是這樣,但是通過下面符號的優(yōu)先級我們可以知道[]的優(yōu)先級要比*號高,所以我們要給*p加上括號,讓其成為指針,int [10] (*p) = &arr,那這樣是否正確呢?還是不對,放進vs編譯器會報錯,數(shù)組的類型比較特殊,應該是這樣int (*p) [10] = &arr;才正確。

3.2 深度剖析&數(shù)組名和數(shù)組名

對于下面的數(shù)組

 int arr[10];
  • arr&arr分別是什么呢?
    對于arr,我們知道它是一個數(shù)組名,數(shù)組名表示首元素的地址,
    那&arr是什么呢,我們來看下面一段代碼:
int main()
{
	int arr[10] = { 0 };
	printf("arr       = %p\n", arr);
	printf("arr+1     = %p\n", arr+1);

	printf("&arr[0]   = %p\n", &arr[0]);
	printf("&arr[0]+1 = %p\n", &arr[0]+1);
	
	printf("&arr      = %p\n", &arr);
	printf("&arr+1    = %p\n", &arr+1);
	return 0;
}

運行結(jié)果如下:
【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft
可以看到數(shù)組名和&數(shù)組名打印的地址和首元素打印的地址是一樣的,這是不是意味著它們是一樣的呢?很明顯通過代碼我們也可以發(fā)現(xiàn),它們并不是相同的,因為&arr+1打印的地址與arr+1打印的地址相差了40個字節(jié),而arr+1打印的地址和首元素&arr+1的仍然一樣,進一步說明,arr就表示首元素地址。

  • 實際上:&arr表示的是整個數(shù)組的地址,它的類型是int (*)[10],是一種數(shù)組指針類型。
    ???????????? ??而arr代表的是數(shù)組首元素的地址,它的類型是int *。
    ???????????????數(shù)組的地址加1,跳過整個數(shù)組的大小,所以&arr+1與&arr的差值就是 10 ? 4 = 40 10*4 =40 10?4=40個字節(jié)。

3.3 數(shù)組指針的使用

3.3.1 在同一函數(shù)內(nèi)直接將數(shù)組的地址賦給數(shù)組指針

#include<stdio.h>
int main()
{
	int arr[10] = { 1,2,3,4,5,6,7,8,9,10 };
	//int[10] *p = &arr;err
	int (*p)[10] = &arr;
	for (int i = 0; i < 10; i++)
	{
	    //兩種打印方式擇一
	    printf("%d ",*((*p)+i));
		printf("%d ", (*p)[i]);
	}
	//int* p2 = &arr;//err
	return 0;
}

  • 可以看到,這樣做簡直就是多此一舉,因為想打印一維數(shù)組,我們直接打印就行了,使用數(shù)組指針,反倒是比較麻煩。

3.3.2 數(shù)組指針在二維數(shù)組傳參上的應用

3.3.2.1 二維數(shù)組傳參使用二維數(shù)組
#include<stdio.h>
void Print(int arr[][5], int r, int c)
{
	for (int i = 0; i < r; i++)
	{
		for (int j = 0; j < c; j++)
		{
			printf("%d ", arr[i][j]);
		}
		printf("\n");
   }
}
int main()
{
	int arr[3][5] = { 1,2,3,4,5,2,3,4,5,6,3,4,5,6,7 };
	Print(arr, 3, 5);
	return 0;
}
3.3.2.2 二維數(shù)組傳參使用數(shù)組指針
#include<stdio.h>
Print(int(*p)[5], int r, int c)
{
	for (int i = 0; i < r; i++)
	{
		for (int j = 0; j < c; j++)
		{
		  //兩種打印方式擇一
			printf("%d ", *(*(p + i) + j));
			printf("%d ", p[i][j]);
		}
		printf("%\n");
	}
}
int main()
{
	int arr[3][5] = { 1,2,3,4,5,2,3,4,5,6,3,4,5,6,7 };
	//arr表示數(shù)組名,數(shù)組名表示首元素的地址,也就是那一行的地址
	Print(arr, 3, 5);
	return 0;
}
  • 因為二維數(shù)組的數(shù)組名代表首元素的地址,首元素地址就是那一行的地址,就等價于一維數(shù)組的地址(&一維數(shù)組數(shù)組名),故又稱二維數(shù)組為一維數(shù)組的數(shù)組,所以可以用數(shù)組指針來接收。

4. 數(shù)組傳參和指針傳參

4.1 一維數(shù)組傳參

  • 有以下主要兩種方式
  1. 傳遞數(shù)組名,用一級指針的方式去接收,通過地址訪問
  2. 傳遞數(shù)組的副本
#include<stdio.h>
void test1(int arr[])
{}
void test1(int arr[10])
{}
void test1(int* arr)
{}
void test2(int* arr[20])
{}
void test2(int** arr)
{}
int main()
{
	int arr1[10] = { 0 };
	int* arr2[20] = { 20 };
	test1(arr1);
	test2(arr2);
	return 0;
}

4.2 二維數(shù)組傳參

  • 正確的方法已經(jīng)在“3.3.2 數(shù)組指針在二維數(shù)組傳參上的應用“版塊給出,下面就幾種錯誤的傳參方法做一下闡述。
#include<stdio.h>
void test(int arr[3][5]) ? 
{}
void test(int arr[][])//err,二維數(shù)組傳參,如果是傳遞數(shù)組的副本,需要給出一行有多少數(shù)字,因為二維數(shù)組其實是一維數(shù)組的擴展,所以需要提供一行有多少元素,來正確進行內(nèi)存訪問
{}
void test (int arr[][5]) ? 
{}
void test(int *arr)//err,傳的是一行的地址,指針的類型是數(shù)組,int(*)[5]。
{}
void test(int *arr[5])//err,傳的是第一行的地址,用指針數(shù)組接收不對,因為傳的是一行的地址。
{}
void  test(int (*arr)[5]) ? 
{}
void test(int **arr)//err,傳的是數(shù)組的地址(第一行的地址),不是一級指針的地址,不能用二級指針接收。
{}
int main()
{
	int arr[3][5] = { 0 };
	test(&arr);
	return 0;
}
  • 注意:傳二維數(shù)組的副本必須給定一行有多少個數(shù),在C語言中,二維數(shù)組在內(nèi)存中以連續(xù)的塊存儲,可以看作是一維數(shù)組的擴展。當傳遞二維數(shù)組作為參數(shù)時,需要提供一行有多少個元素的信息,以便在函數(shù)內(nèi)部正確地進行內(nèi)存訪問。
    二維數(shù)組在內(nèi)存中按行主序(row-major order)存儲。也就是說,二維數(shù)組的每一行依次存儲在內(nèi)存中,并且相鄰的元素在內(nèi)存中也是相鄰的。通過提供一行有多少個元素的信息,可以根據(jù)內(nèi)存布局準確地計算出每個元素的地址,從而進行正確的訪問。
  • 二維數(shù)組不能用二級指針來接收,因為二級指針是指向一級指針的,很明顯,二維數(shù)組的數(shù)組名的類型是第一行即數(shù)組的地址應該用這個int (*)[5]即用數(shù)組指針接收。
  • 二維數(shù)組也不能用指針數(shù)組接收,類型不匹配。

4.3 一級指針傳參

當函數(shù)形參為一級指針時,實參可以是同類型一維數(shù)組數(shù)組名、同類型變量的地址、同類型指針。

  • 請看如下代碼加深理解:
#incldue<stdio.h>
void print(int* p, int sz)
{
    for (int i = 0; i < sz; i++)
    {
        printf("%d ", *(p + i));
        printf("%d ", p[i]);
    }
}
int main()
{
    int arr[5] = { 0,1,2,3,4 };
    int sz = sizeof(arr) / sizeof(arr[0]);
    print(arr, sz);
}
#include<stdio.h>
void test(char *p)
{}
int main()
{
  char ch = 'a';
  char *str = "abcdef";
  char* ptr = &ch; 
  test(str);
  test(&ch);
  test(ptr);
  return 0;
}

4.4 二級指針傳參

當函數(shù)形參為二級指針時,實參可以是一級指針的地址、二級指針。

  • 請看下面代碼,加深理解:
#incldue<stdio.h>
void test(int **ptr)
{
  printf("num = %d\n",**ptr);
}
int main()
{
  int a = 3;
  int* p = &a;
  int **pp = &p;
  test(pp);
  test(&p);
  return 0;
}

5. 函數(shù)指針

函數(shù)指針和數(shù)組指針、字符指針一樣都是指針,只不過指針所指向的對象的類型不同,其中函數(shù)指針與數(shù)組指針最為相似。

5.1 函數(shù)的地址

我們先看下面代碼,函數(shù)名的地址,類比數(shù)組的地址

int Add(int a, int b)
{
	return a + b;
}
int main()
{
    printf("%p\n", &Add);
	printf("%p\n", Add);
	return 0;
}

運行的結(jié)果:
【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft
????????可以看見輸出的是一段地址,這兩個地址都是函數(shù)Add的地址。既然函數(shù)的地址我們知道了,就可以用指針去保存它,我們只需要知道指針指向的對象的類型就行了。

5.2 函數(shù)指針的表示方法

  • *號代表變量是一個指針變量,函數(shù)指針所指向的類型就是函數(shù)聲明去掉變量名和分號后保留的部分,包括返回值和參數(shù)的類型,與數(shù)組指針相似,函數(shù)指針的(*變量名)也要放在函數(shù)名的位置,而數(shù)組指針是放在數(shù)組名的位置。

請看如下代碼:

void test()
{
  printf("i love programming!\n");
}
//除函數(shù)名以外的部分,就是的類型
void (*pf)();//函數(shù)指針,指向一個返回值為void,無參數(shù)的函數(shù)。
void* pf();//表示返回值類型為void*,無參數(shù)的函數(shù)。。
#incldue<stdio.h>
int Add(int a, int b)
{
	return a + b;
}
int main()
{
	int arr[10] = { 0 };
	int(*p)[10] = &arr;//數(shù)組指針
	//int (*)[10]是數(shù)組指針類型
	int(*pf) (int, int) = &Add;
	//int (*)(int,int)是函數(shù)指針類型
	return 0;
}

再給出一組代碼幫助理解:

#include<stdio.h>
int Add(int x, int y)
{
	return x + y;
}
int main()
{
     //&Add和Add都可以
	int (*pf)(int, int) = &Add;
	int (*pf)(int, int) = Add;
	
	int r = Add(3, 5);
	printf("%d\n", r);

	int m = pf(3, 5);
	printf("%d\n", m);
    return 0;
}

運行結(jié)果如下:【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft

  • 函數(shù)指針與數(shù)組指針有相似性,可以對比著去理解。

5.3 兩行有趣的代碼

5.3.1 將0強制轉(zhuǎn)換為函數(shù)指針類型然后調(diào)用

void (*p)() -p是函數(shù)指針
void (*)()  -是函數(shù)指針類型 

(*  (   ( void(*)() )0 ) )();
//(((void(*)())0)是將0強制轉(zhuǎn)換為函數(shù)至真
//(*(函數(shù)指針))是將函數(shù)指針解引用
//然后不傳參數(shù)調(diào)用(*(函數(shù)指針))(); 

【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft

5.3.2 數(shù)組指針、函數(shù)指針等特殊變量類型typedef的使用

#include<stdio.h>
typedef int* ptr_t;//一級指針別名
typedef unsigned int uint;//無符號整形的別名

typedef int(*parr_t)[10];//數(shù)組指針的別名
typedef int (*pf_t)(int, int);//函數(shù)指針的別名
int main()
{
	ptr_t p1;
	uint u2;
	parr_t p2;
	pf_t p3;
}
  • 函數(shù)指針與數(shù)組指針別名的創(chuàng)建與其變量的創(chuàng)建類似,可類比理解。

5.3.3 函數(shù)指針類型的函數(shù)的聲明,并使用別名typedef化簡

請看如下代碼:

   void(* signal ( int, void(*)(int) ) )(int);

解析:
【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft
??????????我們可以觀察到signal函數(shù)的返回類型和其中一個參數(shù)是相同的都是函數(shù)指針類型,下面我們利用別名typedef來使這段代碼看起來更加易懂:

typedef void (*pf_t)(int);
pf_t signal(int,pf_t);

??????????CSDN上的別名沒有高亮,但VS2019里面是有高亮的,定義函數(shù)后,你會發(fā)現(xiàn)編譯器是不會報錯,說明這樣是可行的。
【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft

【C的葵花寶典進階篇】之指針進階(一),C語言進階篇,指針,程序人生,c語言,算法,青少年編程,microsoft文章來源地址http://www.zghlxwxcb.cn/news/detail-535089.html

到了這里,關(guān)于【C的葵花寶典進階篇】之指針進階(一)的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關(guān)文章,希望大家以后多多支持TOY模板網(wǎng)!

本文來自互聯(lián)網(wǎng)用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權(quán),不承擔相關(guān)法律責任。如若轉(zhuǎn)載,請注明出處: 如若內(nèi)容造成侵權(quán)/違法違規(guī)/事實不符,請點擊違法舉報進行投訴反饋,一經(jīng)查實,立即刪除!

領(lǐng)支付寶紅包贊助服務器費用

相關(guān)文章

  • 【運維安全】運維界葵花寶典:Nginx配置與優(yōu)化秘籍

    【運維安全】運維界葵花寶典:Nginx配置與優(yōu)化秘籍

    必要的原理介紹 ● Nginx 里有一個master進程和多個worker進程.master進程并不處理網(wǎng)絡請求,主要負責調(diào)度工作進程: 加載配置,啟動工作進程及非停升級.worker進程負責處理網(wǎng)絡請求與響應. ● master進程主要用來管理worker進程,具體包括如下4個主要功能: 接收來自外界的信號 向各wo

    2024年02月21日
    瀏覽(25)
  • 【程序人生】納瓦爾:確保稀缺性的最簡單的方法就是這個東西來自你的個性 | 納瓦爾寶典

    目錄 納瓦爾簡介 每個人應該找到自己獨一無二的專長 確保稀缺性 產(chǎn)品化的關(guān)鍵點

    2024年02月08日
    瀏覽(21)
  • 【進階C語言】進階指針--學會所有指針類型

    【進階C語言】進階指針--學會所有指針類型

    ?本節(jié)內(nèi)容大致目錄: 1.字符指針 2.指針數(shù)組(數(shù)組) 3.數(shù)組指針 (指針)--比較重要 4.函數(shù)指針--比較重要 5.函數(shù)指針數(shù)組--用的較少 6.指向函數(shù)指針數(shù)組的指針--只需要了解就可以 需要掌握每一種類型的符號和用處。 前言:字符指針是一種指針,是眾多指針類型中的一種。

    2024年02月07日
    瀏覽(22)
  • 『C語言進階』指針進階(一)

    『C語言進階』指針進階(一)

    ?? 博客主頁 : 小羊失眠啦 ?? 系列專欄 : C語言 ??? 每日語錄 : 無論你怎么選,都難免會有遺憾。 ?? 感謝大家點贊??收藏?評論?? 在C語言初階中,我們對指針有了一定的了解,指針是個變量,是用來存放地址的,指針的大小是固定的4/8個字節(jié),指針是有類型的

    2024年02月09日
    瀏覽(27)
  • 『C語言進階』指針進階(二)

    『C語言進階』指針進階(二)

    ?? 博客主頁 : 小羊失眠啦 ?? 系列專欄 : C語言 ??? 每日語錄 : 無論你怎么選,都難免會有遺憾。 ?? 感謝大家點贊??收藏?評論?? 在上篇指針進階中,我們對字符指針、指針數(shù)組、數(shù)組指針以及數(shù)組傳參和指針傳參有了一定的了解,你以為指針進階就只有這些內(nèi)

    2024年02月07日
    瀏覽(22)
  • 【C語言進階】 指針進階(二)

    【C語言進階】 指針進階(二)

    ?? 博客主頁: 小王又困了 ?? 系列專欄: C語言 ?? 人之為學,不日近則日退? ?? 感謝大家點贊??收藏?評論 ?? 目錄 一.函數(shù)指針? 1.1函數(shù)指針的認識 1.2函數(shù)指針的使用 二、函數(shù)指針數(shù)組 1.1函數(shù)指針的認識 1.2 函數(shù)指針數(shù)組實現(xiàn)計算器 ?三、指向函數(shù)指針數(shù)組的指針

    2024年02月15日
    瀏覽(21)
  • 【C語言】指針進階:字符指針&&數(shù)組指針&&函數(shù)指針

    【C語言】指針進階:字符指針&&數(shù)組指針&&函數(shù)指針

    ?作者:@平凡的人1 ?專欄:《C語言從0到1》 ?一句話:凡是過往,皆為序章 ?說明: 過去無可挽回, 未來可以改變 ?? 感謝您的點贊與關(guān)注,同時歡迎各位有空來訪我的 ??平凡舍 回想之前,我們學了 指針 的一些基礎(chǔ)?? 指針與結(jié)構(gòu)體 我們知道了指針的概念: 指針就是

    2023年04月08日
    瀏覽(24)
  • 【C語言進階】指針數(shù)組 —— 數(shù)組指針

    【C語言進階】指針數(shù)組 —— 數(shù)組指針

    ?? 鴿芷咕 : 個人主頁 ??? 個人專欄 : 《C語言進階篇》 《C語言初階篇》 ??生活的理想,就是為了理想的生活! ?? ?? hello! 各位寶子們大家好啊,前面我們已經(jīng)把指針大部分內(nèi)容給學完了,今天就給大家?guī)頂?shù)組指針or指針數(shù)組! ?? ?? 很多說這倆名字不是差不

    2024年02月14日
    瀏覽(19)
  • 進階C語言-指針的進階(中)

    進階C語言-指針的進階(中)

    數(shù)組指針 - 指向數(shù)組的指針 - 存放的是數(shù)組的地址 - 數(shù)組名就是數(shù)組的地址。 函數(shù)指針 - 指向函數(shù)的指針 - 存放的是函數(shù)的地址 - 函數(shù)名就是函數(shù)的地址。 ??閱讀下面這兩段代碼: ?? 指針數(shù)組: 字符指針數(shù)組 - 數(shù)組 - 存放的是字符指針 整型指針數(shù)組 - 數(shù)組 - 存放的是整

    2024年02月09日
    瀏覽(21)
  • 進階C語言-指針的進階(一)

    進階C語言-指針的進階(一)

    通過前面的學習,我們了解了指針的概念: 指針變量就是一個變量,用來存放地址,地址唯一標識一塊內(nèi)存空間。 指針的大小是固定為 4/8 個字節(jié)( 32位平臺/64位平臺 )。 指針是有類型的,指針的類型決定了指針的±整數(shù)的步長,指針解引用操作的時候的權(quán)限。 指針的運算

    2024年02月07日
    瀏覽(26)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領(lǐng)取紅包,優(yōu)惠每天領(lǐng)

二維碼1

領(lǐng)取紅包

二維碼2

領(lǐng)紅包