1
0
mirror of synced 2024-09-07 21:45:03 +00:00

Added: Delphi 2005/2006 compiler versions

Added: support for Delphi 2006' for-in construction on hashes
Added: ResetCache method for Settings factory
This commit is contained in:
Mark van Renswoude 2005-12-28 19:15:17 +00:00
parent cd4e85c4b6
commit 863e817675
8 changed files with 355 additions and 23 deletions

View File

@ -32,5 +32,5 @@
-M
-$M16384,1048576
-K$00400000
-LE"c:\delphi6\Projects\Bpl"
-LN"c:\delphi6\Projects\Bpl"
-LE"c:\program files\borland\delphi7\Projects\Bpl"
-LN"c:\program files\borland\delphi7\Projects\Bpl"

View File

@ -1,5 +1,5 @@
[FileVersion]
Version=6.0
Version=7.0
[Compiler]
A=8
B=0
@ -30,6 +30,55 @@ Z=1
ShowHints=1
ShowWarnings=1
UnitAliases=WinTypes=Windows;WinProcs=Windows;DbiTypes=BDE;DbiProcs=BDE;DbiErrs=BDE;
NamespacePrefix=
SymbolDeprecated=1
SymbolLibrary=1
SymbolPlatform=1
UnitLibrary=1
UnitPlatform=1
UnitDeprecated=1
HResultCompat=1
HidingMember=1
HiddenVirtual=1
Garbage=1
BoundsError=1
ZeroNilCompat=1
StringConstTruncated=1
ForLoopVarVarPar=1
TypedConstVarPar=1
AsgToTypedConst=1
CaseLabelRange=1
ForVariable=1
ConstructingAbstract=1
ComparisonFalse=1
ComparisonTrue=1
ComparingSignedUnsigned=1
CombiningSignedUnsigned=1
UnsupportedConstruct=1
FileOpen=1
FileOpenUnitSrc=1
BadGlobalSymbol=1
DuplicateConstructorDestructor=1
InvalidDirective=1
PackageNoLink=1
PackageThreadVar=1
ImplicitImport=1
HPPEMITIgnored=1
NoRetVal=1
UseBeforeDef=1
ForLoopVarUndef=1
UnitNameMismatch=1
NoCFGFileFound=1
MessageDirective=1
ImplicitVariants=1
UnicodeToLocale=1
LocaleToUnicode=1
ImagebaseMultiple=1
SuspiciousTypecast=1
PrivatePropAccessor=1
UnsafeType=1
UnsafeCode=1
UnsafeCast=1
[Linker]
MapFile=3
OutputObjs=0
@ -56,10 +105,6 @@ HostApplication=
Launcher=
UseLauncher=0
DebugCWD=
[Language]
ActiveLang=
ProjectLang=
RootDir=
[Version Info]
IncludeVerInfo=1
AutoIncBuild=1

View File

