為什麼這篇為什麼要用指標鄉民發文收入到精華區:因為在為什麼要用指標這個討論話題中,有許多相關的文章在討論,這篇最有參考價值!作者Feis (坐吃山空)看板C_and_CPP標題Re: [問題] 自己練習運用基礎的指標小問題時...
為什麼要用指標 在 陳小洛?裏科變態 Instagram 的最佳解答
2021-09-24 13:47:41
G點在性愛中令許多人好奇 過去我也是上網看介紹 但無論是用公分來做指標 或是講陰道內比較粗糙的那區 我還是不太能意會 後來我自己摸索的過程 找到了另一種尋找方式 也許你也可以參考看看 G點(G-Spot)是什麼? 他是陰道周圍的敏感帶之一 由德國醫學家Gräfenberg發現...
※ 引述《M013020058 (帥翰)》之銘言:
: 非常感謝先進的分析
: 目前初學者小弟我為指標分類為下,並提出幾個疑惑的地方。
: 1, 很多書籍都透過變數位址來修改/定義變數資料,但今天不是直接修改/定義變數資料
: 就好?為什麼要繞一圈?
誠如之前所提到的,主要有兩個方向,一個是你不用指標做不到,另一個是這樣做可能
比較快。
後者牽涉到的問題比較多,而且也不是主要的用途,所以我講一下前者。
首先我們知道,在 C 裡面你要存取某個物件/變數的值的時候,
你有兩種方法,一個是你要寫出他的名字,另一個是你要知道他的位址:
方法一: 使用名字
int main() {
int a = 3;
a = 5; // 透過名字去修改變數內容
// 此時 a 的值是 5
return 0;
}
方法二: 使用位址
int main() {
int a = 3;
int *b = &a;
*b = 5; // 透過位址去修改變數內容
// 此時 a 的值是 5
return 0;
}
上述兩種方法都可以達到修改變數 a 內容的效果,而一般的時候我們會建議使用前者,
因為後者看起來就是繞了一圈不知道在幹嘛。
那後者甚麼時候有用呢 ?
最常見的就是在函式呼叫的時候:
void f(int b) {
b = 5;
}
int main() {
int a = 3;
f(a);
// 此時 a 是 3 還是 5 ?
return 0;
}
初學者如果在學習函式的時候沒有對引數傳遞和可視範圍 (scope) 有比較清楚的了解,
那這個例子可能就弄不清楚應該是 3 或是 5
在呼叫完 f(a) 之後,main 裡面的 a 應該還是 3,他不會受到 f 的影響。
這可以從很多面向來解釋,首先呼叫函式的時候,a 會被複製一份變成 f 裡面的 b,
所以 b = 5 修改的是一個複製品,無法修改到原始的變數 a。
那如果我們把 b = 5 改成 a = 5 呢 ?
void f(int a) {
a = 5;
}
結果還是一樣沒用,而 f 裡面的 a 只是一個剛好同名同姓的複製品。
f 函式的定義是在 main 裡面的 a 的可視範圍外,所以是無法用變數名字直接去存取
main 裡面的 a。
此時我們可以使用指標來逃過可視範圍的限制,透過 "位址" 來修改變數內容:
void f(int *b) {
*b = 5;
}
int main() {
int a = 3;
f(&a);
// 此時 a 是 5
return 0;
}
為什麼這裡要特別傳遞指標呢? 就是希望 f 裡面可以透過 "位址" 去存取 main 裡面
的 a 。因為位址是個 "值",是可以複製到 f 裡面的,沒有跟名字一樣有可視範圍限
制。
還有甚麼時候我們可能會需要位址而不能用名字去存取呢 ?
我舉個簡化的例子:
int main() {
int a = 3;
int b = 5;
int c = 9;
int d = 4;
// 可能因為某些原因,我們當初沒有宣告陣列而是使用四個獨立的變數名字
// 如果現在我想要用迴圈去批次處理這些變數怎麼辦 ?
int* t[] = {&a, &b, &c, &d}; // 我們可以使用陣列去存變數位址
for (int i = 0; i < 4; i++) { // 此時就可以使用迴圈去依序存取不同名字的變數
f(t[i]);
}
return 0;
}
: 2,同上,是否是為了讀寫檔案所建立指標功能?
不全然是,讀寫檔案只是指標的一種應用。
因為讀寫檔案的時候是使用函式傳遞、生命週期與可視範圍脫鉤、檔案大小不固定、存
取有效能考量等等,用指標去操作是比較可能的設計。
: 3,以矩陣為例,可用指標來取代矩陣。而兩種在記憶體上或其他地方哪裏不一樣?
你可能有甚麼誤會
指標跟陣列的愛恨情仇有兩個主要的問題:
一個是常見的存取問題,指標可以用來存取所指向的陣列元素。
實際上照 C 的陣列設計,所有陣列的存取都是透過指標。
其實沒有甚麼取不取代的問題。
只是當你要在函式間傳遞陣列的時候,因為 C 函式無法直接傳遞陣列型別的物件,
所以你只能透過傳遞指標去存取。
另一個問題是空間配置問題,
陣列的大小如果是編譯期已知,我們可以透過變數定義來配置:
int a[10];
但是如果在編譯期還不知道的話,我們就需要透過動態配置:
int size;
scanf("%d", &size);
int *a = (int *) malloc(size *sizeof(int));
(C++ 或 C99 後有其他作法)
(註: 有些時候因為編譯器的限制,在函式內能配置的陣列大小會受到限制,
此時也有可能改用後者來動態配置或者改為全域變數。)
所以實際上需要考量的是空間配置問題,看你是屬於哪一種就用哪一個。
: 4, 最後,指標能有一般變數沒有的「動態」功能,所以才需要指標?
不知道動態功能是甚麼意思 ?
: 在指標上的學習,小弟我一直在想這幾個問題?為何需要指標?每本書籍都把指標列為程
: 式碼重要的地方,無法理解~~~~~
因為你寫太少練習,簡單說就是如果你不需要用就可以把程式寫好,看起來程式碼又沒有
亂七八糟。那就不要用指標。
初學者與其練習怎麼用,不如先練習不要用怎麼寫 ?
PS:
我常開玩笑說,如果你完全不要用函式,那你大概就快不需要用指標了。
但是你要怎麼不用函式呢 @@
了解函式呼叫的運作與限制是使用指標一個很重要的基礎
--
※ 發信站: 批踢踢實業坊(ptt.cc), 來自: 140.122.83.198
※ 文章網址: https://www.ptt.cc/bbs/C_and_CPP/M.1438725786.A.D8F.html