2014-01-16 69 views
2

我有一些我從未見過的東西。調試時不會出現在本地變量窗口中的局部變量。我附上了一張圖片。 WHY U NO SHOWN THERE?動態數組變量未顯示在局部變量調試窗口中

正如您所看到的,我在代碼中使用了該變量,並且在調試時禁用了優化。但我也在使用泛型和匿名方法,這些我不是專家。 有問題的程序的代碼是這樣的(是什麼的步驟的作用是爲了在兩個第一陣列ArrayNomes,通過以遞減順序在第一陣列的串的長度ArrayValores):

procedure OrdenarArrays(var ArrayNomes, ArrayValores: array of string; var ArrayIndices: array of Integer); 
    var 
    Comparer: IComparer<Integer>; 
    I: Integer; 
    tmpNomesCampos, tmpValoresCampos: array of String; 
    begin 

    SetLength(tmpNomesCampos, cdsCadastro.FieldCount); 
    SetLength(tmpValoresCampos, cdsCadastro.FieldCount); 

    //Carregar os NomesCampos para serem usados na comparação 
    for I := 0 to High(arrayIndices) do 
    begin 
     tmpNomesCampos[I] := ArrayNomes[I]; 
    end; 

    { Cria novo delegatedcomparer. Ele permite o uso de um callback para comparar os arrays} 
    Comparer := TDelegatedComparer<Integer>.Create(
     { TComparison<Integer> } 
     function(const Left, Right: Integer): Integer 
     begin 
     {colocar em ordem decrescente de acordo com o tamanho do nome do campo} 
//  Result := Left - Right; 
     Result := -(Length(tmpNomesCampos[Left]) - Length(tmpNomesCampos[Right])); 
     end); 

    { Ordena o Array base } 
    TArray.Sort<Integer>(arrayIndices, Comparer); 

    //Reordenar os NomesCampos de acordo com o array IndicesCampos 
    for I := 0 to High(arrayIndices) do 
    begin 
     tmpNomesCampos[I] := ArrayNomes[arrayIndices[I]]; 
     tmpValoresCampos[I] := ArrayValores[arrayIndices[I]]; 
    end; 

    //Salvar nos arrays definitivos; 
    for I := 0 to High(arrayIndices) do 
    begin 
     ArrayNomes[I] := tmpNomesCampos[I]; 
     ArrayValores[I] := tmpValoresCampos[I]; 
    end; 

    end; 

這是變量未示出錯誤?這是一個已知的錯誤嗎?或者它可能是使用我不知道的泛型和匿名方法的功能?

系統:Windows 7 64位/ Delphi的XE(最新的更新)


UPDATE:改變了代碼下面的簡化控制檯版本。這可以幫助任何想要在他的Delphi版本中測試的人。 注意:它不會填充原始數組,因爲它沒有必要顯示問題;

program Project1; 


{$APPTYPE CONSOLE} 

uses 
    SysUtils, Generics.Collections, Generics.Defaults; 

    procedure OrdenarArrays(var ArrayNomes, ArrayValores: array of string; var ArrayIndices: array of Integer); 
    var 
    Comparer: IComparer<Integer>; 
    I: Integer; 
    tmpNomesCampos, tmpValoresCampos: array of String; 
    begin 

    SetLength(tmpNomesCampos, Length(arrayIndices)); 
    SetLength(tmpValoresCampos, Length(arrayIndices)); 

    //Carregar os NomesCampos para serem usados na comparação 
    for I := 0 to High(arrayIndices) do 
    begin 
     tmpNomesCampos[I] := ArrayNomes[I]; 
    end; 

    { Cria novo delegatedcomparer. Ele permite o uso de um callback para comparar os arrays} 
    Comparer := TDelegatedComparer<Integer>.Create(
     { TComparison<Integer> } 
     function(const Left, Right: Integer): Integer 
     begin 
     {colocar em ordem decrescente de acordo com o tamanho do nome do campo} 
    //  Result := Left - Right; 
     Result := -(Length(tmpNomesCampos[Left]) - Length(tmpNomesCampos[Right])); 
     end); 

    { Ordena o Array base } 
    TArray.Sort<Integer>(arrayIndices, Comparer); 

    //Reordenar os NomesCampos de acordo com o array IndicesCampos 
    for I := 0 to High(arrayIndices) do 
    begin 
     tmpNomesCampos[I] := ArrayNomes[arrayIndices[I]]; 
     tmpValoresCampos[I] := ArrayValores[arrayIndices[I]]; 
    end; 

    //Salvar nos arrays definitivos; 
    for I := 0 to High(arrayIndices) do 
    begin 
     ArrayNomes[I] := tmpNomesCampos[I]; 
     ArrayValores[I] := tmpValoresCampos[I]; 
    end; 

    end; 

