C 語言程序設計---指針

2021-02-19 編程劍譜


我應該比大多數讀者年齡都要大一些,所以我就自稱」譜哥「,做事靠譜,為人靠譜的意思;針對 C 語言三大核心:數組、指針、函數,今天繼續寫技術文章。

上次 C 語言寫到了數組,有些書是先講指針,有些書是先講函數,按照我以前學習 C 語言的順序,以及對 C 語言的理解,學習的順序是這樣的:數組--->指針--->函數,所以本篇文章講解 C 之指針。

C 語言是值得好好學習的一門語言,是一門基礎語言,更是我編程入門的語言,其中很多編程思想,至今影響著我,在工作中對我的幫助很大。

基本概念

學習 C 語言之指針,必須強烈推薦一本書:《C 和指針》,好好看,把這本書吃透,C 指針就差不多了。

1、

指針有兩個要素

(1)、首地址:內存中多個連續字節的第一個字節的編號;在 32 位系統下,每個字節的編號都是 32 位二進位,也就是 4B,任何類型的指針都只佔 4B 的存儲空間。

1char *a;         char*        a;
2short *b;        short*       b;
3int *c;          int*         c;
4double *d;       double*      d;
5
6printf("%d %d %d %d\n", sizeof(a), sizeof(b), sizeof(c), sizeof(d));
7

(2)、指針所指向空間的數據類型:以指針的值為首地址,其所指向的空間的數據類型。

2、

指針類與值類

我們之前學習過的各種數據類型:int、float 等等都統稱為值類。

指針類和值類不能簡單的適用以前所講述的語法,例如:自動類型轉換和強制類型轉換是不適用指針類的。

3、

指針的基本運算

& 和 *

A、

&:取地址運算符,單目運算符,優先級在單目運算符中比較低,低於 ++、--。

&左值(左值只能是空間、變量),取的是內存的地址。

&常量和&表達式是語法錯誤的。

B、

1short i, j, *p, *q, **r;
2
3
4
5
6
7
8
9

C、

* 運算符

單目運算符,與 & 優先級相同,且和 & 互為逆運算(連續的兩個 & 和 * 運算符在一起,相互抵消),例如:*&n <=> n、&*p <=> p。

語法:*指針(常量、變量、表達式)

1short i, j, *p, *q, **r;
2p = &i;
3q = &j;
4*p = 30; 
5*q = *p + 15; 

*某的理解:

(1)、其在左邊,理解為:某所指向的空間;

(2)、其在表達式中,理解為:某所指向的空間的值。

1short i, j, *p, *q, **r;
2p = &i;
3q = &j;
4r = &p;
5*p = **r + *q; 

4、

指針定義的理解

A、

1char i, j, *p = &i, *q = &j, **r = &p;
2

B、

double *p;

*p = 3.14;

對於上述語句的理解,是至關重要的。

上述語句會引起:運行時致命錯誤!!!

變量 p 定義為指針變量,佔用 4B,但是沒有初始化(沒有賦初值),其值為垃圾數據;

*p = 3.14; 的意思是:將 3.14 賦值給 p 所指向的空間,也就是將 3.14 賦值給「以 p 的值作為首地址」,該首地址所指向的空間;

綜上所述:將 3.14 賦值給以垃圾值為首地址,所指向的空間,這個空間在哪裡,只有鬼知道!這個垃圾值的取值範圍在 0 到 40 億之間,若落在當前軟體申請的空間範圍內,則相安無事;否則,這個操作(*p = 3.14;),將對不屬於本軟體所申請的空間進行操作,被作業系統認為是「非法訪問」,作業系統將強行終止這個軟體的執行!

5、

指針的其他運算(主要是指針的加減運算)

指針加/減整型值,其結果是一個指針,且指向空間的類型不變。

A、

指針加/減整型

P + 1:所得到的還是指針,將會指向 P 所指向空間的下一個地址(到下一個地址移動的長度是指向空間數據類型的長度)。

指針 +1 所得到的「字節編號」的值。與指針原值(原字節編號)相差sizeof(所指向空間的數據類型)。

指針 +n 的值與指針原值相差 n 倍的 sizeof(所指向空間的數據類型)

