C語言由淺入深理解指針
1. 相關(guān)概念
- 操作系統(tǒng)給每個存儲單元分配了一個編號,從ox00 00 00 00~0xff ff ff ff,這個編號稱為地址,指針就是地址
- 指針變量:即這個變量用來存放一個地址編號
- 無論什么類型的地址,都是存儲單元的變換,在32位平臺下都是4個字節(jié),即任何類型的指針變量都是4個字節(jié)大小,64位操作系統(tǒng)占8個字節(jié)。
- 對應(yīng)類型的指針變量,只能存放對應(yīng)類型的地址。例如整型指針變量,只能存放整型變量的地址。
#include <stdio.h> int main() { char *a; short *b; int *c; long *d; float *e; double *f; printf("sizeof(a)=%d\n", sizeof(a)); printf("sizeof(b)=%d\n", sizeof(b)); printf("sizeof(c)=%d\n", sizeof(c)); printf("sizeof(d)=%d\n", sizeof(d)); printf("sizeof(e)=%d\n", sizeof(e)); printf("sizeof(f)=%d\n", sizeof(f)); return 0; }
可見,我的操作系統(tǒng)是64位的。
為什么在64位系統(tǒng)中指針的大小是8,而32位的卻是4?
64位系統(tǒng),這個位數(shù)指的是CPU 里面的通用寄存器的數(shù)據(jù)寬度為64位,也就是說一個地址占二進制位數(shù)是64,所以:
sizeof(double *)==sizeof(int *)==sizeof(char *)==64/8==8
32位系統(tǒng),同理,他的一個地址占32位二進制空間,sizeof(double *)==sizeof(int *)==sizeof(char *)==32/8==4
其實明白了兩個系統(tǒng)的尋址原理就能明白,大體就是這個原因。地址跟系統(tǒng)有關(guān),但是基本數(shù)據(jù)類型占的大小是由C語言本身決定。
2. 指針的定義方法
數(shù)據(jù)類型 *指針變量名
int p; // 定義了一個指針變量p 在定義指針變量的時候, 是用來修飾變量的,代表指針變量。
關(guān)于指針的運算符:
& 取地址 * 取值
#include <stdio.h> int main() { int a = 100; int *p; // 定義一個指針變量 p = &a; // 給指針變量賦值 printf("a = %d, %d\n", a, *p); // *p 等價于變量 a return 0; }
拓展:如果一行中定義多個指針變量,每個變量前面都要加*修飾
3. 指針的分類
- 字符指針
- 短整型指針
- 整型指針
- 長整型指針
- float型指針
- double型指針
- 函數(shù)指針
- 結(jié)構(gòu)體指針
- 指針的指針
- 數(shù)組的指針
4. 指針和變量的關(guān)系
引用變量的方法:
1.直接通過變量的名稱
2.通過*指針名稱 引用
#include <stdio.h> int main() { int *p1, *p2, temp, a, b; p1 = &a; p2 = &b; printf("請輸入a,b的值:\n"); scanf("%d %d", p1, p2); // 和之前的scanf不同,這里直接用p1p2作為寫入地址。 temp = *p1; // 用p1指向的變量a給temp賦值 *p1 = *p2; // 用p2指向的變量b給p1指向的變量a賦值 *p2 = temp; // temp給p2指向的變量b賦值 printf("a=%d b=%d\n", a, b); printf("*p1=%d,*p2=%d\n", *p1, *p2); return 0; }
如果想讓不同類型的指針相互賦值的時候,需要強制類型轉(zhuǎn)換:
#include <stdio.h> int main() { int a = 0x1234, b = 0x5678; // 4個字節(jié) char *p1, *p2; // char類型只能保存一個字節(jié) printf("%#x %#x\n", a, b); p1 = (char *)&a; // 強制類型轉(zhuǎn)換 p2 = (char *)&b; printf("%#x %#x\n", *p1, *p2); p1++; // 指針向上移動 p2++; printf("%#x %#x\n", *p1, *p2); return 0; }
5. 指針與數(shù)組的關(guān)系
指針保存的是數(shù)組第一個元素的地址
也可以通過*(p+2)=100給當(dāng)前地址的下一個變量賦值
#include<stdio.h> int main(){ int a[5] = {0,1,2,3,4}; int *p; p = a; // 指針指向數(shù)組a的第一個元素的首地址 printf("a[2]=%d\n",a[2]); printf("p[2]=%d\n",p[2]); // *(a+n) <==> *(p+n) <==> a[n] <==> p[n] printf("*(p+2)%d\n",*(p+2)); printf("*(a+2)%d\n",*(a+2)); printf("p=%p\n",p); printf("p+2=%p\n",p+2); return 0; }
6. 指針的運算
指針可以加一個整數(shù),往下指幾個它指向的變量,結(jié)果還是地址
#include <stdio.h> void test1() { int a[10]; int *p, *q; p = a; q = p + 2; // p q 間隔8個字節(jié),意味著加一個整數(shù)最終移動的字節(jié)數(shù)與指針變量的類型也有關(guān)系 printf("p=%p\n", p); printf("q=%p\n", q); return; } int main() { test1(); return 0; }
- 兩個相同的指針可以比較大小
前提:指向同一個數(shù)組的元素
#include <stdio.h> void test2() { int a[10]; int *p, *q; p = &a[1]; q = &a[6]; if (p < q) { printf("p < q\n"); } else if (p > q) { printf("p > q\n"); } else { printf("p = q\n"); } return; } int main() { // test1(); test2(); return 0; }
- 兩個同類型的指針可以做減法
前提:指向同一個數(shù)組元素,減法的結(jié)果是指針指向的中間有多少個元素
#include <stdio.h> void test3() { int a[10]; int *p, *q; p = &a[0]; q = &a[3]; printf("%ld\n", q - p); return ; } int main() { // test1(); // test2(); test3(); return 0; }
- 兩個相同類型的指針可以相互賦值
#include <stdio.h> void test4() { int a = 100; int *p, *q; p = &a; printf("a=%d %d\n", a, *p); q = p; printf("*q=%d\n", *q); *q = 999; printf("a=%d\n", a); } int main() { // test1(); // test2(); // test3(); test4(); return 0; }
到此這篇關(guān)于C語言由淺入深理解指針的文章就介紹到這了,更多相關(guān)C語言指針內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
淺析C/C++中的可變參數(shù)與默認(rèn)參數(shù)
C支持可變參數(shù)的函數(shù),這里的意思是C支持函數(shù)帶有可變數(shù)量的參數(shù),最常見的例子就是我們十分熟悉的printf()系列函數(shù)。我們還知道在函數(shù)調(diào)用時參數(shù)是自右向左壓棧的2013-09-09使用Objective-C獲取IPHONE手機IMSI序列號
這篇文章主要介紹了使用Objective-C獲取IPHONE手機IMSI序列號的方法以及通過IMSI序列號獲取運營商、手機號的方法,非常的實用,有需要的小伙伴可以參考下。2015-04-04Windows配置VSCode+CMake+Ninja+Boost.Test的C++開發(fā)環(huán)境(教程詳解)
這篇文章主要介紹了Windows配置VSCode+CMake+Ninja+Boost.Test的C++開發(fā)環(huán)境,本文通過圖文并茂的形式給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下2020-05-05深入探討linux下進程的最大線程數(shù)、進程最大數(shù)、進程打開的文件數(shù)
本篇文章是對linux下進程的最大線程數(shù)、進程最大數(shù)、進程打開的文件數(shù)進行了詳細(xì)的分析介紹,需要的朋友參考下2013-05-05