回覆列表
  • 1 # 素食的貓

    許多年前,七十年代,那時的絕大多數計算機語言,記得陣列大小都必須是用常量定義,那時計算機硬體也就數十K記憶體,數著記憶體個數規劃演算法的年代、哪裡敢想定義“不知道大小的陣列”這類事情去?

  • 2 # 文化歷史精神

    陣列的大小不能用變量表示的,是因為在編譯連線期間記憶體要按照你制定的長度給陣列分配相應的記憶體空間,如果是變數的話就沒有辦法給它分配了,你可以用符號常量來解決,在開頭用:

    # define m 100

    # define n 100 然後在程式中就可以定義u[m][n]二維陣列了,當不一定非要是100,可以是任何一個正整數。

    C語言裡,所有變數空間都是在程式執行之初向系統申請的,包括和指標,它也需要空間,除了一些動態申請方式如malloc函式。沒有申請的空間系統是不允許讀寫的。那麼如果一個數組大小是變數定義,則在程式執行前不能確定陣列大小,也就無法申請,故不允許。解決的辦法如前面所說,如:

    int a[n];

    可改為

    int* const a = (int*)malloc(sizeof(int)*n);

    這樣a變數就完全可以當作一個數組直接使用了,包括a[1]之類的。因為“[]”中括號運算子做的只是偏移其內的地址數並取值。如:

    a[1]

    等價於

    *(a + 1)

    而const修飾符在星號之後,則表示指標在被聲明後不能改變,即只能指向這個獲取的空間,完全符合陣列的性質。

    0 15

    更多回答(9)

  • 3 # 浪漫峨眉峰

    c語言設計之初,程式執行之前所有的儲存空間都必須分配完成,變數是在程式執行過程中會動態改變,因此,程式執行之前無法確定變數大小,所以不是不建議,是不能用變數定義陣列大小。

  • 4 # TonyDeng

    你這個是C語言裡經典的“可變陣列”問題,無論是什麼平臺的C編譯器,包括C++編譯器,都是不推薦的。

    但很特殊,GCC編譯器有獨特擴充套件,支援偽可變陣列,就是你希望的那樣,可以定義int arr[x]這樣的陣列,此時,變數x未知具體數値,但編譯器在編譯時允許透過,在執行時,取得x的動態値,才在中分配這個陣列。注意:跟原本的陣列一樣,這種形式的陣列也一樣在棧中分配,此時分配的陣列尺寸不再可變,跟預定義常量尺寸的陣列是一樣的,衹不過這是“延遲”分配而已。看起來這是人們所希望的“可變陣列”,但實際上不是,真的不是,因為你不能再一次改變它的容量。實際上,這種陣列使用方式隱藏一個很危險的坑,就是會很容易超過棧的大小,盡管GCC多數在Linux系統上程式設計,有4M的棧空間,但不注意的話,也一樣會爆棧。

    經典而且正規的用法,是在堆上使用可變陣列!由於已經有這個規範的解決方案,所以C語言本身不建議這樣做,GCC搞這個很得學院派學生的讚歎,然而我真的不以為然。

    本質上,C型別的陣列,在C++或別的語言,如C#或java中,都不建議再使用了,這些語言推薦的替代型別是vector或List,是兼顧效率和可變性的動態分配資料型別,比傳統的C陣列好用得多,就是可以把變數作為長度,還隨時可變。

    C型別陣列之所以難以變化的根本原因,就是它類似房屋,只能建一次,要改變房屋大小,要麼拆掉重建,或者另外找空地重建,這些動作都是要花費的——C#/java字串是隻讀的也是因此。棧的綫性使用法則,不容許分配過之後再去改變尺寸,堆可以,那是另外新建,因為堆上找空地容易得多,但C語言上realloc()之前,必須記得把原先malloc()的空間free()掉,原先的房屋不拆,就是霸佔資源的記憶體洩露,還要告訴所有指向原先地址的指標指向新地址(這個才是要命的)。指標雖好用,風險須謹記!

  • 中秋節和大豐收的關聯?
  • 為何有人認為錢易賺,易在哪兒?而有些人認為錢難賺,難在何處?