{$MODE OBJFPC}
{$MODESWITCH AUTODEREF}
uses
  dstrings,
  dhashmap_oldstyle,
  dhashfuncs;

type
TStruct = record
  A, B, C: LongInt;
end;

type
TRecord = record
  I: LongInt;
  S: AnsiString;
end;

THashMapOfRecord = object(THashMap)
protected
  procedure DeleteElement(P: Pointer); virtual;
  procedure CopyElement(Src, Dst: Pointer); virtual;
end;

procedure THashMapOfRecord.DeleteElement(P: Pointer);
begin
  TRecord(P^).S := '';
end;

procedure THashMapOfRecord.CopyElement(Src, Dst: Pointer);
begin
  TRecord(Dst^) := TRecord(Src^);
end;

var
  HashMap: THashMap;
  Records: THashMapOfRecord;
  S: TStruct;
  R: TRecord;

begin
  HashMap.Init(SizeOf(TStruct), @HashPjw32);
  S.A := 1;
  S.B := 2;
  S.C := 1;
  HashMap.Add('a', @S);
  S.A := 4;
  S.B := 5;
  S.C := 6;
  HashMap.Add('b', @S);
  Writeln(TStruct(HashMap.Get('a')^).A);
  Writeln(TStruct(HashMap.Get('b')^).A);
  HashMap.Done;

  Records.Init(SizeOf(TRecord), @HashPjw32);
  R.I := 335;
  R.S := 'Hello ';
  Records.Add('a', @R);
  R.S := 'world!';
  Records.Add('b', @R);
  R.S := TRecord(Records.Get('a')^).S + TRecord(Records.Get('b')^).S;
  Records.Add('c', @R);
  Records.Del('a');
  Records.Del('b');
  Writeln(TRecord(Records.Get('c')^).S);
  Records.Done;
end.