@ -19,6 +19,7 @@ type
procedure testClear();
procedure testDelete(); virtual; abstract;
procedure testIterate(); virtual; abstract;
procedure testEnumerator(); virtual; abstract;
end;
// Two test cases involving all value managers.
@ -36,6 +37,7 @@ type
procedure testGet(); override;
procedure testDelete(); override;
procedure testIterate(); override;
procedure testEnumerator(); override;
end;
THashesPOTest = class(THashesTest)
@ -51,6 +53,7 @@ type
procedure testGet(); override;
procedure testDelete(); override;
procedure testIterate(); override;
procedure testEnumerator(); override;
end;
THashesVariantTest = class(THashesTest)
@ -66,6 +69,7 @@ type
procedure testGet(); override;
procedure testDelete(); override;
procedure testIterate(); override;
procedure testEnumerator(); override;
end;
implementation
@ -135,6 +139,40 @@ begin
CheckTrue(Hash.Exists('Key3'), 'Key3 does not exist!');
end;
procedure THashesSITest.testEnumerator;
var
aPresent: array[1..3] of Boolean;
sKey: String;
begin
FillTestItems();
FillChar(aPresent, SizeOf(aPresent), #0);
for sKey in Hash do
begin
if sKey = 'Key1' then
aPresent[1] := True
else if sKey = 'Key2' then
aPresent[2] := True
else if sKey = 'Key3' then
aPresent[3] := True;
end;
CheckTrue(aPresent[1], 'Key1 was not in the enumeration!');
CheckTrue(aPresent[2], 'Key2 was not in the enumeration!');
CheckTrue(aPresent[3], 'Key3 was not in the enumeration!');
{ Not supported yet, maybe in the future.
FillChar(aPresent, SizeOf(aPresent), #0);
for iValue in Hash.Values do
aPresent[iValue] := True;
CheckTrue(aPresent[1], 'Value of Key1 was not in the enumeration!');
CheckTrue(aPresent[2], 'Value of Key2 was not in the enumeration!');
CheckTrue(aPresent[3], 'Value of Key3 was not in the enumeration!');
}
end;
procedure THashesSITest.testIterate;
var
aPresent: array[1..3] of Boolean;
@ -201,6 +239,23 @@ begin
CheckTrue(Hash.Exists(Pointer(2)), 'Key3 does not exist!');
end;
procedure THashesPOTest.testEnumerator;
var
aPresent: array[0..2] of Boolean;
pKey: Pointer;
begin
FillTestItems();
FillChar(aPresent, SizeOf(aPresent), #0);
for pKey in Hash do
aPresent[Integer(pKey)] := True;
CheckTrue(aPresent[0], 'Key1 was not in the enumeration!');
CheckTrue(aPresent[1], 'Key2 was not in the enumeration!');
CheckTrue(aPresent[2], 'Key3 was not in the enumeration!');
end;
procedure THashesPOTest.testIterate;
var
aPresent: array[0..2] of Boolean;
@ -271,6 +326,11 @@ begin
CheckTrue(Hash.Exists('Key3'), 'Key3 does not exist!');
end;
procedure THashesVariantTest.testEnumerator;
begin
Check(True, 'Not implemented yet.');
end;
procedure THashesVariantTest.testIterate;
var
aPresent: array[0..2] of Boolean;

View File

@ -32,8 +32,8 @@
-M
-$M16384,1048576
-K$00400000
-LE"c:\program files\borland\delphi7\Projects\Bpl"
-LN"c:\program files\borland\delphi7\Projects\Bpl"
-LE"C:\Documents and Settings\PsychoMark\My Documents\Borland Studio Projects\Bpl"
-LN"C:\Documents and Settings\PsychoMark\My Documents\Borland Studio Projects\Bpl"
-w-SYMBOL_PLATFORM
-w-UNIT_PLATFORM
-w-UNSAFE_TYPE

View File

@ -1,17 +1,16 @@
program X2UtUnitTests;
uses
MemCheck,
TestFramework,
GUITestRunner,
Variants,
BitsTest in 'Units\BitsTest.pas',
HashesTest in 'Units\HashesTest.pas',
SettingsTest in 'Units\SettingsTest.pas',
IniParserTest in 'Units\IniParserTest.pas';
HashesTest in 'Units\HashesTest.pas';
//SettingsTest in 'Units\SettingsTest.pas',
//IniParserTest in 'Units\IniParserTest.pas';
begin
MemChk();
// MemChk();
RunRegisteredTests();
end.

View File

@ -2,6 +2,33 @@
// being used...
{$DEFINE DUNKNOWN}
{$IFDEF VER180}
{$DEFINE D2006}
{$DEFINE D2005}
{$DEFINE D8}
{$DEFINE D7}
{$DEFINE D6}
{$DEFINE D5}
{$DEFINE D4}
{$DEFINE D3}
{$DEFINE D2}
{$DEFINE D1}
{$UNDEF DUNKNOWN}
{$ENDIF}
{$IFDEF VER170}
{$DEFINE D2005}
{$DEFINE D8}
{$DEFINE D7}
{$DEFINE D6}
{$DEFINE D5}
{$DEFINE D4}
{$DEFINE D3}
{$DEFINE D2}
{$DEFINE D1}
{$UNDEF DUNKNOWN}
{$ENDIF}
{$IFDEF VER160}
{$DEFINE D8}
{$DEFINE D7}
@ -75,6 +102,8 @@
// so I don't know what defines they have... if you do know,
// feel free to send me any changes...
{$IFDEF DUNKNOWN}
{$DEFINE D2006}
{$DEFINE D2005}
{$DEFINE D8}
{$DEFINE D7}
{$DEFINE D6}

View File

@ -14,6 +14,11 @@
:: For example; TX2SOHash indicates that it uses String keys to identify
:: Object values.
::
:: As of Delphi 2006, all default hashes support the for...in structure.
:: To enumerate all keys, use "for x in Hash". As of yet, there is no
:: direct support for value enumeration yet; you can use
:: First/Next/CurrentValue for that.
::
:: Last changed: $Date$
:: Revision: $Rev$
:: Author: $Author$
@ -35,6 +40,10 @@ type
//:$ Raised when the cursor is not available
EX2HashNoCursor = class(Exception);
// Forward declarations
TX2CustomHash = class;
{$REGION 'Internal hash structures'}
{
:$ Internal representation of a hash item.
}
@ -83,12 +92,14 @@ type
property Current: PX2HashValue read GetCurrent;
end;
{$ENDREGION}
{$REGION 'Internal value managers'}
{
:$ Base value manager.
}
TX2CustomHashManager = class(TObject)
public
protected
procedure Initialize(var AData: Pointer); virtual;
procedure Finalize(var AData: Pointer); virtual;
@ -103,7 +114,7 @@ type
end;
TX2HashPointerManager = class(TX2CustomHashManager)
public
protected
function ToPointer(const AValue: Pointer): Pointer; overload;
function ToValue(const AData: Pointer): Pointer; overload;
end;
@ -112,7 +123,7 @@ type
:$ Integer value class.
}
TX2HashIntegerManager = class(TX2CustomHashManager)
public
protected
function ToPointer(const AValue: Integer): Pointer; overload;
function ToValue(const AData: Pointer): Integer; overload;
end;
@ -123,7 +134,7 @@ type
TX2HashObjectManager = class(TX2CustomHashManager)
private
FOwnsObjects: Boolean;
public
protected
procedure Finalize(var AData: Pointer); override;
function ToPointer(const AValue: TObject): Pointer; overload;
@ -136,7 +147,7 @@ type
:$ String value class.
}
TX2HashStringManager = class(TX2CustomHashManager)
public
protected
procedure Finalize(var AData: Pointer); override;
function DataSize(const AData: Pointer): Cardinal; override;
@ -150,7 +161,72 @@ type
function Compare(const AData: Pointer; const AValue: Pointer;
const ASize: Cardinal): Boolean; override;
end;
{$ENDREGION}
{$REGION 'Delphi 2006 enumerator support'}
{
:$ Base enumerator class.
}
TX2HashEnumerator = class(TObject)
private
FCursor: TX2HashCursor;
FManager: TX2CustomHashManager;
FEnumKeys: Boolean;
function GetCursor(): Pointer;
protected
property Manager: TX2CustomHashManager read FManager;
property Cursor: Pointer read GetCursor;
public
constructor Create(const AHash: TX2CustomHash;
const AEnumKeys: Boolean);
destructor Destroy(); override;
function MoveNext(): Boolean;
end;
{
:$ Enumerator for pointer values.
}
TX2HashPointerEnumerator = class(TX2HashEnumerator)
private
function GetCurrent: Pointer;
public
property Current: Pointer read GetCurrent;
end;
{
:$ Enumerator for integer values.
}
TX2HashIntegerEnumerator = class(TX2HashEnumerator)
private
function GetCurrent: Integer;
public
property Current: Integer read GetCurrent;
end;
{
:$ Enumerator for object values.
}
TX2HashObjectEnumerator = class(TX2HashEnumerator)
private
function GetCurrent: TObject;
public
property Current: TObject read GetCurrent;
end;
{
:$ Enumerator for string values
}
TX2HashStringEnumerator = class(TX2HashEnumerator)
private
function GetCurrent(): String;
public
property Current: String read GetCurrent;
end;
{$ENDREGION}
{$REGION 'Abstract hash implementation'}
{
:$ Hash implementation.
}
@ -162,6 +238,9 @@ type
FCursor: TX2HashCursor;
FKeyManager: TX2CustomHashManager;
FValueManager: TX2CustomHashManager;
FKeys: TObject;
FValues: TObject;
protected
function CreateCursor(): TX2HashCursor; virtual;
function CreateKeyManager(): TX2CustomHashManager; virtual; abstract;
@ -201,7 +280,9 @@ type
property Count: Integer read FCount;
end;
{$ENDREGION}
{$REGION 'Base hash classes'}
{
:$ Base hash implementation for pointer keys.
}
@ -213,6 +294,8 @@ type
function Find(const AKey: Pointer;
const AAllowCreate: Boolean): PX2HashValue; overload;
public
function GetEnumerator(): TX2HashPointerEnumerator;
function Exists(const AKey: Pointer): Boolean; overload;
function Delete(const AKey: Pointer): Boolean; overload;
@ -230,6 +313,8 @@ type
function Find(const AKey: Integer;
const AAllowCreate: Boolean): PX2HashValue; overload;
public
function GetEnumerator(): TX2HashIntegerEnumerator;
function Exists(const AKey: Integer): Boolean; overload;
function Delete(const AKey: Integer): Boolean; overload;
@ -247,6 +332,8 @@ type
function Find(const AKey: TObject;
const AAllowCreate: Boolean): PX2HashValue; overload;
public
function GetEnumerator(): TX2HashObjectEnumerator;
function Exists(const AKey: TObject): Boolean; overload;
function Delete(const AKey: TObject): Boolean; overload;
@ -264,13 +351,16 @@ type
function Find(const AKey: String;
const AAllowCreate: Boolean): PX2HashValue; overload;
public
function GetEnumerator(): TX2HashStringEnumerator;
function Exists(const AKey: String): Boolean; overload;
function Delete(const AKey: String): Boolean; overload;
property CurrentKey: String read GetCurrentKey;
end;
{$ENDREGION}
{$REGION 'Concrete hash classes'}
{
:$ Pointer-to-Pointer hash.
}
@ -530,6 +620,7 @@ type
property CurrentValue: String read GetCurrentValue;
property Values[Key: String]: String read GetValue write SetValue; default;
end;
{$ENDREGION}
implementation
const
@ -584,6 +675,7 @@ begin
end;
{$REGION 'Internal hash structures'}
{========================================
TX2HashCursor
========================================}
@ -685,8 +777,10 @@ begin
break;
until False;
end;
{$ENDREGION}
{$REGION 'Internal value managers'}
{========================================
TX2CustomHashManager
========================================}
@ -857,8 +951,10 @@ begin
Result := CompareMem(pSource, AValue, ASize);
end;
{$ENDREGION}
{$REGION 'Abstract hash implementation'}
{========================== TX2CustomHash
Initialization
========================================}
@ -883,7 +979,9 @@ end;
function TX2CustomHash.CreateCursor(): TX2HashCursor;
begin
Result := TX2HashCursor.Create(FRoot);
Result := nil;
if Assigned(FRoot) then
Result := TX2HashCursor.Create(FRoot);
end;
procedure TX2CustomHash.InvalidateCursor();
@ -1190,9 +1288,77 @@ begin
Result := Cursor.Next();
end;
{$ENDREGION}
{$REGION 'Delphi 2006 enumerator support'}
{========================================
TX2HashEnumerator
========================================}
constructor TX2HashEnumerator.Create(const AHash: TX2CustomHash;
const AEnumKeys: Boolean);
begin
inherited Create();
FEnumKeys := AEnumKeys;
if AEnumKeys then
FManager := AHash.KeyManager
else
FManager := AHash.ValueManager;
FCursor := AHash.CreateCursor();
end;
destructor TX2HashEnumerator.Destroy();
begin
FreeAndNil(FCursor);
inherited;
end;
function TX2HashEnumerator.GetCursor(): Pointer;
begin
if FEnumKeys then
Result := FCursor.Current^.Key
else
Result := FCursor.Current^.Value;
end;
function TX2HashEnumerator.MoveNext(): Boolean;
begin
Result := False;
if Assigned(FCursor) then
Result := FCursor.Next();
end;
{ TX2HashPointerEnumerator }
function TX2HashPointerEnumerator.GetCurrent(): Pointer;
begin
Result := TX2HashPointerManager(Manager).ToValue(Cursor);
end;
{ TX2HashIntegerEnumerator }
function TX2HashIntegerEnumerator.GetCurrent(): Integer;
begin
Result := TX2HashIntegerManager(Manager).ToValue(Cursor);
end;
{ TX2HashObjectEnumerator }
function TX2HashObjectEnumerator.GetCurrent(): TObject;
begin
Result := TX2HashObjectManager(Manager).ToValue(Cursor);
end;
{ TX2HashStringEnumerator }
function TX2HashStringEnumerator.GetCurrent(): String;
begin
Result := TX2HashStringManager(Manager).ToValue(Cursor);
end;
{$ENDREGION}
{$REGION 'Base hash classes'}
{========================================
TX2CustomPointerHash
========================================}
@ -1207,6 +1373,11 @@ begin
Result := TX2HashPointerManager(KeyManager).ToValue(Cursor.Current^.Key);
end;
function TX2CustomPointerHash.GetEnumerator(): TX2HashPointerEnumerator;
begin
Result := TX2HashPointerEnumerator.Create(Self, True);
end;
function TX2CustomPointerHash.Find(const AKey: Pointer;
const AAllowCreate: Boolean): PX2HashValue;
begin
@ -1238,6 +1409,11 @@ begin
Result := TX2HashIntegerManager(KeyManager).ToValue(Cursor.Current^.Key);
end;
function TX2CustomIntegerHash.GetEnumerator(): TX2HashIntegerEnumerator;
begin
Result := TX2HashIntegerEnumerator.Create(Self, True);
end;
function TX2CustomIntegerHash.Find(const AKey: Integer;
const AAllowCreate: Boolean): PX2HashValue;
begin
@ -1269,6 +1445,11 @@ begin
Result := TX2HashObjectManager(KeyManager).ToValue(Cursor.Current^.Key);
end;
function TX2CustomObjectHash.GetEnumerator(): TX2HashObjectEnumerator;
begin
Result := TX2HashObjectEnumerator.Create(Self, True);
end;
function TX2CustomObjectHash.Find(const AKey: TObject;
const AAllowCreate: Boolean): PX2HashValue;
begin
@ -1301,6 +1482,11 @@ begin
end;
function TX2CustomStringHash.GetEnumerator(): TX2HashStringEnumerator;
begin
Result := TX2HashStringEnumerator.Create(Self, True);
end;
function TX2CustomStringHash.Find(const AKey: String;
const AAllowCreate: Boolean): PX2HashValue;
begin
@ -1316,8 +1502,10 @@ function TX2CustomStringHash.Delete(const AKey: String): Boolean;
begin
Result := inherited Delete(PChar(AKey), Length(AKey));
end;
{$ENDREGION}
{$REGION 'Concrete hash classes'}
{========================================
TX2PPHash
========================================}
@ -1873,6 +2061,8 @@ begin
inherited SetValue(Find(Key, True),
TX2HashStringManager(ValueManager).ToPointer(Value));
end;
{$ENDREGION}
initialization
CRC32Init();

View File

@ -155,7 +155,7 @@ type
//:$ Validates the specified value using the defined callback method
//:$ if present.
function ValidateValue(const AName: String; const AValue: Variant): Variant;
end deprecated;
end;
{
:$ Settings factory.
@ -173,6 +173,8 @@ type
constructor Create();
destructor Destroy(); override;
procedure ResetCache();
//:$ Loads a section from the settings.
//:: Sub-sections are indicated by seperating the sections with a dot ('.')
//:: characters, ex: Sub.Section. The underlying extension will translate
@ -186,7 +188,7 @@ type
//:: callback method to perform centralized checks.
procedure Define(const ASection, AName: String; const AValue: Variant;
const ACallback: TX2SettingsCallback = nil);
end deprecated;
end;
implementation
@ -655,4 +657,11 @@ begin
FCallback(AAction, ASection, AName, AValue);
end;
procedure TX2SettingsFactory.ResetCache();
begin
FDefines.First();
while FDefines.Next() do
TX2SettingsDefine(FDefines.CurrentValue).Cached := False;
end;
end.