B、

指針減指針  => int 類型

指針減指針,其結果的絕對值是:兩指針所指向的空間之間 sizeof(數據類型) 元素的個數。

參加指針相減運算的兩個指針,其指向空間的數據類型必須一致!

實質上,指針相減的內部運算過程是:兩指針值(字節編號)相減,再除以 sizeof(所指向空間的數據類型)

指針不能加指針,會出現語法錯誤!

總結:指針 + 1 或者 -1,指針移動的步長:是指向空間數據類型的長度(這個長度是通過 sizeof() 可以計算的)。

指針與數組

1、

指針與一維數組

int a[10];

數組名稱的本質:是該數組的首地址常量。

A、數組名稱是常量

1int a[10], *p = &a[0];
2++a; 
3++p; 

B、

數組名稱是首地址(指針),可以參加指針能夠參與的所有運算。

1*a = 3; 
2*(a+0) = 3; <=> a[0] = 3;
3*(a+1) = 3; <=> a[1] = 3;
4*(a+2) = 3; <=> a[2] = 3;

int i; //且其取值在有效下標範圍內:

*(a+i) = 3; <=> a[i] = 3;

得到了指針與數組的本質:

a[i] <=> *(a+i)

表象           本質

2、

指針與二維數組

指針與二維數組在理解上是比較難的,只有理解了指針與二維數組,那麼指針與多維數組,三階指針、四階指針、五階指針、直至多階指針,一維數組,二維數組,三維數組,直至多維數組,在理解上就都不是問題了,挖掘本質,才能更清楚的認識。

指針與二維數組屬於指針的高級進階,後面有時間在分享這塊的知識點。

指針與字符串

1、

"ABCDE" //字符串常量

字符串常量的本質:是該字符串的首地址常量,即指針常量。

1char *p = "I love you";
2
3p = "Hello";
4printf("%s\n", p);
5p[2] = 'm';  

2、

字符串常量的本質是指針常量,可以參加指針所能夠參加的所有運算。

因此:

字符串常量可以進行 * 和 [] 的運算;

字符串常量不能相加;(指針是不能相加的);

字符串常量的關係運算符(大小比較),實質上比較的是它們的內存首地址的大小比較,而非字符串內容(ASCII碼)的大小比較。

字符串常量不能更改其內容。

字符串的本質是字符數組,數組名稱的本質依然是指針常量;

所以,以上結論依然適用於字符串!

3、

字符串類處理函數

A、

string.h

對於 scanf("%s"...) 和 gets() 的理解

strlen() 函數的工作原理:

C 語言將其唯一的參數當成首地址,從這個首地址所指向的空間開始,統計所有字符的個數,直到遇到0(結束標誌)。

B、

字符串輸入、輸出函數

輸入:scanf("%s", ...)、gets(...)

輸出:printf("%s", ...)、puts(...)

C、

strcpy()

聲明:char *strcpy(char *target, char *source);

功能:將後者字符串,賦值給前者:將以第二個參數的值為首地址所指向的字節開始的「遇零則止」的字符,複製一份,賦值給第一個參數的值為首地址所指向的字節開始向後的連續存儲空間中;該函數的返回值,就是第一個參數的值。

D、

strcat()

聲明:char *strcat(char *, char *);

功能:字符串連接,將第二個參數所指向的字符串,連接到第一個參數所指字符串的末尾。

E、

strstr()/strchr()

聲明:char *strstr(char *string, char *subString);  

//subString意思為:子串

功能:查找 subString 第一次出現的地址值,若 subString 不是 string 的子串,則返回 NULL。

F、

strcmp()

聲明:int strcmp(char *s1, char *s2);

功能:比較 s1 和 s2 所指向的字符串的內容;

若 s1 字符串內容小於 s2 字符串內容,則返回值為負整數;

若 s1 字符串內容大於 s2 字符串內容,則返回值為正整數;

若二者內容相等,則返回為0。

G、

strrev()

聲明:char *strrev(char *);

功能:將字符串逆序。

這篇文章僅僅是 C 語言指針的入門篇,看完之後,不知道大家能理解多少,學到多少;根據這篇文章的線路,去學習 C 指針,會清晰很多,只有多思考,才能消化吸收,才能理解。

