2008-10-02 40 views
3
使用具有多維動態數組長度()

我使用在Delphi多維動態數組,我試圖算出這個:在Delphi

我有2個單獨的值的第一索引和第二索引完全彼此分開。

隨着新值的增加,我希望增長數組,如果新值超出任何一個邊界。

對於新值x,y

我檢查:

if Length(List) < (x + 1) then 
    SetLength(List, x + 1); 
if Length(List[0]) < (y + 1) then 
    SetLength(List, Length(List), y + 1); 

這是做到這一點的正確方式或是否有更好的方式生長所需的陣列?

回答

2

我想你忘了使用第二個索引第二維度;不斷增長的第二個維度時

if Length(List) < (x + 1) then 
    SetLength(List, x + 1); 
if Length(List[x]) < (y + 1) then 
    SetLength(List[x], y + 1); 

的使用注意事項的「X」作爲第一個維度指數:

您的代碼也許應該這樣寫的。

一個警告,雖然:

你應該知道的是Delphi使用動態數組引用計數太(就像它是如何與AnsiString類型來完成的)事實。 正因爲如此,像上面這樣增長的陣列才能正常工作,但是任何其他的參考仍然會有舊的副本!

解決這個問題的唯一方法就是跟蹤這些數組的一個額外級別的間接 - 即。 :使用指向動態數組的指針(它本身也是一個指針,但沒關係)。

還要注意的是任何那些「外部」指針的應該在於動態數組的地址可能會改變,生長時/使用SetLength收縮它()作爲任何情況進行更新。

+1

如果要創建不規則數組 - 即不同索引具有不同子維長度的數組,則只需在子維上調用SetLength(即SetLength(List [X],...))。 另外,這將創建二維數組插入List [x](希望編譯器會抱怨)。 – gabr 2008-10-03 06:44:04

4

它看起來好像沒什麼問題 - 如果你改變了最後一行

SetLength(List, Length(List), y + 1); 
+0

可能是這個問題被編輯了,但是你的代碼示例與問題的最後一行沒有什麼不同! – PatrickvL 2008-10-03 05:59:04

+0

是的,這個問題已被編輯,您可以通過點擊問題底部「編輯」文本右側的鏈接來​​檢查修改。 – gabr 2008-10-03 06:44:40

1

@PatrickvL: 對不起,但那是錯誤的。你的代碼甚至不會編譯,因爲它試圖爲一維元素List [x]設置兩個維度。(PatrickvL更新了他的代碼,因此這部分答案不再有效。)

以下代碼演示了多維數組調整大小。

program TestDimensions;

{$APPTYPE CONSOLE} 

uses 
    SysUtils; 

var 
    List: array of array of integer; 

begin 
    //set both dimensions 
    SetLength(List, 3, 2); 
    Writeln('X = ', Length(List), ', Y = ', Length(List[0])); //X = 3, Y = 2 
    //set main dimension to 4, keep subdimension untouched 
    SetLength(List, 4); 
    Writeln('X = ', Length(List), ', Y = ', Length(List[0])); //X = 4, Y = 2 
    //set subdimension to 3, keep main dimenstion untouched 
    SetLength(List, Length(List), 3); 
    Writeln('X = ', Length(List), ', Y = ', Length(List[0])); //X = 4, Y = 3 
    //all List[0]..List[3] have 3 elements 
    Writeln(Length(List[0]), Length(List[1]), Length(List[2]), Length(List[3])); //3333 
    //you can change subdimension for each List[] vector 
    SetLength(List[0], 1); 
    SetLength(List[3], 7); 
    //List is now a ragged array 
    Writeln(Length(List[0]), Length(List[1]), Length(List[2]), Length(List[3])); //1337 
    //this does not even compile because it tries to set dimension that does not exist! 
// SetLength(List[0], Length(List[0]), 12); 
    Readln; 
end. 

德爾福的幫助也很好地解釋了這一點(結構類型,數組)。

多維動態數組 要聲明多維動態數組,請使用...構造的迭代數組。例如,

類型TMessageGrid =字符串數組的數組;
var Msgs:TMessageGrid;

聲明一個字符串的二維數組。要實例化這個數組,用兩個整數參數調用SetLength。例如,如果I 和J是整數值變量,則可以使用下列公式中的一個或多個:其中,

分配一個I-by-J數組,Msgs [0,0]表示該數組的一個元素。您可以創建不是矩形的多維動態數組。第一步是調用SetLength,爲數組的前n個維傳遞參數。例如,

var Ints:Integer數組的數組;
SetLength(Ints,10);

爲Ints分配10行,但不分欄。稍後,您可以一次分配一列(給它們不同的長度);例如

SetLength(Ints [2],5);

使第三列Ints五個整數長。此時(即使其他列尚未分配),您可以將值分配給第三列 - 例如,Ints [2,4]:= 6.

以下示例使用動態數組(和在SysUtils單元中聲明的IntToStr函數)創建一個三角形的字符串矩陣。 A:數組的字符串數組;數組的數組;
I,J:Integer;
begin
SetLength(A,10); (A)爲高(A)
開始
SetLength(A [I],I);對於J:=低(A [I])至高(A [I])來說,可以使用以下公式來計算:其中J:=低(A [I])至高(A [I])
A [I,J]:= IntToStr(I)+'
end;
end;