9

How can I sort TDictionary by a key of Integer in ascending order in Delphi 2009?

Max Smith
  • 395
  • 1
  • 2
  • 13

1 Answers1

17

The RTL TDictionaries are not sorted and cannot be sorted (other than by hash, which they are). You need to use another container if you wish to sort either the keys or the values. For example :

program Project1;

{$APPTYPE CONSOLE}

uses
  Generics.Collections, Generics.Defaults, SysUtils;

var
  LDict : TDictionary<integer, string>;
  i, j : integer;
  LArray : TArray<integer>;
begin
  LDict := TDictionary<integer, string>.Create;
  try
    // Generate some values
    Randomize;
    for i := 0 to 20 do begin
      j := Random(1000);
      LDict.AddOrSetValue(j, Format('The Value : %d', [j]));
    end;
    WriteLn('Disorder...');
    for i in LDict.Keys do
      WriteLn(LDict.Items[i]);
    // Sort
    LArray := LDict.Keys.ToArray;
    TArray.Sort<integer>(LArray);
    WriteLn('Order...');
    for i in LArray do
      WriteLn(LDict.Items[i]);
  finally
    LDict.Free;
  end;
  Readln;
end.
J...
  • 30,968
  • 6
  • 66
  • 143
  • 2
    The spring4d dictionary is ordered – David Heffernan Apr 22 '20 at 13:51
  • @DavidHeffernan With O(1) lookup? And without double the storage requirements? Surely something had to be sacrificed for that... – J... Apr 20 '21 at 11:02
  • 1
    Nope. It is code that I donated to spring4d, and worked with Stefan to integrate it and then he has done quite a lot more work optimising it. The algorithm is based on the Python compact dictionary. There are lots of articles about this, but here's a video from its creator: https://paulvanderlaken.com/2019/12/28/history-modern-python-dictionary-raymond-hettinger/ – David Heffernan Apr 20 '21 at 11:06
  • @DavidHeffernan Interesting. I think I'll try to find an article. – J... Apr 20 '21 at 11:07