File: lazfglhash.pas

package info (click to toggle)
lazarus 2.0.0%2Bdfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: buster
  • size: 214,460 kB
  • sloc: pascal: 1,862,622; xml: 265,709; cpp: 56,595; sh: 3,008; java: 609; makefile: 535; perl: 297; sql: 222; ansic: 137
file content (128 lines) | stat: -rw-r--r-- 3,152 bytes parent folder | download | duplicates (2)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
{
 *****************************************************************************
  This file is part of LazUtils.

  See the file COPYING.modifiedLGPL.txt, included in this distribution,
  for details about the license.
 *****************************************************************************
}
unit lazfglhash;

{$mode objfpc}{$H+}

interface

uses
  contnrs;

type
  generic TLazHTGNode<T> = Class(THTCustomNode)
  Private
    FData : T;
  public
    property Data: T read FData write FData;
  end;

  { TLazFPGHashTable }

  generic TLazFPGHashTable<T> = Class(TFPCustomHashTable)
  Protected
    type
      THTGNode = Class(THTCustomNode)
      Private
        FData : T;
      public
        property Data: T read FData write FData;
      end;
      TGIteratorMethod = Procedure(Item: T; const Key: string; var Continue: Boolean) of object;
    Function CreateNewNode(const aKey : String) : THTCustomNode; override;
    Procedure AddNode(ANode : THTCustomNode); override;
    Procedure SetData(const Index: string; AValue: T); virtual;
    Function GetData(const index: string): T; virtual;
    {$if not(defined(ver2) or defined(ver3_0))}
    Function ForEachCall(aMethod: TGIteratorMethod): THTGNode; virtual;
    {$endif}
  Public
    {$if not(defined(ver2) or defined(ver3_0))}
    Function Iterate(aMethod: TGIteratorMethod): T; virtual;
    {$endif}
    Procedure Add(const aKey: string; const aItem: T); virtual;
    property Items[const index: string]: T read GetData write SetData; default;
  end;


implementation

{ TFPGHashTable }

function TLazFPGHashTable.CreateNewNode(const aKey: String): THTCustomNode;
begin
  Result:=THTGNode.CreateWith(aKey);
end;

procedure TLazFPGHashTable.AddNode(ANode: THTCustomNode);
begin
  with THTGNode(ANode) do
    Add(Key,Data);
end;

procedure TLazFPGHashTable.SetData(const Index: string; AValue: T);
begin
  THTGNode(FindOrCreateNew(index)).Data:=AValue;
end;

function TLazFPGHashTable.GetData(const index: string): T;
var
  node: THTGNode;
begin
  node:=THTGNode(Find(Index));
  if Assigned(node) then
    Result:=node.Data;
end;

{$if not(defined(ver2) or defined(ver3_0))}
function TLazFPGHashTable.ForEachCall(aMethod: TGIteratorMethod): THTGNode;
var
  i, j: Longword;
  continue: boolean;
begin
  Result:=nil;
  continue:=True;
  if HashTableSize>0 then
    for i:=0 to HashTableSize-1 do
      if Assigned(Chain(i)) then
        if chain(i).Count>0 then
          for j:=0 to Chain(i).Count-1 do
            begin
            aMethod(THTGNode(Chain(i)[j]).Data, THTGNode(Chain(i)[j]).Key, continue);
            if not continue then
              begin
              Result:=THTGNode(Chain(i)[j]);
              Exit;
              end;
            end;
end;

function TLazFPGHashTable.Iterate(aMethod: TGIteratorMethod): T;
var
  N : THTGNode;
begin
  N:=ForEachCall(AMethod);
  if Assigned(N) then
    Result:=N.Data
end;
{$endif}

procedure TLazFPGHashTable.Add(const aKey: string; const aItem: T);
var
  chn: TFPObjectList;
  NewNode: THTGNode;
begin
  chn:=FindChainForAdd(akey);
  NewNode:=THTGNode(CreateNewNode(aKey));
  NewNode.Data:=aItem;
  chn.Add(NewNode);
end;

end.