推薦閱讀:

在 BAT 實習期間,無出其右的戰略打法!!!

我的 2018 年終總結

認真的人 自帶光芒

相關焦點

  • c語言程序設計自學教程
    如果您不甘落後,那麼請自製自控,自學c語言程序設計也是完全可能的。c語言十分依賴於計算機思維,而思維的培養不是一日之功,而是一個日積月累的過程一:準確把握語法語句概念1、編譯預處理不是C語言的一部分,不佔運行時間,不要加分號。
  • C語言程序設計 | 教與學(教學大綱)
    章節學習目標理論課時上機課時建議第1章面向計算思維的C語言程序設計上機實踐l了解計算思維;l了解面向計算思維的C程序設計實踐內容設計;l了解面向計算思維的C程序設計上機實踐過程。1第2章      Visual  Studio 2010環境下C語言程序設計與調試l熟悉C語言程序的開發步驟;l熟悉Visual Studio 2010安裝及運行;l熟悉一個簡單的「Hello World」程序的編寫與調試過程。
  • C 語言程序設計---入門篇
    從本篇文章開始,我將分享 C 系列,將 C 語言的方方面面,從最基礎的語法帶領大家入門
  • c語言50本電子書
    .pdfC語言之父《C程序設計語言(中文版)》(第2版).pdfC語言從初學到精通.pdfC語言函數手冊.PDFC語言各章節知識點總結.pdfC語言常見問題集.pdfC語言開發從入門到精通.pdfC語言深度剖析.pdfC語言程序設計 李健 文字版.pdfC語言程序設計(第四版
  • C語言程序設計試題1
    學年期末考試級專業()《C語言程序設計f;,將數學表達式C= (F-32)能正確表示成C語言賦值表達式的是(   ) A.c=5*(f-32)/9 B.c=5/9(f-32) C.c=5/9*(f-32) D.c=5/(9*(f-32))6.設int i=10;,表達式30-i<=i<=9的值是(   )A.0 B.1
  • c語言指針與字符數組
    ,字符串的使用在C語言中也是非常重要的,常常會遇到一些操作,如字符串的修改、拷貝、字符串長度等,在物聯網的應用中也尤為突出,物聯網應用中所用的模組,大多是需要使用AT指令的,這就需要對字符串的操作。我們定義一個指針變量char * pc;內存示意,通常指針是4個字節,假設這裡的地址是200
  • 2019年武漢紡織大學專升本《C語言程序設計》詳細考試大綱
    [導讀]湖北湖北普通專升本網權威發布《2019年武漢紡織大學專升本《C語言程序設計》詳細考試大綱》,由胡老師整理髮布,更多2019年武漢紡織大學專升本《C語言程序設計》詳細考試大綱
  • C++語言程序設計
    基於上述考慮,本課程雖然內容主要為C語言程序設計,但還是涉及了一部分C++的內容。本課程以實打實提高學生的實際編程能力為目標,只要能寫出好程序,用的是C語言還是C++語言,並不重要。主要為以下三部分:1) 11 周: C語言程序設計2) 2  周:用C++的STL(標準模板庫)輕鬆實現高效的排序和查找。這部分內容雖不多,但對於提高編寫程序的效率極其有用。
  • C語言程序設計試題3
    學年期末考試級專業()《C語言程序設計C程序在作邏輯運算時判斷操作數真、假的表述中,正確的是(   )A.0為假,非0為真 B.只有1為真 C.-1為假,1為真 D.0為真,非0為假5.若p1、p2都是指向整型的指針,p1已經指向數量x,要使p2也指向x,正確的是(   )A.p2=p1; B.p2=**p1; C.p2=&
  • 為什麼指針被譽為 C 語言靈魂?
    所以,要想徹底理解指針,首先要理解 C 語言中變量的存儲本質,也就是內存。在 C 語言中我們會這樣定義變量:int a = 999;char c = 'c';當你寫下一個變量定義的時候,實際上是向內存申請了一塊空間來存放你的變量。
  • c語言程序設計是什麼概念?及其作用與產生原因
    c語言程序設計什麼是c語言程序設計?它的作用是什麼?因為什麼而產生?首先,c語言是一門計算機高級語言,就是除了0011101這樣的二進位代碼這些基本語言外。人類用適合自己一般邏輯的方便的,字符,詞組,字母等等來設計的語言。
  • C語言簡明教程(九)指針(二)
    通過改變指針變量的值使它指向字符串中的不同字符。編寫程序 11-3.c 用 i++ 來遍歷數組,程序 11-4.c 用 p++ 遍歷數組。解題思路:定義一個函數 copy_string 用來實現字符串複製的功能,在主函數中調用此函數,函數的形參和實參可以分別用字符數組名或字符指針變量。分別編程,以供分析比較。編寫程序 11-5.c 用字符數組名作為函數參數,程序 11-6.c 用字符型指針變量作實參,程序 11-7.c 用字符指針變量作形參和實參。
  • 《電腦程式設計基礎(C語言)》通用
    《電腦程式設計基礎(C語言)》通用單項選擇練習題說明:帶*號的對非信息學院的同學不作要求。已定義c為字符型變量,則下列語句中正確的是 ( C )    A)c='97'     B)c="97"     C)c=『a』     D)c="a" 20.
  • C語言指針詳解
    先聲明幾個指針放著做例子:例一:(1)int *ptr;(2)char *ptr;(3)int **ptr;(4)int (*ptr)[3];(5)int *(*ptr)[4];如果看不懂後幾個例子的話,請參閱我前段時間貼出的文章 如何理解c和c++的複雜類型聲明>&
  • 2018年自考《C語言程序設計》試題七
    2018年自考《C語言程序設計》試題七二、 閱讀程序題閱讀程序對於初學者來說很重要,一方面可以鞏固所學的語法知識,另一方面通過閱讀別人寫好的程序來打開自己的思路,就所謂見多識廣。如果選擇有誤,就要認真分析原因,是概念方面的錯誤還是對程序邏輯理解不對,從而加深對語法規則的理解,提高程序設計能力。程序設計語言是開發程序的一個工具,學習語言的目的是為了編寫程序來解決實際問題,所以特別提倡通過實際上機來檢驗備選答案,增強動手能力。1.下面程序的輸出結果是____。
  • c語言的指針真的很有趣
    指針是一個很有趣的東西,想要成為一個出色的程式設計師,那麼指針就要學的好,指針涉及到內存分配的問題。每一個變量都有自己的內存,可以使用&來訪問變量存儲的位置。ta就是一個地址。這語句中用*來指定指針變量int *ip; /* 一個整型的指針 */double *dp; /* 一個 double 型的指針 */float *fp; /* 一個浮點型的指針 */
  • C語言陷阱與技巧31節,都說void*指針是「萬能指針」,它萬能在哪
    (void *dest, constvoid *src, size_t n);void *memmove(void *dest, constvoid *src, size_t n);前面的章節在討論C語言指針時,提到指針從某種程度上來說,無非就是一個地址,它的類型只是用於說明數據結構的。
  • 五邑大學2020年本科插班生專業課《C語言程序設計》考試大綱
    總體要求:考生應按本大綱的要求了解或理解「C語言程序設計」中的數據類型、運算符與表達式、順序結構、選擇結構、循環控制、數組、函數、指針、預處理命令、結構體與共用體、文件的基本概念。熟練掌握程序設計的基本方法和C語言本身的語法、語句和使用方法。
  • C 語言指針詳解
    指針pp為指向指針p的指針定義指針變量C語言中,定義變量時,在變量名 前 寫一個 * 星號,這個變量就變成了對應變量類型的指針變量。必要時要加( ) 來避免優先級的問題。引申:C語言中,定義變量時,在定義的最前面寫上typedef ,那麼這個變量名就成了一種類型,即這個類型的同義詞。
  • 安徽大學《C語言程序設計》 期末試題 兩份
    安徽大學20   -20   學年第   學期《C語言程序設計    B)若a<b且c=d,則x=1;若a>=b,則x=2。    C)若a<b且c=d,則x=1;若a<b且c!=d,則x=2。D)若a<b且c=d,則x=1;若c!=d,則x=2。  6.下列程序段的執行結果是______。