var 
    NomesCampos, ValoresCampos: array of String; 
    IndicesCampos: array of Integer; 
    I: Integer; 
begin 
    try 

    SetLength(NomesCampos, 42); 
    SetLength(ValoresCampos, 42); 
    SetLength(IndicesCampos, 42); 

// for I := 0 to 41 do 

    OrdenarArrays(NomesCampos, ValoresCampos, IndicesCampos); 

    Readln; 
    except 
    on E: Exception do 
     Writeln(E.ClassName, ': ', E.Message); 
    end; 
end. 
+0

首先,我會擺脫依賴於cdsCadastro.FieldCount的,並將它傳遞到方法。如果這樣做不能幫助您將方法從本地嵌套方法中移出。 –

+0

您可以製作三條線,其中第一條和第三條線將使用它,然後查看它是否在第二條線上可見。或者在禁用優化的情況下編譯程序(推薦用於調試)。它將顯示在第2行,使用數組的行之間? –

+0

@ Arioch'The Optimization已被禁用。我不好,我會更新這個問題。 – EMBarbosa

回答

5

這是XE5中仍然存在的調試器/ IDE錯誤。正如您懷疑的那樣,問題在於使用匿名方法。關鍵是一個變量是否被捕獲。當捕獲變量時,該變量不會顯示在本地窗口中。這裏是我可以編造最短SSCCE:

{$APPTYPE CONSOLE} 

uses 
    System.SysUtils; 

procedure Foo1; 
var 
    func: TFunc<Integer>; 
    val: Integer; 
begin 
    val := 666; 
    func := 
    function: Integer 
    begin 
     Result := val; 
    end; 
end; 

procedure Foo2; 
var 
    func: TFunc<Integer>; 
    val: Integer; 
begin 
    val := 666; 
    func := 
    function: Integer 
    begin 
     Result := 666; 
    end; 
end; 

begin 
    Foo1; 
    Foo2; 
    Readln; 
end. 

在調試器,Foo1.val在本地窗口中顯示不出來。但Foo2.val呢。

QC#121821

+0

+1,已投票。提示,你可以爲自己的質量控制報告投票,:-) –

+1

此外,你不能添加一個'Foo1.val'的手錶, – EMBarbosa

+1

@LURD涉及更多與質量控制鬥爭,他們會採取任何通知嗎?我很驚訝他們還沒有修正浮點控制..... –

0

不是一個問題的答案,但對如何寫在一個更簡單的方法例程(至少如果我明白了什麼應該做的)建議

procedure OrderArrays(var ArrayNameValuePairs: array of TPair<string, string>); 
begin 
    TArray.Sort<TPair<string, string>>(ArrayNameValuePairs, 
    TComparer<TPair<string, string>>.Construct(
     function(const Left, Right: TPair<string, string>): Integer 
     begin 
     Result := Length(Right.Key) - Length(Left.Key); 
     end)); 
end; 

正如你可以看到我他們顯然屬於一起的名字和價值。這使得對這個組合數組進行排序變得非常容易,因爲您不必對排列第三個數組的數組進行排序來對兩個原始數組重新排序。

+0

謝謝。我會在稍後嘗試。使用第三個數組的優點是,我甚至不需要排序前兩個數組,即使我這樣做,我也可以知道更改前的位置。 – EMBarbosa