1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885188618871888188918901891189218931894189518961897189818991900190119021903190419051906190719081909191019111912191319141915191619171918191919201921192219231924192519261927192819291930193119321933193419351936193719381939194019411942194319441945194619471948194919501951195219531954195519561957195819591960196119621963196419651966196719681969197019711972197319741975197619771978197919801981198219831984198519861987198819891990199119921993199419951996199719981999200020012002200320042005200620072008200920102011201220132014201520162017201820192020202120222023202420252026202720282029203020312032203320342035203620372038203920402041204220432044204520462047204820492050205120522053205420552056205720582059206020612062206320642065206620672068206920702071207220732074207520762077207820792080208120822083208420852086208720882089209020912092209320942095209620972098209921002101210221032104210521062107210821092110211121122113211421152116211721182119212021212122212321242125212621272128212921302131213221332134213521362137213821392140214121422143214421452146214721482149215021512152215321542155215621572158215921602161216221632164216521662167216821692170217121722173217421752176217721782179218021812182218321842185218621872188218921902191219221932194219521962197219821992200220122022203220422052206220722082209221022112212221322142215221622172218221922202221222222232224222522262227222822292230223122322233223422352236223722382239224022412242224322442245224622472248224922502251225222532254225522562257225822592260226122622263226422652266226722682269227022712272227322742275227622772278227922802281228222832284228522862287228822892290229122922293229422952296229722982299230023012302230323042305230623072308230923102311231223132314231523162317231823192320232123222323232423252326232723282329233023312332233323342335233623372338233923402341234223432344234523462347234823492350235123522353235423552356235723582359236023612362236323642365236623672368236923702371237223732374237523762377237823792380238123822383238423852386238723882389239023912392239323942395239623972398239924002401240224032404240524062407240824092410241124122413241424152416241724182419242024212422242324242425242624272428242924302431243224332434243524362437243824392440244124422443244424452446244724482449245024512452245324542455245624572458245924602461246224632464246524662467246824692470247124722473247424752476247724782479248024812482248324842485248624872488248924902491249224932494249524962497249824992500250125022503250425052506250725082509251025112512251325142515251625172518251925202521252225232524252525262527252825292530253125322533253425352536253725382539254025412542254325442545254625472548254925502551255225532554255525562557255825592560256125622563256425652566256725682569257025712572257325742575257625772578257925802581258225832584258525862587258825892590259125922593259425952596259725982599260026012602260326042605260626072608260926102611261226132614261526162617261826192620262126222623262426252626262726282629263026312632263326342635263626372638263926402641264226432644264526462647264826492650265126522653265426552656265726582659266026612662266326642665266626672668266926702671267226732674267526762677267826792680268126822683268426852686268726882689269026912692269326942695269626972698269927002701270227032704270527062707270827092710271127122713271427152716271727182719272027212722272327242725272627272728272927302731273227332734273527362737273827392740274127422743274427452746274727482749275027512752275327542755275627572758275927602761276227632764276527662767276827692770277127722773277427752776277727782779278027812782278327842785278627872788278927902791279227932794279527962797279827992800280128022803280428052806280728082809281028112812281328142815281628172818281928202821282228232824282528262827282828292830283128322833283428352836283728382839284028412842284328442845284628472848284928502851285228532854285528562857285828592860286128622863286428652866286728682869287028712872287328742875287628772878287928802881288228832884288528862887288828892890289128922893289428952896289728982899290029012902290329042905290629072908290929102911291229132914291529162917291829192920292129222923292429252926292729282929293029312932293329342935293629372938293929402941294229432944294529462947294829492950295129522953295429552956295729582959296029612962296329642965296629672968296929702971297229732974297529762977297829792980298129822983298429852986298729882989299029912992299329942995299629972998299930003001300230033004300530063007300830093010301130123013301430153016301730183019302030213022302330243025302630273028302930303031303230333034303530363037303830393040304130423043304430453046304730483049305030513052305330543055305630573058305930603061306230633064306530663067306830693070307130723073307430753076307730783079308030813082308330843085308630873088308930903091309230933094309530963097309830993100310131023103310431053106310731083109311031113112311331143115311631173118311931203121312231233124312531263127312831293130313131323133313431353136313731383139314031413142314331443145314631473148314931503151315231533154315531563157315831593160316131623163316431653166316731683169317031713172317331743175317631773178317931803181318231833184318531863187318831893190319131923193319431953196319731983199320032013202320332043205320632073208320932103211321232133214321532163217321832193220322132223223322432253226322732283229323032313232323332343235323632373238323932403241324232433244324532463247324832493250325132523253325432553256325732583259326032613262326332643265326632673268326932703271327232733274327532763277327832793280328132823283328432853286328732883289329032913292329332943295329632973298329933003301330233033304330533063307330833093310331133123313331433153316331733183319332033213322332333243325332633273328332933303331333233333334333533363337333833393340334133423343334433453346334733483349335033513352335333543355335633573358335933603361336233633364336533663367336833693370337133723373337433753376337733783379338033813382338333843385338633873388338933903391339233933394339533963397339833993400340134023403340434053406340734083409341034113412341334143415341634173418341934203421 |
- {
- This file is part of the Free Pascal/NewPascal run time library.
- Copyright (c) 2014 by Maciej Izak (hnb)
- member of the NewPascal development team (http://newpascal.org)
- Copyright(c) 2004-2018 DaThoX
- It contains the generics collections library
- See the file COPYING.FPC, included in this distribution,
- for details about the copyright.
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
- Acknowledgment
- Thanks to Sphere 10 Software (http://sphere10.com) for sponsoring
- many new types and major refactoring of entire library
- Thanks to mORMot (http://synopse.info) project for the best implementations
- of hashing functions like crc32c and xxHash32 :)
- **********************************************************************}
- unit Generics.Defaults;
- {$MODE DELPHI}{$H+}
- {$POINTERMATH ON}
- {$MACRO ON}
- {$COPERATORS ON}
- {$HINTS OFF}
- {$WARNINGS OFF}
- {$NOTES OFF}
- {$OVERFLOWCHECKS OFF}
- {$RANGECHECKS OFF}
- interface
- uses
- Classes, SysUtils, Generics.Hashes, TypInfo, Variants, Math, Generics.Strings, Generics.Helpers;
- type
- IComparer<T> = interface
- function Compare(const Left, Right: T): Integer; overload;
- end;
- TOnComparison<T> = function(const Left, Right: T): Integer of object;
- TComparisonFunc<T> = function(const Left, Right: T): Integer;
- TComparer<T> = class(TInterfacedObject, IComparer<T>)
- public
- class function Default: IComparer<T>; static;
- function Compare(const ALeft, ARight: T): Integer; virtual; abstract; overload;
- class function Construct(const AComparison: TOnComparison<T>): IComparer<T>; overload;
- class function Construct(const AComparison: TComparisonFunc<T>): IComparer<T>; overload;
- end;
- TDelegatedComparerEvents<T> = class(TComparer<T>)
- private
- FComparison: TOnComparison<T>;
- public
- function Compare(const ALeft, ARight: T): Integer; override;
- constructor Create(AComparison: TOnComparison<T>);
- end;
- TDelegatedComparerFunc<T> = class(TComparer<T>)
- private
- FComparison: TComparisonFunc<T>;
- public
- function Compare(const ALeft, ARight: T): Integer; override;
- constructor Create(AComparison: TComparisonFunc<T>);
- end;
- IEqualityComparer<T> = interface
- function Equals(const ALeft, ARight: T): Boolean;
- function GetHashCode(const AValue: T): UInt32;
- end;
- IExtendedEqualityComparer<T> = interface(IEqualityComparer<T>)
- procedure GetHashList(const AValue: T; AHashList: PUInt32); // for double hashing and more
- end;
- ShortString1 = string[1];
- ShortString2 = string[2];
- ShortString3 = string[3];
- { TAbstractInterface }
- TInterface = class
- public
- function QueryInterface(constref {%H-}IID: TGUID;{%H-} out Obj): HResult; {$IFNDEF WINDOWS}cdecl{$ELSE}stdcall{$ENDIF}; virtual;
- function _AddRef: LongInt; {$IFNDEF WINDOWS}cdecl{$ELSE}stdcall{$ENDIF}; virtual; abstract;
- function _Release: LongInt; {$IFNDEF WINDOWS}cdecl{$ELSE}stdcall{$ENDIF}; virtual; abstract;
- end;
- { TRawInterface }
- TRawInterface = class(TInterface)
- public
- function _AddRef: LongInt; override;
- function _Release: LongInt; override;
- end;
- { TComTypeSizeInterface }
- // INTERNAL USE ONLY!
- TComTypeSizeInterface = class(TInterface)
- public
- // warning ! self as PSpoofInterfacedTypeSizeObject
- function _AddRef: LongInt; override;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- function _Release: LongInt; override;
- end;
- { TSingletonImplementation }
- TSingletonImplementation = class(TRawInterface, IInterface)
- public
- function QueryInterface(constref IID: TGUID; out Obj): HResult; override;
- end;
- TCompare = class
- protected
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class function _Binary(const ALeft, ARight): Integer;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class function _DynArray(const ALeft, ARight: Pointer): Integer;
- public
- class function Integer(const ALeft, ARight: Integer): Integer;
- class function Int8(const ALeft, ARight: Int8): Integer;
- class function Int16(const ALeft, ARight: Int16): Integer;
- class function Int32(const ALeft, ARight: Int32): Integer;
- class function Int64(const ALeft, ARight: Int64): Integer;
- class function UInt8(const ALeft, ARight: UInt8): Integer;
- class function UInt16(const ALeft, ARight: UInt16): Integer;
- class function UInt32(const ALeft, ARight: UInt32): Integer;
- class function UInt64(const ALeft, ARight: UInt64): Integer;
- class function Single(const ALeft, ARight: Single): Integer;
- class function Double(const ALeft, ARight: Double): Integer;
- class function Extended(const ALeft, ARight: Extended): Integer;
- class function Currency(const ALeft, ARight: Currency): Integer;
- class function Comp(const ALeft, ARight: Comp): Integer;
- class function Binary(const ALeft, ARight; const ASize: SizeInt): Integer;
- class function DynArray(const ALeft, ARight: Pointer; const AElementSize: SizeInt): Integer;
- class function ShortString1(const ALeft, ARight: ShortString1): Integer;
- class function ShortString2(const ALeft, ARight: ShortString2): Integer;
- class function ShortString3(const ALeft, ARight: ShortString3): Integer;
- class function &String(const ALeft, ARight: string): Integer;
- class function ShortString(const ALeft, ARight: ShortString): Integer;
- class function AnsiString(const ALeft, ARight: AnsiString): Integer;
- class function WideString(const ALeft, ARight: WideString): Integer;
- class function UnicodeString(const ALeft, ARight: UnicodeString): Integer;
- class function Method(const ALeft, ARight: TMethod): Integer;
- class function Variant(const ALeft, ARight: PVariant): Integer;
- class function Pointer(const ALeft, ARight: PtrUInt): Integer;
- end;
- { TEquals }
- TEquals = class
- protected
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class function _Binary(const ALeft, ARight): Boolean;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class function _DynArray(const ALeft, ARight: Pointer): Boolean;
- public
- class function Integer(const ALeft, ARight: Integer): Boolean;
- class function Int8(const ALeft, ARight: Int8): Boolean;
- class function Int16(const ALeft, ARight: Int16): Boolean;
- class function Int32(const ALeft, ARight: Int32): Boolean;
- class function Int64(const ALeft, ARight: Int64): Boolean;
- class function UInt8(const ALeft, ARight: UInt8): Boolean;
- class function UInt16(const ALeft, ARight: UInt16): Boolean;
- class function UInt32(const ALeft, ARight: UInt32): Boolean;
- class function UInt64(const ALeft, ARight: UInt64): Boolean;
- class function Single(const ALeft, ARight: Single): Boolean;
- class function Double(const ALeft, ARight: Double): Boolean;
- class function Extended(const ALeft, ARight: Extended): Boolean;
- class function Currency(const ALeft, ARight: Currency): Boolean;
- class function Comp(const ALeft, ARight: Comp): Boolean;
- class function Binary(const ALeft, ARight; const ASize: SizeInt): Boolean;
- class function DynArray(const ALeft, ARight: Pointer; const AElementSize: SizeInt): Boolean;
- class function &Class(const ALeft, ARight: TObject): Boolean;
- class function ShortString1(const ALeft, ARight: ShortString1): Boolean;
- class function ShortString2(const ALeft, ARight: ShortString2): Boolean;
- class function ShortString3(const ALeft, ARight: ShortString3): Boolean;
- class function &String(const ALeft, ARight: String): Boolean;
- class function ShortString(const ALeft, ARight: ShortString): Boolean;
- class function AnsiString(const ALeft, ARight: AnsiString): Boolean;
- class function WideString(const ALeft, ARight: WideString): Boolean;
- class function UnicodeString(const ALeft, ARight: UnicodeString): Boolean;
- class function Method(const ALeft, ARight: TMethod): Boolean;
- class function Variant(const ALeft, ARight: PVariant): Boolean;
- class function Pointer(const ALeft, ARight: PtrUInt): Boolean;
- end;
- THashServiceClass = class of THashService;
- TExtendedHashServiceClass = class of TExtendedHashService;
- THashFactoryClass = class of THashFactory;
- TExtendedHashFactoryClass = class of TExtendedHashFactory;
- { TComparerService }
- {$DEFINE STD_RAW_INTERFACE_METHODS :=
- QueryInterface: @TRawInterface.QueryInterface;
- _AddRef : @TRawInterface._AddRef;
- _Release : @TRawInterface._Release
- }
- {$DEFINE STD_COM_TYPESIZE_INTERFACE_METHODS :=
- QueryInterface: @TComTypeSizeInterface.QueryInterface;
- _AddRef : @TComTypeSizeInterface._AddRef;
- _Release : @TComTypeSizeInterface._Release
- }
- TGetHashListOptions = set of (ghloHashListAsInitData);
- THashFactory = class
- private type
- PPEqualityComparerVMT = ^PEqualityComparerVMT;
- PEqualityComparerVMT = ^TEqualityComparerVMT;
- TEqualityComparerVMT = packed record
- QueryInterface: CodePointer;
- _AddRef: CodePointer;
- _Release: CodePointer;
- Equals: CodePointer;
- GetHashCode: CodePointer;
- __Reserved: CodePointer; // initially or TExtendedEqualityComparerVMT compatibility
- // (important when ExtendedEqualityComparer is calling Binary method)
- __ClassRef: THashFactoryClass; // hidden field in VMT. For class ref THashFactoryClass
- end;
- private
- (***********************************************************************************************************************
- Hashes
- (**********************************************************************************************************************)
- class function Int8 (const AValue: Int8 ): UInt32; overload;
- class function Int16 (const AValue: Int16 ): UInt32; overload;
- class function Int32 (const AValue: Int32 ): UInt32; overload;
- class function Int64 (const AValue: Int64 ): UInt32; overload;
- class function UInt8 (const AValue: UInt8 ): UInt32; overload;
- class function UInt16 (const AValue: UInt16 ): UInt32; overload;
- class function UInt32 (const AValue: UInt32 ): UInt32; overload;
- class function UInt64 (const AValue: UInt64 ): UInt32; overload;
- class function Single (const AValue: Single ): UInt32; overload;
- class function Double (const AValue: Double ): UInt32; overload;
- class function Extended (const AValue: Extended ): UInt32; overload;
- class function Currency (const AValue: Currency ): UInt32; overload;
- class function Comp (const AValue: Comp ): UInt32; overload;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class function Binary (const AValue ): UInt32; overload;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class function DynArray (const AValue: Pointer ): UInt32; overload;
- class function &Class (const AValue: TObject ): UInt32; overload;
- class function ShortString1 (const AValue: ShortString1 ): UInt32; overload;
- class function ShortString2 (const AValue: ShortString2 ): UInt32; overload;
- class function ShortString3 (const AValue: ShortString3 ): UInt32; overload;
- class function ShortString (const AValue: ShortString ): UInt32; overload;
- class function AnsiString (const AValue: AnsiString ): UInt32; overload;
- class function WideString (const AValue: WideString ): UInt32; overload;
- class function UnicodeString(const AValue: UnicodeString): UInt32; overload;
- class function Method (const AValue: TMethod ): UInt32; overload;
- class function Variant (const AValue: PVariant ): UInt32; overload;
- class function Pointer (const AValue: Pointer ): UInt32; overload;
- public
- const MAX_HASHLIST_COUNT = 1;
- const HASH_FUNCTIONS_COUNT = 1;
- const HASHLIST_COUNT_PER_FUNCTION: array[1..HASH_FUNCTIONS_COUNT] of Integer = (1);
- const HASH_FUNCTIONS_MASK_SIZE = 1;
- class function GetHashService: THashServiceClass; virtual; abstract;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; virtual; abstract; reintroduce;
- end;
- TExtendedHashFactory = class(THashFactory)
- private type
- PPExtendedEqualityComparerVMT = ^PExtendedEqualityComparerVMT;
- PExtendedEqualityComparerVMT = ^TExtendedEqualityComparerVMT;
- TExtendedEqualityComparerVMT = packed record
- QueryInterface: CodePointer;
- _AddRef: CodePointer;
- _Release: CodePointer;
- Equals: CodePointer;
- GetHashCode: CodePointer;
- GetHashList: CodePointer;
- __ClassRef: TExtendedHashFactoryClass; // hidden field in VMT. For class ref THashFactoryClass
- end;
- private
- (***********************************************************************************************************************
- Hashes 2
- (**********************************************************************************************************************)
- class procedure Int8 (const AValue: Int8 ; AHashList: PUInt32); overload;
- class procedure Int16 (const AValue: Int16 ; AHashList: PUInt32); overload;
- class procedure Int32 (const AValue: Int32 ; AHashList: PUInt32); overload;
- class procedure Int64 (const AValue: Int64 ; AHashList: PUInt32); overload;
- class procedure UInt8 (const AValue: UInt8 ; AHashList: PUInt32); overload;
- class procedure UInt16 (const AValue: UInt16 ; AHashList: PUInt32); overload;
- class procedure UInt32 (const AValue: UInt32 ; AHashList: PUInt32); overload;
- class procedure UInt64 (const AValue: UInt64 ; AHashList: PUInt32); overload;
- class procedure Single (const AValue: Single ; AHashList: PUInt32); overload;
- class procedure Double (const AValue: Double ; AHashList: PUInt32); overload;
- class procedure Extended (const AValue: Extended ; AHashList: PUInt32); overload;
- class procedure Currency (const AValue: Currency ; AHashList: PUInt32); overload;
- class procedure Comp (const AValue: Comp ; AHashList: PUInt32); overload;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class procedure Binary (const AValue ; AHashList: PUInt32); overload;
- // warning ! self as PSpoofInterfacedTypeSizeObject
- class procedure DynArray (const AValue: Pointer ; AHashList: PUInt32); overload;
- class procedure &Class (const AValue: TObject ; AHashList: PUInt32); overload;
- class procedure ShortString1 (const AValue: ShortString1 ; AHashList: PUInt32); overload;
- class procedure ShortString2 (const AValue: ShortString2 ; AHashList: PUInt32); overload;
- class procedure ShortString3 (const AValue: ShortString3 ; AHashList: PUInt32); overload;
- class procedure ShortString (const AValue: ShortString ; AHashList: PUInt32); overload;
- class procedure AnsiString (const AValue: AnsiString ; AHashList: PUInt32); overload;
- class procedure WideString (const AValue: WideString ; AHashList: PUInt32); overload;
- class procedure UnicodeString(const AValue: UnicodeString; AHashList: PUInt32); overload;
- class procedure Method (const AValue: TMethod ; AHashList: PUInt32); overload;
- class procedure Variant (const AValue: PVariant ; AHashList: PUInt32); overload;
- class procedure Pointer (const AValue: Pointer ; AHashList: PUInt32); overload;
- public
- class procedure GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32; AOptions: TGetHashListOptions = []); virtual; abstract;
- end;
- TComparerService = class abstract
- private type
- TSelectMethod = function(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer of object;
- private
- class function SelectIntegerEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- class function SelectFloatEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- class function SelectShortStringEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- class function SelectBinaryEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- class function SelectDynArrayEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- private type
- PSpoofInterfacedTypeSizeObject = ^TSpoofInterfacedTypeSizeObject;
- TSpoofInterfacedTypeSizeObject = record
- VMT: Pointer;
- RefCount: LongInt;
- Size: SizeInt;
- ConstParaRef: Boolean;
- end;
- PInstance = ^TInstance;
- TInstance = record
- class function Create(ASelector: Boolean; AInstance: Pointer): TComparerService.TInstance; static;
- class function CreateSelector(ASelectorInstance: CodePointer): TComparerService.TInstance; static;
- case Selector: Boolean of
- false: (Instance: Pointer);
- true: (SelectorInstance: CodePointer);
- end;
- PComparerVMT = ^TComparerVMT;
- TComparerVMT = packed record
- QueryInterface: CodePointer;
- _AddRef: CodePointer;
- _Release: CodePointer;
- Compare: CodePointer;
- end;
- TSelectFunc = function(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- private
- class function CreateInterface(AVMT: Pointer; ASize: SizeInt; AConstParaRef: Boolean): PSpoofInterfacedTypeSizeObject; static;
- class function SelectIntegerComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- class function SelectInt64Comparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- class function SelectFloatComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- class function SelectShortStringComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- class function SelectBinaryComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- class function SelectDynArrayComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- private const
- UseBinaryMethods: set of TTypeKind = [tkUnknown, tkSet, tkFile, tkArray, tkRecord, tkObject];
- // IComparer VMT
- Comparer_Int8_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Int8);
- Comparer_Int16_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Int16 );
- Comparer_Int32_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Int32 );
- Comparer_Int64_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Int64 );
- Comparer_UInt8_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.UInt8 );
- Comparer_UInt16_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.UInt16);
- Comparer_UInt32_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.UInt32);
- Comparer_UInt64_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.UInt64);
- Comparer_Single_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Single );
- Comparer_Double_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Double );
- Comparer_Extended_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Extended);
- Comparer_Currency_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Currency);
- Comparer_Comp_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Comp );
- Comparer_Binary_VMT : TComparerVMT = (STD_COM_TYPESIZE_INTERFACE_METHODS; Compare: @TCompare._Binary );
- Comparer_DynArray_VMT: TComparerVMT = (STD_COM_TYPESIZE_INTERFACE_METHODS; Compare: @TCompare._DynArray);
- Comparer_ShortString1_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.ShortString1 );
- Comparer_ShortString2_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.ShortString2 );
- Comparer_ShortString3_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.ShortString3 );
- Comparer_ShortString_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.ShortString );
- Comparer_AnsiString_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.AnsiString );
- Comparer_WideString_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.WideString );
- Comparer_UnicodeString_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.UnicodeString);
- Comparer_Method_VMT : TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Method );
- Comparer_Variant_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Variant);
- Comparer_Pointer_VMT: TComparerVMT = (STD_RAW_INTERFACE_METHODS; Compare: @TCompare.Pointer);
- // Instances
- Comparer_Int8_Instance : Pointer = @Comparer_Int8_VMT ;
- Comparer_Int16_Instance : Pointer = @Comparer_Int16_VMT ;
- Comparer_Int32_Instance : Pointer = @Comparer_Int32_VMT ;
- Comparer_Int64_Instance : Pointer = @Comparer_Int64_VMT ;
- Comparer_UInt8_Instance : Pointer = @Comparer_UInt8_VMT ;
- Comparer_UInt16_Instance: Pointer = @Comparer_UInt16_VMT;
- Comparer_UInt32_Instance: Pointer = @Comparer_UInt32_VMT;
- Comparer_UInt64_Instance: Pointer = @Comparer_UInt64_VMT;
- Comparer_Single_Instance : Pointer = @Comparer_Single_VMT ;
- Comparer_Double_Instance : Pointer = @Comparer_Double_VMT ;
- Comparer_Extended_Instance: Pointer = @Comparer_Extended_VMT;
- Comparer_Currency_Instance: Pointer = @Comparer_Currency_VMT;
- Comparer_Comp_Instance : Pointer = @Comparer_Comp_VMT ;
- //Comparer_Binary_Instance : Pointer = @Comparer_Binary_VMT ; // dynamic instance
- //Comparer_DynArray_Instance: Pointer = @Comparer_DynArray_VMT; // dynamic instance
- Comparer_ShortString1_Instance : Pointer = @Comparer_ShortString1_VMT ;
- Comparer_ShortString2_Instance : Pointer = @Comparer_ShortString2_VMT ;
- Comparer_ShortString3_Instance : Pointer = @Comparer_ShortString3_VMT ;
- Comparer_ShortString_Instance : Pointer = @Comparer_ShortString_VMT ;
- Comparer_AnsiString_Instance : Pointer = @Comparer_AnsiString_VMT ;
- Comparer_WideString_Instance : Pointer = @Comparer_WideString_VMT ;
- Comparer_UnicodeString_Instance: Pointer = @Comparer_UnicodeString_VMT;
- Comparer_Method_Instance : Pointer = @Comparer_Method_VMT ;
- Comparer_Variant_Instance: Pointer = @Comparer_Variant_VMT;
- Comparer_Pointer_Instance: Pointer = @Comparer_Pointer_VMT;
- ComparerInstances: array[TTypeKind] of TInstance =
- (
- // tkUnknown
- (Selector: True; SelectorInstance: @TComparerService.SelectBinaryComparer),
- // tkInteger
- (Selector: True; SelectorInstance: @TComparerService.SelectIntegerComparer),
- // tkChar
- (Selector: False; Instance: @Comparer_UInt8_Instance),
- // tkEnumeration
- (Selector: True; SelectorInstance: @TComparerService.SelectIntegerComparer),
- // tkFloat
- (Selector: True; SelectorInstance: @TComparerService.SelectFloatComparer),
- // tkSet
- (Selector: True; SelectorInstance: @TComparerService.SelectBinaryComparer),
- // tkMethod
- (Selector: False; Instance: @Comparer_Method_Instance),
- // tkSString
- (Selector: True; SelectorInstance: @TComparerService.SelectShortStringComparer),
- // tkLString - only internal use / deprecated in compiler
- (Selector: False; Instance: @Comparer_AnsiString_Instance), // <- unsure
- // tkAString
- (Selector: False; Instance: @Comparer_AnsiString_Instance),
- // tkWString
- (Selector: False; Instance: @Comparer_WideString_Instance),
- // tkVariant
- (Selector: False; Instance: @Comparer_Variant_Instance),
- // tkArray
- (Selector: True; SelectorInstance: @TComparerService.SelectBinaryComparer),
- // tkRecord
- (Selector: True; SelectorInstance: @TComparerService.SelectBinaryComparer),
- // tkInterface
- (Selector: False; Instance: @Comparer_Pointer_Instance),
- // tkClass
- (Selector: False; Instance: @Comparer_Pointer_Instance),
- // tkObject
- (Selector: True; SelectorInstance: @TComparerService.SelectBinaryComparer),
- // tkWChar
- (Selector: False; Instance: @Comparer_UInt16_Instance),
- // tkBool
- (Selector: True; SelectorInstance: @TComparerService.SelectIntegerComparer),
- // tkInt64
- (Selector: False; Instance: @Comparer_Int64_Instance),
- // tkQWord
- (Selector: False; Instance: @Comparer_UInt64_Instance),
- // tkDynArray
- (Selector: True; SelectorInstance: @TComparerService.SelectDynArrayComparer),
- // tkInterfaceRaw
- (Selector: False; Instance: @Comparer_Pointer_Instance),
- // tkProcVar
- (Selector: False; Instance: @Comparer_Pointer_Instance),
- // tkUString
- (Selector: False; Instance: @Comparer_UnicodeString_Instance),
- // tkUChar - WTF? ... http://bugs.freepascal.org/view.php?id=24609
- (Selector: False; Instance: @Comparer_UInt16_Instance), // <- unsure maybe Comparer_UInt32_Instance
- // tkHelper
- (Selector: False; Instance: @Comparer_Pointer_Instance),
- // tkFile
- (Selector: True; SelectorInstance: @TComparerService.SelectBinaryComparer), // <- unsure what type?
- // tkClassRef
- (Selector: False; Instance: @Comparer_Pointer_Instance),
- // tkPointer
- (Selector: False; Instance: @Comparer_Pointer_Instance)
- );
- public
- class function LookupComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer; static;
- end;
- THashService = class(TComparerService)
- public
- class function LookupEqualityComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- end;
- TExtendedHashService = class(THashService)
- public
- class function LookupEqualityComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function LookupExtendedEqualityComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer; virtual; abstract;
- end;
- {$DEFINE HASH_FACTORY := PPEqualityComparerVMT(Self)^.__ClassRef}
- {$DEFINE EXTENDED_HASH_FACTORY := PPExtendedEqualityComparerVMT(Self)^.__ClassRef}
- { THashService }
- THashService<T: THashFactory> = class(THashService)
- private
- class function SelectIntegerEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectFloatEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectShortStringEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectBinaryEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectDynArrayEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- private const
- // IEqualityComparer VMT templates
- {$WARNINGS OFF}
- EqualityComparer_Int8_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int8 ; GetHashCode: @THashFactory.Int8 );
- EqualityComparer_Int16_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int16 ; GetHashCode: @THashFactory.Int16 );
- EqualityComparer_Int32_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int32 ; GetHashCode: @THashFactory.Int32 );
- EqualityComparer_Int64_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int64 ; GetHashCode: @THashFactory.Int64 );
- EqualityComparer_UInt8_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt8 ; GetHashCode: @THashFactory.UInt8 );
- EqualityComparer_UInt16_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt16; GetHashCode: @THashFactory.UInt16);
- EqualityComparer_UInt32_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt32; GetHashCode: @THashFactory.UInt32);
- EqualityComparer_UInt64_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt64; GetHashCode: @THashFactory.UInt64);
- EqualityComparer_Single_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Single ; GetHashCode: @THashFactory.Single );
- EqualityComparer_Double_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Double ; GetHashCode: @THashFactory.Double );
- EqualityComparer_Extended_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Extended; GetHashCode: @THashFactory.Extended);
- EqualityComparer_Currency_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Currency; GetHashCode: @THashFactory.Currency);
- EqualityComparer_Comp_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Comp ; GetHashCode: @THashFactory.Comp );
- EqualityComparer_Binary_VMT : THashFactory.TEqualityComparerVMT = (STD_COM_TYPESIZE_INTERFACE_METHODS; Equals: @TEquals._Binary ; GetHashCode: @THashFactory.Binary );
- EqualityComparer_DynArray_VMT: THashFactory.TEqualityComparerVMT = (STD_COM_TYPESIZE_INTERFACE_METHODS; Equals: @TEquals._DynArray; GetHashCode: @THashFactory.DynArray);
- EqualityComparer_Class_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.&Class; GetHashCode: @THashFactory.&Class);
- EqualityComparer_ShortString1_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString1 ; GetHashCode: @THashFactory.ShortString1 );
- EqualityComparer_ShortString2_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString2 ; GetHashCode: @THashFactory.ShortString2 );
- EqualityComparer_ShortString3_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString3 ; GetHashCode: @THashFactory.ShortString3 );
- EqualityComparer_ShortString_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString ; GetHashCode: @THashFactory.ShortString );
- EqualityComparer_AnsiString_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.AnsiString ; GetHashCode: @THashFactory.AnsiString );
- EqualityComparer_WideString_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.WideString ; GetHashCode: @THashFactory.WideString );
- EqualityComparer_UnicodeString_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UnicodeString; GetHashCode: @THashFactory.UnicodeString);
- EqualityComparer_Method_VMT : THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Method ; GetHashCode: @THashFactory.Method );
- EqualityComparer_Variant_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Variant; GetHashCode: @THashFactory.Variant);
- EqualityComparer_Pointer_VMT: THashFactory.TEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Pointer; GetHashCode: @THashFactory.Pointer);
- {.$WARNINGS ON} // do not enable warnings ever in this unit, or you will get many warnings about uninitialized TEqualityComparerVMT fields
- private class var
- // IEqualityComparer VMT
- FEqualityComparer_Int8_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Int16_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Int32_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Int64_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_UInt8_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_UInt16_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_UInt32_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_UInt64_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Single_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Double_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Extended_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Currency_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Comp_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Binary_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_DynArray_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Class_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_ShortString1_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_ShortString2_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_ShortString3_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_ShortString_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_AnsiString_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_WideString_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_UnicodeString_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Method_VMT : THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Variant_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Pointer_VMT: THashFactory.TEqualityComparerVMT;
- FEqualityComparer_Int8_Instance : Pointer;
- FEqualityComparer_Int16_Instance : Pointer;
- FEqualityComparer_Int32_Instance : Pointer;
- FEqualityComparer_Int64_Instance : Pointer;
- FEqualityComparer_UInt8_Instance : Pointer;
- FEqualityComparer_UInt16_Instance : Pointer;
- FEqualityComparer_UInt32_Instance : Pointer;
- FEqualityComparer_UInt64_Instance : Pointer;
- FEqualityComparer_Single_Instance : Pointer;
- FEqualityComparer_Double_Instance : Pointer;
- FEqualityComparer_Extended_Instance : Pointer;
- FEqualityComparer_Currency_Instance : Pointer;
- FEqualityComparer_Comp_Instance : Pointer;
- //FEqualityComparer_Binary_Instance : Pointer; // dynamic instance
- //FEqualityComparer_DynArray_Instance : Pointer; // dynamic instance
- FEqualityComparer_ShortString1_Instance : Pointer;
- FEqualityComparer_ShortString2_Instance : Pointer;
- FEqualityComparer_ShortString3_Instance : Pointer;
- FEqualityComparer_ShortString_Instance : Pointer;
- FEqualityComparer_AnsiString_Instance : Pointer;
- FEqualityComparer_WideString_Instance : Pointer;
- FEqualityComparer_UnicodeString_Instance: Pointer;
- FEqualityComparer_Method_Instance : Pointer;
- FEqualityComparer_Variant_Instance : Pointer;
- FEqualityComparer_Pointer_Instance : Pointer;
- FEqualityComparerInstances: array[TTypeKind] of TInstance;
- private
- class constructor Create;
- public
- class function LookupEqualityComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- end;
- { TExtendedHashService }
- TExtendedHashService<T: TExtendedHashFactory> = class(TExtendedHashService)
- private
- class function SelectIntegerEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectFloatEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectShortStringEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectBinaryEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- class function SelectDynArrayEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- private const
- // IExtendedEqualityComparer VMT templates
- {$WARNINGS OFF}
- ExtendedEqualityComparer_Int8_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int8 ; GetHashCode: @THashFactory.Int8 ; GetHashList: @TExtendedHashFactory.Int8 );
- ExtendedEqualityComparer_Int16_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int16 ; GetHashCode: @THashFactory.Int16 ; GetHashList: @TExtendedHashFactory.Int16 );
- ExtendedEqualityComparer_Int32_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int32 ; GetHashCode: @THashFactory.Int32 ; GetHashList: @TExtendedHashFactory.Int32 );
- ExtendedEqualityComparer_Int64_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Int64 ; GetHashCode: @THashFactory.Int64 ; GetHashList: @TExtendedHashFactory.Int64 );
- ExtendedEqualityComparer_UInt8_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt8 ; GetHashCode: @THashFactory.UInt8 ; GetHashList: @TExtendedHashFactory.UInt8 );
- ExtendedEqualityComparer_UInt16_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt16; GetHashCode: @THashFactory.UInt16; GetHashList: @TExtendedHashFactory.UInt16);
- ExtendedEqualityComparer_UInt32_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt32; GetHashCode: @THashFactory.UInt32; GetHashList: @TExtendedHashFactory.UInt32);
- ExtendedEqualityComparer_UInt64_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UInt64; GetHashCode: @THashFactory.UInt64; GetHashList: @TExtendedHashFactory.UInt64);
- ExtendedEqualityComparer_Single_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Single ; GetHashCode: @THashFactory.Single ; GetHashList: @TExtendedHashFactory.Single );
- ExtendedEqualityComparer_Double_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Double ; GetHashCode: @THashFactory.Double ; GetHashList: @TExtendedHashFactory.Double );
- ExtendedEqualityComparer_Extended_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Extended; GetHashCode: @THashFactory.Extended; GetHashList: @TExtendedHashFactory.Extended);
- ExtendedEqualityComparer_Currency_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Currency; GetHashCode: @THashFactory.Currency; GetHashList: @TExtendedHashFactory.Currency);
- ExtendedEqualityComparer_Comp_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Comp ; GetHashCode: @THashFactory.Comp ; GetHashList: @TExtendedHashFactory.Comp );
- ExtendedEqualityComparer_Binary_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_COM_TYPESIZE_INTERFACE_METHODS; Equals: @TEquals._Binary ; GetHashCode: @THashFactory.Binary ; GetHashList: @TExtendedHashFactory.Binary );
- ExtendedEqualityComparer_DynArray_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_COM_TYPESIZE_INTERFACE_METHODS; Equals: @TEquals._DynArray; GetHashCode: @THashFactory.DynArray; GetHashList: @TExtendedHashFactory.DynArray);
- ExtendedEqualityComparer_Class_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.&Class; GetHashCode: @THashFactory.&Class; GetHashList: @TExtendedHashFactory.&Class);
- ExtendedEqualityComparer_ShortString1_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString1 ; GetHashCode: @THashFactory.ShortString1 ; GetHashList: @TExtendedHashFactory.ShortString1 );
- ExtendedEqualityComparer_ShortString2_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString2 ; GetHashCode: @THashFactory.ShortString2 ; GetHashList: @TExtendedHashFactory.ShortString2 );
- ExtendedEqualityComparer_ShortString3_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString3 ; GetHashCode: @THashFactory.ShortString3 ; GetHashList: @TExtendedHashFactory.ShortString3 );
- ExtendedEqualityComparer_ShortString_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.ShortString ; GetHashCode: @THashFactory.ShortString ; GetHashList: @TExtendedHashFactory.ShortString );
- ExtendedEqualityComparer_AnsiString_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.AnsiString ; GetHashCode: @THashFactory.AnsiString ; GetHashList: @TExtendedHashFactory.AnsiString );
- ExtendedEqualityComparer_WideString_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.WideString ; GetHashCode: @THashFactory.WideString ; GetHashList: @TExtendedHashFactory.WideString );
- ExtendedEqualityComparer_UnicodeString_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.UnicodeString; GetHashCode: @THashFactory.UnicodeString; GetHashList: @TExtendedHashFactory.UnicodeString);
- ExtendedEqualityComparer_Method_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Method ; GetHashCode: @THashFactory.Method ; GetHashList: @TExtendedHashFactory.Method );
- ExtendedEqualityComparer_Variant_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Variant; GetHashCode: @THashFactory.Variant; GetHashList: @TExtendedHashFactory.Variant);
- ExtendedEqualityComparer_Pointer_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT = (STD_RAW_INTERFACE_METHODS; Equals: @TEquals.Pointer; GetHashCode: @THashFactory.Pointer; GetHashList: @TExtendedHashFactory.Pointer);
- {.$WARNINGS ON} // do not enable warnings ever in this unit, or you will get many warnings about uninitialized TEqualityComparerVMT fields
- private class var
- // IExtendedEqualityComparer VMT
- FExtendedEqualityComparer_Int8_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Int16_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Int32_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Int64_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_UInt8_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_UInt16_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_UInt32_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_UInt64_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Single_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Double_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Extended_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Currency_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Comp_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Binary_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_DynArray_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Class_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_ShortString1_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_ShortString2_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_ShortString3_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_ShortString_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_AnsiString_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_WideString_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_UnicodeString_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Method_VMT : TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Variant_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Pointer_VMT: TExtendedHashFactory.TExtendedEqualityComparerVMT;
- FExtendedEqualityComparer_Int8_Instance : Pointer;
- FExtendedEqualityComparer_Int16_Instance : Pointer;
- FExtendedEqualityComparer_Int32_Instance : Pointer;
- FExtendedEqualityComparer_Int64_Instance : Pointer;
- FExtendedEqualityComparer_UInt8_Instance : Pointer;
- FExtendedEqualityComparer_UInt16_Instance : Pointer;
- FExtendedEqualityComparer_UInt32_Instance : Pointer;
- FExtendedEqualityComparer_UInt64_Instance : Pointer;
- FExtendedEqualityComparer_Single_Instance : Pointer;
- FExtendedEqualityComparer_Double_Instance : Pointer;
- FExtendedEqualityComparer_Extended_Instance : Pointer;
- FExtendedEqualityComparer_Currency_Instance : Pointer;
- FExtendedEqualityComparer_Comp_Instance : Pointer;
- //FExtendedEqualityComparer_Binary_Instance : Pointer; // dynamic instance
- //FExtendedEqualityComparer_DynArray_Instance : Pointer; // dynamic instance
- FExtendedEqualityComparer_ShortString1_Instance : Pointer;
- FExtendedEqualityComparer_ShortString2_Instance : Pointer;
- FExtendedEqualityComparer_ShortString3_Instance : Pointer;
- FExtendedEqualityComparer_ShortString_Instance : Pointer;
- FExtendedEqualityComparer_AnsiString_Instance : Pointer;
- FExtendedEqualityComparer_WideString_Instance : Pointer;
- FExtendedEqualityComparer_UnicodeString_Instance: Pointer;
- FExtendedEqualityComparer_Method_Instance : Pointer;
- FExtendedEqualityComparer_Variant_Instance : Pointer;
- FExtendedEqualityComparer_Pointer_Instance : Pointer;
- // all instances
- FExtendedEqualityComparerInstances: array[TTypeKind] of TInstance;
- private
- class constructor Create;
- public
- class function LookupExtendedEqualityComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer; override;
- end;
- TOnEqualityComparison<T> = function(const ALeft, ARight: T): Boolean of object;
- TEqualityComparisonFunc<T> = function(const ALeft, ARight: T): Boolean;
- TOnHasher<T> = function(const AValue: T): UInt32 of object;
- TOnExtendedHasher<T> = procedure(const AValue: T; AHashList: PUInt32) of object;
- THasherFunc<T> = function(const AValue: T): UInt32;
- TExtendedHasherFunc<T> = procedure(const AValue: T; AHashList: PUInt32);
- TEqualityComparer<T> = class(TInterfacedObject, IEqualityComparer<T>)
- public
- class function Default: IEqualityComparer<T>; static; overload;
- class function Default(AHashFactoryClass: THashFactoryClass): IEqualityComparer<T>; static; overload;
- class function Construct(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>): IEqualityComparer<T>; overload;
- class function Construct(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>): IEqualityComparer<T>; overload;
- function Equals(const ALeft, ARight: T): Boolean; virtual; overload; abstract;
- function GetHashCode(const AValue: T): UInt32; virtual; overload; abstract;
- end;
- { TDelegatedEqualityComparerEvent }
- TDelegatedEqualityComparerEvents<T> = class(TEqualityComparer<T>)
- private
- FEqualityComparison: TOnEqualityComparison<T>;
- FHasher: TOnHasher<T>;
- public
- function Equals(const ALeft, ARight: T): Boolean; override;
- function GetHashCode(const AValue: T): UInt32; override;
- constructor Create(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>);
- end;
- TDelegatedEqualityComparerFunc<T> = class(TEqualityComparer<T>)
- private
- FEqualityComparison: TEqualityComparisonFunc<T>;
- FHasher: THasherFunc<T>;
- public
- function Equals(const ALeft, ARight: T): Boolean; override;
- function GetHashCode(const AValue: T): UInt32; override;
- constructor Create(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>);
- end;
- { TExtendedEqualityComparer }
- TExtendedEqualityComparer<T> = class(TEqualityComparer<T>, IExtendedEqualityComparer<T>)
- public
- class function Default: IExtendedEqualityComparer<T>; static; overload; reintroduce;
- class function Default(AExtenedHashFactoryClass: TExtendedHashFactoryClass): IExtendedEqualityComparer<T>; static; overload; reintroduce;
- class function Construct(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>; const AExtendedHasher: TOnExtendedHasher<T>): IExtendedEqualityComparer<T>; overload; reintroduce;
- class function Construct(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>; const AExtendedHasher: TExtendedHasherFunc<T>): IExtendedEqualityComparer<T>; overload; reintroduce;
- class function Construct(const AEqualityComparison: TOnEqualityComparison<T>;
- const AExtendedHasher: TOnExtendedHasher<T>): IExtendedEqualityComparer<T>; overload; reintroduce;
- class function Construct(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AExtendedHasher: TExtendedHasherFunc<T>): IExtendedEqualityComparer<T>; overload; reintroduce;
- procedure GetHashList(const AValue: T; AHashList: PUInt32); virtual; abstract;
- end;
- TDelegatedExtendedEqualityComparerEvents<T> = class(TExtendedEqualityComparer<T>)
- private
- FEqualityComparison: TOnEqualityComparison<T>;
- FHasher: TOnHasher<T>;
- FExtendedHasher: TOnExtendedHasher<T>;
- function GetHashCodeMethod(const AValue: T): UInt32;
- public
- function Equals(const ALeft, ARight: T): Boolean; override;
- function GetHashCode(const AValue: T): UInt32; override;
- procedure GetHashList(const AValue: T; AHashList: PUInt32); override;
- constructor Create(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>; const AExtendedHasher: TOnExtendedHasher<T>); overload;
- constructor Create(const AEqualityComparison: TOnEqualityComparison<T>;
- const AExtendedHasher: TOnExtendedHasher<T>); overload;
- end;
- TDelegatedExtendedEqualityComparerFunc<T> = class(TExtendedEqualityComparer<T>)
- private
- FEqualityComparison: TEqualityComparisonFunc<T>;
- FHasher: THasherFunc<T>;
- FExtendedHasher: TExtendedHasherFunc<T>;
- public
- function Equals(const ALeft, ARight: T): Boolean; override;
- function GetHashCode(const AValue: T): UInt32; override;
- procedure GetHashList(const AValue: T; AHashList: PUInt32); override;
- constructor Create(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>; const AExtendedHasher: TExtendedHasherFunc<T>); overload;
- constructor Create(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AExtendedHasher: TExtendedHasherFunc<T>); overload;
- end;
- TBinaryComparer<T> = class(TInterfacedObject, IComparer<T>)
- public
- function Compare(const ALeft, ARight: T): Integer;
- end;
- TBinaryEqualityComparer<T> = class(TInterfacedObject, IEqualityComparer<T>)
- private
- FHashFactory: THashFactoryClass;
- public
- constructor Create(AHashFactoryClass: THashFactoryClass);
- function Equals(const ALeft, ARight: T): Boolean;
- function GetHashCode(const AValue: T): UInt32;
- end;
- TBinaryExtendedEqualityComparer<T> = class(TBinaryEqualityComparer<T>, IExtendedEqualityComparer<T>)
- private
- FExtendedHashFactory: TExtendedHashFactoryClass;
- public
- constructor Create(AHashFactoryClass: TExtendedHashFactoryClass);
- procedure GetHashList(const AValue: T; AHashList: PUInt32);
- end;
- { TDelphiHashFactory }
- TDelphiHashFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TGenericsHashFactory }
- TGenericsHashFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TxxHash32HashFactory }
- TxxHash32HashFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TxxHash32PascalHashFactory }
- TxxHash32PascalHashFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TAdler32HashFactory }
- TAdler32HashFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TSdbmHashFactory }
- TSdbmHashFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TSdbmHashFactory }
- TSimpleChecksumFactory = class(THashFactory)
- public
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- end;
- { TDelphiDoubleHashFactory }
- TDelphiDoubleHashFactory = class(TExtendedHashFactory)
- public
- const MAX_HASHLIST_COUNT = 2;
- const HASH_FUNCTIONS_COUNT = 1;
- const HASHLIST_COUNT_PER_FUNCTION: array[1..HASH_FUNCTIONS_COUNT] of Integer = (2);
- const HASH_FUNCTIONS_MASK_SIZE = 1;
- const HASH_FUNCTIONS_MASK = 1; // 00000001b
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- class procedure GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32; AOptions: TGetHashListOptions = []); override;
- end;
- TDelphiQuadrupleHashFactory = class(TExtendedHashFactory)
- public
- const MAX_HASHLIST_COUNT = 4;
- const HASH_FUNCTIONS_COUNT = 2;
- const HASHLIST_COUNT_PER_FUNCTION: array[1..HASH_FUNCTIONS_COUNT] of Integer = (2, 2);
- const HASH_FUNCTIONS_MASK_SIZE = 2;
- const HASH_FUNCTIONS_MASK = 3; // 00000011b
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- class procedure GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32; AOptions: TGetHashListOptions = []); override;
- end;
- TDelphiSixfoldHashFactory = class(TExtendedHashFactory)
- public
- const MAX_HASHLIST_COUNT = 6;
- const HASH_FUNCTIONS_COUNT = 3;
- const HASHLIST_COUNT_PER_FUNCTION: array[1..HASH_FUNCTIONS_COUNT] of Integer = (2, 2, 2);
- const HASH_FUNCTIONS_MASK_SIZE = 3;
- const HASH_FUNCTIONS_MASK = 7; // 00000111b
- class function GetHashService: THashServiceClass; override;
- class function GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32 = 0): UInt32; override;
- class procedure GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32; AOptions: TGetHashListOptions = []); override;
- end;
- TDefaultHashFactory = TGenericsHashFactory;
- TDefaultGenericInterface = (giComparer, giEqualityComparer, giExtendedEqualityComparer);
- TCustomComparer<T> = class(TSingletonImplementation, IComparer<T>, IEqualityComparer<T>, IExtendedEqualityComparer<T>)
- protected
- function Compare(const Left, Right: T): Integer; virtual; abstract;
- function Equals(const Left, Right: T): Boolean; reintroduce; overload; virtual; abstract;
- function GetHashCode(const Value: T): UInt32; reintroduce; overload; virtual; abstract;
- procedure GetHashList(const Value: T; AHashList: PUInt32); virtual; abstract;
- end;
- TOrdinalComparer<T, THashFactory> = class(TCustomComparer<T>)
- protected class var
- FComparer: IComparer<T>;
- FEqualityComparer: IEqualityComparer<T>;
- FExtendedEqualityComparer: IExtendedEqualityComparer<T>;
- class constructor Create;
- public
- class function Ordinal: TCustomComparer<T>; virtual; abstract;
- end;
- // TGStringComparer will be renamed to TStringComparer -> bug #26030
- // anyway class var can't be used safely -> bug #24848
- TGStringComparer<T, THashFactory> = class(TOrdinalComparer<T, THashFactory>)
- private class var
- FOrdinal: TCustomComparer<T>;
- class destructor Destroy;
- public
- class function Ordinal: TCustomComparer<T>; override;
- end;
- TGStringComparer<T> = class(TGStringComparer<T, TDelphiQuadrupleHashFactory>);
- TStringComparer = class(TGStringComparer<string>);
- TAnsiStringComparer = class(TGStringComparer<AnsiString>);
- TUnicodeStringComparer = class(TGStringComparer<UnicodeString>);
- { TGOrdinalStringComparer }
- // TGOrdinalStringComparer will be renamed to TOrdinalStringComparer -> bug #26030
- // anyway class var can't be used safely -> bug #24848
- TGOrdinalStringComparer<T, THashFactory> = class(TGStringComparer<T, THashFactory>)
- public
- function Compare(const ALeft, ARight: T): Integer; override;
- function Equals(const ALeft, ARight: T): Boolean; overload; override;
- function GetHashCode(const AValue: T): UInt32; overload; override;
- procedure GetHashList(const AValue: T; AHashList: PUInt32); override;
- end;
- TGOrdinalStringComparer<T> = class(TGOrdinalStringComparer<T, TDelphiQuadrupleHashFactory>);
- TOrdinalStringComparer = class(TGOrdinalStringComparer<string>);
- TGIStringComparer<T, THashFactory> = class(TOrdinalComparer<T, THashFactory>)
- private class var
- FOrdinal: TCustomComparer<T>;
- class destructor Destroy;
- public
- class function Ordinal: TCustomComparer<T>; override;
- end;
- TGIStringComparer<T> = class(TGIStringComparer<T, TDelphiQuadrupleHashFactory>);
- TIStringComparer = class(TGIStringComparer<string>);
- TIAnsiStringComparer = class(TGIStringComparer<AnsiString>);
- TIUnicodeStringComparer = class(TGIStringComparer<UnicodeString>);
- TGOrdinalIStringComparer<T, THashFactory> = class(TGIStringComparer<T, THashFactory>)
- public
- function Compare(const ALeft, ARight: T): Integer; override;
- function Equals(const ALeft, ARight: T): Boolean; overload; override;
- function GetHashCode(const AValue: T): UInt32; overload; override;
- procedure GetHashList(const AValue: T; AHashList: PUInt32); override;
- end;
- TGOrdinalIStringComparer<T> = class(TGOrdinalIStringComparer<T, TDelphiQuadrupleHashFactory>);
- TOrdinalIStringComparer = class(TGOrdinalIStringComparer<string>);
- // Delphi version of Bob Jenkins Hash
- function BobJenkinsHash(const AData; ALength, AInitData: Integer): Integer; // same result as HashLittle_Delphi, just different interface
- function BinaryCompare(const ALeft, ARight: Pointer; ASize: PtrUInt): Integer; inline;
- function _LookupVtableInfo(AGInterface: TDefaultGenericInterface; ATypeInfo: PTypeInfo; ASize: SizeInt;
- AConstParaRef: Boolean): Pointer; inline;
- function _LookupVtableInfoEx(AGInterface: TDefaultGenericInterface; ATypeInfo: PTypeInfo; ASize: SizeInt;
- AConstParaRef: Boolean; AFactory: THashFactoryClass): Pointer;
- implementation
- { TComparer<T> }
- class function TComparer<T>.Default: IComparer<T>;
- begin
- if GetTypeKind(T) in TComparerService.UseBinaryMethods then begin
- Result := TBinaryComparer<T>.Create
- end else
- Result := _LookupVtableInfo(giComparer, TypeInfo(T), SizeOf(T), ConstParamIsRef<T>());
- end;
- class function TComparer<T>.Construct(const AComparison: TOnComparison<T>): IComparer<T>;
- begin
- Result := TDelegatedComparerEvents<T>.Create(AComparison);
- end;
- class function TComparer<T>.Construct(const AComparison: TComparisonFunc<T>): IComparer<T>;
- begin
- Result := TDelegatedComparerFunc<T>.Create(AComparison);
- end;
- function TDelegatedComparerEvents<T>.Compare(const ALeft, ARight: T): Integer;
- begin
- Result := FComparison(ALeft, ARight);
- end;
- constructor TDelegatedComparerEvents<T>.Create(AComparison: TOnComparison<T>);
- begin
- FComparison := AComparison;
- end;
- function TDelegatedComparerFunc<T>.Compare(const ALeft, ARight: T): Integer;
- begin
- Result := FComparison(ALeft, ARight);
- end;
- constructor TDelegatedComparerFunc<T>.Create(AComparison: TComparisonFunc<T>);
- begin
- FComparison := AComparison;
- end;
- { TInterface }
- function TInterface.QueryInterface(constref IID: TGUID; out Obj): HResult;
- begin
- Result := E_NOINTERFACE;
- end;
- { TRawInterface }
- function TRawInterface._AddRef: LongInt;
- begin
- Result := -1;
- end;
- function TRawInterface._Release: LongInt;
- begin
- Result := -1;
- end;
- { TComTypeSizeInterface }
- function TComTypeSizeInterface._AddRef: LongInt;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- Result := InterLockedIncrement(_self.RefCount);
- end;
- function TComTypeSizeInterface._Release: LongInt;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- Result := InterLockedDecrement(_self.RefCount);
- if _self.RefCount = 0 then
- Dispose(_self);
- end;
- { TSingletonImplementation }
- function TSingletonImplementation.QueryInterface(constref IID: TGUID; out Obj): HResult;
- begin
- if GetInterface(IID, Obj) then
- Result := S_OK
- else
- Result := E_NOINTERFACE;
- end;
- { TCompare }
- (***********************************************************************************************************************
- Comparers
- (**********************************************************************************************************************)
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers Int8 - Int32 and UInt8 - UInt32
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.Integer(const ALeft, ARight: Integer): Integer;
- begin
- Result := Math.CompareValue(ALeft, ARight);
- end;
- class function TCompare.Int8(const ALeft, ARight: Int8): Integer;
- begin
- Result := ALeft - ARight;
- end;
- class function TCompare.Int16(const ALeft, ARight: Int16): Integer;
- begin
- Result := ALeft - ARight;
- end;
- class function TCompare.Int32(const ALeft, ARight: Int32): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.Int64(const ALeft, ARight: Int64): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.UInt8(const ALeft, ARight: UInt8): Integer;
- begin
- Result := System.Integer(ALeft) - System.Integer(ARight);
- end;
- class function TCompare.UInt16(const ALeft, ARight: UInt16): Integer;
- begin
- Result := System.Integer(ALeft) - System.Integer(ARight);
- end;
- class function TCompare.UInt32(const ALeft, ARight: UInt32): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.UInt64(const ALeft, ARight: UInt64): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for Float types
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.Single(const ALeft, ARight: Single): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.Double(const ALeft, ARight: Double): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.Extended(const ALeft, ARight: Extended): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for other number types
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.Currency(const ALeft, ARight: Currency): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.Comp(const ALeft, ARight: Comp): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for binary data (records etc) and dynamics arrays
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare._Binary(const ALeft, ARight): Integer;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- if _self.ConstParaRef then
- Result := CompareMemRange(@ALeft, @ARight, _self.Size)
- else
- Result := CompareMemRange(PPointer(@ALeft)^, PPointer(@ARight)^, _self.Size);
- end;
- class function TCompare._DynArray(const ALeft, ARight: Pointer): Integer;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- LLength, LLeftLength, LRightLength: Integer;
- begin
- LLeftLength := DynArraySize(ALeft);
- LRightLength := DynArraySize(ARight);
- if LLeftLength > LRightLength then
- LLength := LRightLength
- else
- LLength := LLeftLength;
- Result := CompareMemRange(ALeft, ARight, LLength * _self.Size);
- if Result = 0 then
- Result := LLeftLength - LRightLength;
- end;
- class function TCompare.Binary(const ALeft, ARight; const ASize: SizeInt): Integer;
- begin
- Result := CompareMemRange(@ALeft, @ARight, ASize);
- end;
- class function TCompare.DynArray(const ALeft, ARight: Pointer; const AElementSize: SizeInt): Integer;
- var
- LLength, LLeftLength, LRightLength: Integer;
- begin
- LLeftLength := DynArraySize(ALeft);
- LRightLength := DynArraySize(ARight);
- if LLeftLength > LRightLength then
- LLength := LRightLength
- else
- LLength := LLeftLength;
- Result := CompareMemRange(ALeft, ARight, LLength * AElementSize);
- if Result = 0 then
- Result := LLeftLength - LRightLength;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for string types
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.ShortString1(const ALeft, ARight: ShortString1): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.ShortString2(const ALeft, ARight: ShortString2): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.ShortString3(const ALeft, ARight: ShortString3): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.ShortString(const ALeft, ARight: ShortString): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- class function TCompare.&String(const ALeft, ARight: String): Integer;
- begin
- Result := CompareStr(ALeft, ARight);
- end;
- class function TCompare.AnsiString(const ALeft, ARight: AnsiString): Integer;
- begin
- Result := AnsiCompareStr(ALeft, ARight);
- end;
- class function TCompare.WideString(const ALeft, ARight: WideString): Integer;
- begin
- Result := WideCompareStr(ALeft, ARight);
- end;
- class function TCompare.UnicodeString(const ALeft, ARight: UnicodeString): Integer;
- begin
- Result := UnicodeCompareStr(ALeft, ARight);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for Delegates
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.Method(const ALeft, ARight: TMethod): Integer;
- begin
- Result := CompareMemRange(@ALeft, @ARight, SizeOf(System.TMethod));
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for Variant
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.Variant(const ALeft, ARight: PVariant): Integer;
- var
- LLeftString, LRightString: string;
- begin
- try
- case VarCompareValue(ALeft^, ARight^) of
- vrGreaterThan:
- Exit(1);
- vrLessThan:
- Exit(-1);
- vrEqual:
- Exit(0);
- vrNotEqual:
- if VarIsEmpty(ALeft^) or VarIsNull(ALeft^) then
- Exit(1)
- else
- Exit(-1);
- end;
- except
- try
- LLeftString := ALeft^;
- LRightString := ARight^;
- Result := CompareStr(LLeftString, LRightString);
- except
- Result := CompareMemRange(ALeft, ARight, SizeOf(System.Variant));
- end;
- end;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Comparers for Pointer
- {----------------------------------------------------------------------------------------------------------------------}
- class function TCompare.Pointer(const ALeft, ARight: PtrUInt): Integer;
- begin
- if ALeft > ARight then
- Exit(1)
- else if ALeft < ARight then
- Exit(-1)
- else
- Exit(0);
- end;
- { TEquals }
- (***********************************************************************************************************************
- Equality Comparers
- (**********************************************************************************************************************)
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers Int8 - Int32 and UInt8 - UInt32
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.Integer(const ALeft, ARight: Integer): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Int8(const ALeft, ARight: Int8): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Int16(const ALeft, ARight: Int16): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Int32(const ALeft, ARight: Int32): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Int64(const ALeft, ARight: Int64): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.UInt8(const ALeft, ARight: UInt8): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.UInt16(const ALeft, ARight: UInt16): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.UInt32(const ALeft, ARight: UInt32): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.UInt64(const ALeft, ARight: UInt64): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for Float types
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.Single(const ALeft, ARight: Single): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Double(const ALeft, ARight: Double): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Extended(const ALeft, ARight: Extended): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for other number types
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.Currency(const ALeft, ARight: Currency): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.Comp(const ALeft, ARight: Comp): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for binary data (records etc) and dynamics arrays
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals._Binary(const ALeft, ARight): Boolean;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- if _self.ConstParaRef then
- Result := CompareMem(@ALeft, @ARight, _self.Size)
- else
- Result := CompareMem(PPointer(@ALeft)^, PPointer(@ARight)^, _self.Size);
- end;
- class function TEquals._DynArray(const ALeft, ARight: Pointer): Boolean;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- LLength: Integer;
- begin
- LLength := DynArraySize(ALeft);
- if LLength <> DynArraySize(ARight) then
- Exit(False);
- Result := CompareMem(ALeft, ARight, LLength * _self.Size);
- end;
- class function TEquals.Binary(const ALeft, ARight; const ASize: SizeInt): Boolean;
- begin
- Result := CompareMem(@ALeft, @ARight, ASize);
- end;
- class function TEquals.DynArray(const ALeft, ARight: Pointer; const AElementSize: SizeInt): Boolean;
- var
- LLength: Integer;
- begin
- LLength := DynArraySize(ALeft);
- if LLength <> DynArraySize(ARight) then
- Exit(False);
- Result := CompareMem(ALeft, ARight, LLength * AElementSize);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for classes
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.&class(const ALeft, ARight: TObject): Boolean;
- begin
- if ALeft <> nil then
- Exit(ALeft.Equals(ARight))
- else
- Exit(ARight = nil);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for string types
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.ShortString1(const ALeft, ARight: ShortString1): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.ShortString2(const ALeft, ARight: ShortString2): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.ShortString3(const ALeft, ARight: ShortString3): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.&String(const ALeft, ARight: String): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.ShortString(const ALeft, ARight: ShortString): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.AnsiString(const ALeft, ARight: AnsiString): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.WideString(const ALeft, ARight: WideString): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- class function TEquals.UnicodeString(const ALeft, ARight: UnicodeString): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for Delegates
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.Method(const ALeft, ARight: TMethod): Boolean;
- begin
- Result := (ALeft.Code = ARight.Code) and (ALeft.Data = ARight.Data);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for Variant
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.Variant(const ALeft, ARight: PVariant): Boolean;
- begin
- Result := VarCompareValue(ALeft^, ARight^) = vrEqual;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- Equality Comparers for Pointer
- {----------------------------------------------------------------------------------------------------------------------}
- class function TEquals.Pointer(const ALeft, ARight: PtrUInt): Boolean;
- begin
- Result := ALeft = ARight;
- end;
- (***********************************************************************************************************************
- Hashes
- (**********************************************************************************************************************)
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode Int8 - Int32 and UInt8 - UInt32
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Int8(const AValue: Int8): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Int8), 0);
- end;
- class function THashFactory.Int16(const AValue: Int16): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Int16), 0);
- end;
- class function THashFactory.Int32(const AValue: Int32): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Int32), 0);
- end;
- class function THashFactory.Int64(const AValue: Int64): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Int64), 0);
- end;
- class function THashFactory.UInt8(const AValue: UInt8): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.UInt8), 0);
- end;
- class function THashFactory.UInt16(const AValue: UInt16): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.UInt16), 0);
- end;
- class function THashFactory.UInt32(const AValue: UInt32): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.UInt32), 0);
- end;
- class function THashFactory.UInt64(const AValue: UInt64): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.UInt64), 0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Float types
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Single(const AValue: Single): UInt32;
- var
- LMantissa: Float;
- LExponent: Integer;
- begin
- Frexp(AValue, LMantissa, LExponent);
- if LMantissa = 0 then
- LMantissa := Abs(LMantissa);
- Result := HASH_FACTORY.GetHashCode(@LMantissa, SizeOf(Math.Float), 0);
- Result := HASH_FACTORY.GetHashCode(@LExponent, SizeOf(System.Integer), Result);
- end;
- class function THashFactory.Double(const AValue: Double): UInt32;
- var
- LMantissa: Float;
- LExponent: Integer;
- begin
- Frexp(AValue, LMantissa, LExponent);
- if LMantissa = 0 then
- LMantissa := Abs(LMantissa);
- Result := HASH_FACTORY.GetHashCode(@LMantissa, SizeOf(Math.Float), 0);
- Result := HASH_FACTORY.GetHashCode(@LExponent, SizeOf(System.Integer), Result);
- end;
- class function THashFactory.Extended(const AValue: Extended): UInt32;
- var
- LMantissa: Float;
- LExponent: Integer;
- begin
- Frexp(AValue, LMantissa, LExponent);
- if LMantissa = 0 then
- LMantissa := Abs(LMantissa);
- Result := HASH_FACTORY.GetHashCode(@LMantissa, SizeOf(Math.Float), 0);
- Result := HASH_FACTORY.GetHashCode(@LExponent, SizeOf(System.Integer), Result);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for other number types
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Currency(const AValue: Currency): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Int64), 0);
- end;
- class function THashFactory.Comp(const AValue: Comp): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Int64), 0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for binary data (records etc) and dynamics arrays
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Binary(const AValue): UInt32;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, _self.Size, 0);
- end;
- class function THashFactory.DynArray(const AValue: Pointer): UInt32;
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- Result := HASH_FACTORY.GetHashCode(AValue, DynArraySize(AValue) * _self.Size, 0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for classes
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.&Class(const AValue: TObject): UInt32;
- begin
- if AValue = nil then
- Exit($2A);
- Result := AValue.GetHashCode;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for string types
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.ShortString1(const AValue: ShortString1): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue), 0);
- end;
- class function THashFactory.ShortString2(const AValue: ShortString2): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue), 0);
- end;
- class function THashFactory.ShortString3(const AValue: ShortString3): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue), 0);
- end;
- class function THashFactory.ShortString(const AValue: ShortString): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue), 0);
- end;
- class function THashFactory.AnsiString(const AValue: AnsiString): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue) * SizeOf(System.AnsiChar), 0);
- end;
- class function THashFactory.WideString(const AValue: WideString): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue) * SizeOf(System.WideChar), 0);
- end;
- class function THashFactory.UnicodeString(const AValue: UnicodeString): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue[1], Length(AValue) * SizeOf(System.UnicodeChar), 0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Delegates
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Method(const AValue: TMethod): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.TMethod), 0);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Variant
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Variant(const AValue: PVariant): UInt32;
- begin
- try
- Result := HASH_FACTORY.UnicodeString(AValue^);
- except
- Result := HASH_FACTORY.GetHashCode(AValue, SizeOf(System.Variant), 0);
- end;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Pointer
- {----------------------------------------------------------------------------------------------------------------------}
- class function THashFactory.Pointer(const AValue: Pointer): UInt32;
- begin
- Result := HASH_FACTORY.GetHashCode(@AValue, SizeOf(System.Pointer), 0);
- end;
- { TExtendedHashFactory }
- (***********************************************************************************************************************
- Hashes 2
- (**********************************************************************************************************************)
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode Int8 - Int32 and UInt8 - UInt32
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Int8(const AValue: Int8; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Int8), AHashList, []);
- end;
- class procedure TExtendedHashFactory.Int16(const AValue: Int16; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Int16), AHashList, []);
- end;
- class procedure TExtendedHashFactory.Int32(const AValue: Int32; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Int32), AHashList, []);
- end;
- class procedure TExtendedHashFactory.Int64(const AValue: Int64; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Int64), AHashList, []);
- end;
- class procedure TExtendedHashFactory.UInt8(const AValue: UInt8; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.UInt8), AHashList, []);
- end;
- class procedure TExtendedHashFactory.UInt16(const AValue: UInt16; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.UInt16), AHashList, []);
- end;
- class procedure TExtendedHashFactory.UInt32(const AValue: UInt32; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.UInt32), AHashList, []);
- end;
- class procedure TExtendedHashFactory.UInt64(const AValue: UInt64; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.UInt64), AHashList, []);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Float types
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Single(const AValue: Single; AHashList: PUInt32);
- var
- LMantissa: Float;
- LExponent: Integer;
- begin
- Frexp(AValue, LMantissa, LExponent);
- if LMantissa = 0 then
- LMantissa := Abs(LMantissa);
- EXTENDED_HASH_FACTORY.GetHashList(@LMantissa, SizeOf(Math.Float), AHashList, []);
- EXTENDED_HASH_FACTORY.GetHashList(@LExponent, SizeOf(System.Integer), AHashList, [ghloHashListAsInitData]);
- end;
- class procedure TExtendedHashFactory.Double(const AValue: Double; AHashList: PUInt32);
- var
- LMantissa: Float;
- LExponent: Integer;
- begin
- Frexp(AValue, LMantissa, LExponent);
- if LMantissa = 0 then
- LMantissa := Abs(LMantissa);
- EXTENDED_HASH_FACTORY.GetHashList(@LMantissa, SizeOf(Math.Float), AHashList, []);
- EXTENDED_HASH_FACTORY.GetHashList(@LExponent, SizeOf(System.Integer), AHashList, [ghloHashListAsInitData]);
- end;
- class procedure TExtendedHashFactory.Extended(const AValue: Extended; AHashList: PUInt32);
- var
- LMantissa: Float;
- LExponent: Integer;
- begin
- Frexp(AValue, LMantissa, LExponent);
- if LMantissa = 0 then
- LMantissa := Abs(LMantissa);
- EXTENDED_HASH_FACTORY.GetHashList(@LMantissa, SizeOf(Math.Float), AHashList, []);
- EXTENDED_HASH_FACTORY.GetHashList(@LExponent, SizeOf(System.Integer), AHashList, [ghloHashListAsInitData]);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for other number types
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Currency(const AValue: Currency; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Int64), AHashList, []);
- end;
- class procedure TExtendedHashFactory.Comp(const AValue: Comp; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Int64), AHashList, []);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for binary data (records etc) and dynamics arrays
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Binary(const AValue; AHashList: PUInt32);
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, _self.Size, AHashList, []);
- end;
- class procedure TExtendedHashFactory.DynArray(const AValue: Pointer; AHashList: PUInt32);
- var
- _self: TComparerService.PSpoofInterfacedTypeSizeObject absolute Self;
- begin
- EXTENDED_HASH_FACTORY.GetHashList(AValue, DynArraySize(AValue) * _self.Size, AHashList, []);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for classes
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.&Class(const AValue: TObject; AHashList: PUInt32);
- var
- LValue: PtrInt;
- begin
- if AValue = nil then
- begin
- LValue := $2A;
- EXTENDED_HASH_FACTORY.GetHashList(@LValue, SizeOf(LValue), AHashList, []);
- Exit;
- end;
- LValue := AValue.GetHashCode;
- EXTENDED_HASH_FACTORY.GetHashList(@LValue, SizeOf(LValue), AHashList, []);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for string types
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.ShortString1(const AValue: ShortString1; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue), AHashList, []);
- end;
- class procedure TExtendedHashFactory.ShortString2(const AValue: ShortString2; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue), AHashList, []);
- end;
- class procedure TExtendedHashFactory.ShortString3(const AValue: ShortString3; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue), AHashList, []);
- end;
- class procedure TExtendedHashFactory.ShortString(const AValue: ShortString; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue), AHashList, []);
- end;
- class procedure TExtendedHashFactory.AnsiString(const AValue: AnsiString; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue) * SizeOf(System.AnsiChar), AHashList, []);
- end;
- class procedure TExtendedHashFactory.WideString(const AValue: WideString; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue) * SizeOf(System.WideChar), AHashList, []);
- end;
- class procedure TExtendedHashFactory.UnicodeString(const AValue: UnicodeString; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue[1], Length(AValue) * SizeOf(System.UnicodeChar), AHashList, []);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Delegates
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Method(const AValue: TMethod; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.TMethod), AHashList, []);
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Variant
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Variant(const AValue: PVariant; AHashList: PUInt32);
- begin
- try
- EXTENDED_HASH_FACTORY.UnicodeString(AValue^, AHashList);
- except
- EXTENDED_HASH_FACTORY.GetHashList(AValue, SizeOf(System.Variant), AHashList, []);
- end;
- end;
- {-----------------------------------------------------------------------------------------------------------------------
- GetHashCode for Pointer
- {----------------------------------------------------------------------------------------------------------------------}
- class procedure TExtendedHashFactory.Pointer(const AValue: Pointer; AHashList: PUInt32);
- begin
- EXTENDED_HASH_FACTORY.GetHashList(@AValue, SizeOf(System.Pointer), AHashList, []);
- end;
- { TComparerService }
- class function TComparerService.CreateInterface(AVMT: Pointer; ASize: SizeInt; AConstParaRef: Boolean): PSpoofInterfacedTypeSizeObject;
- begin
- Result := New(PSpoofInterfacedTypeSizeObject);
- Result.VMT := AVMT;
- Result.RefCount := 0;
- Result.Size := ASize;
- Result.ConstParaRef := AConstParaRef;
- end;
- class function TComparerService.SelectIntegerComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ATypeData.OrdType of
- otSByte:
- Exit(@Comparer_Int8_Instance);
- otUByte:
- Exit(@Comparer_UInt8_Instance);
- otSWord:
- Exit(@Comparer_Int16_Instance);
- otUWord:
- Exit(@Comparer_UInt16_Instance);
- otSLong:
- Exit(@Comparer_Int32_Instance);
- otULong:
- Exit(@Comparer_UInt32_Instance);
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- class function TComparerService.SelectInt64Comparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- if ATypeData.MaxInt64Value > ATypeData.MinInt64Value then
- Exit(@Comparer_Int64_Instance)
- else
- Exit(@Comparer_UInt64_Instance);
- end;
- class function TComparerService.SelectFloatComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ATypeData.FloatType of
- ftSingle:
- Exit(@Comparer_Single_Instance);
- ftDouble:
- Exit(@Comparer_Double_Instance);
- ftExtended:
- Exit(@Comparer_Extended_Instance);
- ftComp:
- Exit(@Comparer_Comp_Instance);
- ftCurr:
- Exit(@Comparer_Currency_Instance);
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- class function TComparerService.SelectShortStringComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ASize of
- 2: Exit(@Comparer_ShortString1_Instance);
- 3: Exit(@Comparer_ShortString2_Instance);
- 4: Exit(@Comparer_ShortString3_Instance);
- else
- Exit(@Comparer_ShortString_Instance);
- end;
- end;
- class function TComparerService.SelectBinaryComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := CreateInterface(@Comparer_Binary_VMT, ASize, AConstParaRef);
- end;
- class function TComparerService.SelectDynArrayComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := CreateInterface(@Comparer_DynArray_VMT, ATypeData.elSize, AConstParaRef);
- end;
- class function TComparerService.LookupComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- var
- LInstance: PInstance;
- begin
- if ATypeInfo = nil then
- Exit(SelectBinaryComparer(Nil, ASize, AConstParaRef))
- else
- begin
- LInstance := @ComparerInstances[ATypeInfo.Kind];
- if LInstance.Selector then
- Result := TSelectFunc(LInstance.SelectorInstance)(GetTypeData(ATypeInfo), ASize, AConstParaRef)
- else
- Result := LInstance.Instance;
- end;
- end;
- { TComparerService.TInstance }
- class function TComparerService.TInstance.Create(ASelector: Boolean;
- AInstance: Pointer): TComparerService.TInstance;
- begin
- Result.Selector := ASelector;
- Result.Instance := AInstance;
- end;
- class function TComparerService.TInstance.CreateSelector(ASelectorInstance: CodePointer): TComparerService.TInstance;
- begin
- Result.Selector := True;
- Result.SelectorInstance := ASelectorInstance;
- end;
- { TExtendedHashService }
- class function TExtendedHashService.LookupEqualityComparer(ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := LookupExtendedEqualityComparer(ATypeInfo, ASize, AConstParaRef);
- end;
- { THashService }
- class function THashService<T>.SelectIntegerEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ATypeData.OrdType of
- otSByte:
- Exit(@FEqualityComparer_Int8_Instance);
- otUByte:
- Exit(@FEqualityComparer_UInt8_Instance);
- otSWord:
- Exit(@FEqualityComparer_Int16_Instance);
- otUWord:
- Exit(@FEqualityComparer_UInt16_Instance);
- otSLong:
- Exit(@FEqualityComparer_Int32_Instance);
- otULong:
- Exit(@FEqualityComparer_UInt32_Instance);
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- class function THashService<T>.SelectFloatEqualityComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ATypeData.FloatType of
- ftSingle:
- Exit(@FEqualityComparer_Single_Instance);
- ftDouble:
- Exit(@FEqualityComparer_Double_Instance);
- ftExtended:
- Exit(@FEqualityComparer_Extended_Instance);
- ftComp:
- Exit(@FEqualityComparer_Comp_Instance);
- ftCurr:
- Exit(@FEqualityComparer_Currency_Instance);
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- class function THashService<T>.SelectShortStringEqualityComparer(
- ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ASize of
- 2: Exit(@FEqualityComparer_ShortString1_Instance);
- 3: Exit(@FEqualityComparer_ShortString2_Instance);
- 4: Exit(@FEqualityComparer_ShortString3_Instance);
- else
- Exit(@FEqualityComparer_ShortString_Instance);
- end
- end;
- class function THashService<T>.SelectBinaryEqualityComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := CreateInterface(@FEqualityComparer_Binary_VMT, ASize, AConstParaRef);
- end;
- class function THashService<T>.SelectDynArrayEqualityComparer(
- ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := CreateInterface(@FEqualityComparer_DynArray_VMT, ATypeData.elSize, AConstParaRef);
- end;
- class function THashService<T>.LookupEqualityComparer(ATypeInfo: PTypeInfo;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- var
- LInstance: PInstance;
- LSelectMethod: TSelectMethod;
- begin
- if ATypeInfo = nil then
- Exit(SelectBinaryEqualityComparer(Nil, ASize, AConstParaRef))
- else
- begin
- LInstance := @FEqualityComparerInstances[ATypeInfo.Kind];
- Result := LInstance.Instance;
- if LInstance.Selector then
- begin
- TMethod(LSelectMethod).Code := LInstance.SelectorInstance;
- TMethod(LSelectMethod).Data := Self;
- Result := LSelectMethod(GetTypeData(ATypeInfo), ASize, AConstParaRef);
- end;
- end;
- end;
- class constructor THashService<T>.Create;
- begin
- FEqualityComparer_Int8_VMT := EqualityComparer_Int8_VMT ;
- FEqualityComparer_Int16_VMT := EqualityComparer_Int16_VMT ;
- FEqualityComparer_Int32_VMT := EqualityComparer_Int32_VMT ;
- FEqualityComparer_Int64_VMT := EqualityComparer_Int64_VMT ;
- FEqualityComparer_UInt8_VMT := EqualityComparer_UInt8_VMT ;
- FEqualityComparer_UInt16_VMT := EqualityComparer_UInt16_VMT ;
- FEqualityComparer_UInt32_VMT := EqualityComparer_UInt32_VMT ;
- FEqualityComparer_UInt64_VMT := EqualityComparer_UInt64_VMT ;
- FEqualityComparer_Single_VMT := EqualityComparer_Single_VMT ;
- FEqualityComparer_Double_VMT := EqualityComparer_Double_VMT ;
- FEqualityComparer_Extended_VMT := EqualityComparer_Extended_VMT ;
- FEqualityComparer_Currency_VMT := EqualityComparer_Currency_VMT ;
- FEqualityComparer_Comp_VMT := EqualityComparer_Comp_VMT ;
- FEqualityComparer_Binary_VMT := EqualityComparer_Binary_VMT ;
- FEqualityComparer_DynArray_VMT := EqualityComparer_DynArray_VMT ;
- FEqualityComparer_Class_VMT := EqualityComparer_Class_VMT ;
- FEqualityComparer_ShortString1_VMT := EqualityComparer_ShortString1_VMT ;
- FEqualityComparer_ShortString2_VMT := EqualityComparer_ShortString2_VMT ;
- FEqualityComparer_ShortString3_VMT := EqualityComparer_ShortString3_VMT ;
- FEqualityComparer_ShortString_VMT := EqualityComparer_ShortString_VMT ;
- FEqualityComparer_AnsiString_VMT := EqualityComparer_AnsiString_VMT ;
- FEqualityComparer_WideString_VMT := EqualityComparer_WideString_VMT ;
- FEqualityComparer_UnicodeString_VMT := EqualityComparer_UnicodeString_VMT;
- FEqualityComparer_Method_VMT := EqualityComparer_Method_VMT ;
- FEqualityComparer_Variant_VMT := EqualityComparer_Variant_VMT ;
- FEqualityComparer_Pointer_VMT := EqualityComparer_Pointer_VMT ;
- /////
- FEqualityComparer_Int8_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Int16_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Int32_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Int64_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_UInt8_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_UInt16_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_UInt32_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_UInt64_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Single_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Double_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Extended_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Currency_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Comp_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Binary_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_DynArray_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Class_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_ShortString1_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_ShortString2_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_ShortString3_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_ShortString_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_AnsiString_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_WideString_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_UnicodeString_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Method_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Variant_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- FEqualityComparer_Pointer_VMT.__ClassRef := THashFactoryClass(T.ClassType);
- ///////
- FEqualityComparer_Int8_Instance := @FEqualityComparer_Int8_VMT ;
- FEqualityComparer_Int16_Instance := @FEqualityComparer_Int16_VMT ;
- FEqualityComparer_Int32_Instance := @FEqualityComparer_Int32_VMT ;
- FEqualityComparer_Int64_Instance := @FEqualityComparer_Int64_VMT ;
- FEqualityComparer_UInt8_Instance := @FEqualityComparer_UInt8_VMT ;
- FEqualityComparer_UInt16_Instance := @FEqualityComparer_UInt16_VMT ;
- FEqualityComparer_UInt32_Instance := @FEqualityComparer_UInt32_VMT ;
- FEqualityComparer_UInt64_Instance := @FEqualityComparer_UInt64_VMT ;
- FEqualityComparer_Single_Instance := @FEqualityComparer_Single_VMT ;
- FEqualityComparer_Double_Instance := @FEqualityComparer_Double_VMT ;
- FEqualityComparer_Extended_Instance := @FEqualityComparer_Extended_VMT ;
- FEqualityComparer_Currency_Instance := @FEqualityComparer_Currency_VMT ;
- FEqualityComparer_Comp_Instance := @FEqualityComparer_Comp_VMT ;
- //FEqualityComparer_Binary_Instance := @FEqualityComparer_Binary_VMT ; // dynamic instance
- //FEqualityComparer_DynArray_Instance := @FEqualityComparer_DynArray_VMT ; // dynamic instance
- FEqualityComparer_ShortString1_Instance := @FEqualityComparer_ShortString1_VMT ;
- FEqualityComparer_ShortString2_Instance := @FEqualityComparer_ShortString2_VMT ;
- FEqualityComparer_ShortString3_Instance := @FEqualityComparer_ShortString3_VMT ;
- FEqualityComparer_ShortString_Instance := @FEqualityComparer_ShortString_VMT ;
- FEqualityComparer_AnsiString_Instance := @FEqualityComparer_AnsiString_VMT ;
- FEqualityComparer_WideString_Instance := @FEqualityComparer_WideString_VMT ;
- FEqualityComparer_UnicodeString_Instance := @FEqualityComparer_UnicodeString_VMT;
- FEqualityComparer_Method_Instance := @FEqualityComparer_Method_VMT ;
- FEqualityComparer_Variant_Instance := @FEqualityComparer_Variant_VMT ;
- FEqualityComparer_Pointer_Instance := @FEqualityComparer_Pointer_VMT ;
- //////
- FEqualityComparerInstances[tkUnknown] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectBinaryEqualityComparer)).Code);
- FEqualityComparerInstances[tkInteger] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectIntegerEqualityComparer)).Code);
- FEqualityComparerInstances[tkChar] := TInstance.Create(False, @FEqualityComparer_UInt8_Instance);
- FEqualityComparerInstances[tkEnumeration] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectIntegerEqualityComparer)).Code);
- FEqualityComparerInstances[tkFloat] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectFloatEqualityComparer)).Code);
- FEqualityComparerInstances[tkSet] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectBinaryEqualityComparer)).Code);
- FEqualityComparerInstances[tkMethod] := TInstance.Create(False, @FEqualityComparer_Method_Instance);
- FEqualityComparerInstances[tkSString] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectShortStringEqualityComparer)).Code);
- FEqualityComparerInstances[tkLString] := TInstance.Create(False, @FEqualityComparer_AnsiString_Instance);
- FEqualityComparerInstances[tkAString] := TInstance.Create(False, @FEqualityComparer_AnsiString_Instance);
- FEqualityComparerInstances[tkWString] := TInstance.Create(False, @FEqualityComparer_WideString_Instance);
- FEqualityComparerInstances[tkVariant] := TInstance.Create(False, @FEqualityComparer_Variant_Instance);
- FEqualityComparerInstances[tkArray] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectBinaryEqualityComparer)).Code);
- FEqualityComparerInstances[tkRecord] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectBinaryEqualityComparer)).Code);
- FEqualityComparerInstances[tkInterface] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance);
- FEqualityComparerInstances[tkClass] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance);
- FEqualityComparerInstances[tkObject] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectBinaryEqualityComparer)).Code);
- FEqualityComparerInstances[tkWChar] := TInstance.Create(False, @FEqualityComparer_UInt16_Instance);
- FEqualityComparerInstances[tkBool] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectIntegerEqualityComparer)).Code);
- FEqualityComparerInstances[tkInt64] := TInstance.Create(False, @FEqualityComparer_Int64_Instance);
- FEqualityComparerInstances[tkQWord] := TInstance.Create(False, @FEqualityComparer_UInt64_Instance);
- FEqualityComparerInstances[tkDynArray] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectDynArrayEqualityComparer)).Code);
- FEqualityComparerInstances[tkInterfaceRaw] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance);
- FEqualityComparerInstances[tkProcVar] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance);
- FEqualityComparerInstances[tkUString] := TInstance.Create(False, @FEqualityComparer_UnicodeString_Instance);
- FEqualityComparerInstances[tkUChar] := TInstance.Create(False, @FEqualityComparer_UInt16_Instance);
- FEqualityComparerInstances[tkHelper] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance);
- FEqualityComparerInstances[tkFile] := TInstance.CreateSelector(TMethod(TSelectMethod(THashService<T>.SelectBinaryEqualityComparer)).Code);
- FEqualityComparerInstances[tkClassRef] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance);
- FEqualityComparerInstances[tkPointer] := TInstance.Create(False, @FEqualityComparer_Pointer_Instance)
- end;
- { TExtendedHashService }
- class function TExtendedHashService<T>.SelectIntegerEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ATypeData.OrdType of
- otSByte:
- Exit(@FExtendedEqualityComparer_Int8_Instance);
- otUByte:
- Exit(@FExtendedEqualityComparer_UInt8_Instance);
- otSWord:
- Exit(@FExtendedEqualityComparer_Int16_Instance);
- otUWord:
- Exit(@FExtendedEqualityComparer_UInt16_Instance);
- otSLong:
- Exit(@FExtendedEqualityComparer_Int32_Instance);
- otULong:
- Exit(@FExtendedEqualityComparer_UInt32_Instance);
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- class function TExtendedHashService<T>.SelectFloatEqualityComparer(ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ATypeData.FloatType of
- ftSingle:
- Exit(@FExtendedEqualityComparer_Single_Instance);
- ftDouble:
- Exit(@FExtendedEqualityComparer_Double_Instance);
- ftExtended:
- Exit(@FExtendedEqualityComparer_Extended_Instance);
- ftComp:
- Exit(@FExtendedEqualityComparer_Comp_Instance);
- ftCurr:
- Exit(@FExtendedEqualityComparer_Currency_Instance);
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- class function TExtendedHashService<T>.SelectShortStringEqualityComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- case ASize of
- 2: Exit(@FExtendedEqualityComparer_ShortString1_Instance);
- 3: Exit(@FExtendedEqualityComparer_ShortString2_Instance);
- 4: Exit(@FExtendedEqualityComparer_ShortString3_Instance);
- else
- Exit(@FExtendedEqualityComparer_ShortString_Instance);
- end
- end;
- class function TExtendedHashService<T>.SelectBinaryEqualityComparer(ATypeData: PTypeData;
- ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := CreateInterface(@FExtendedEqualityComparer_Binary_VMT, ASize, AConstParaRef);
- end;
- class function TExtendedHashService<T>.SelectDynArrayEqualityComparer(
- ATypeData: PTypeData; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := CreateInterface(@FExtendedEqualityComparer_DynArray_VMT, ATypeData.elSize, AConstParaRef);
- end;
- class function TExtendedHashService<T>.LookupExtendedEqualityComparer(
- ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- var
- LInstance: PInstance;
- LSelectMethod: TSelectMethod;
- begin
- if ATypeInfo = nil then
- Exit(SelectBinaryEqualityComparer(Nil, ASize, AConstParaRef))
- else
- begin
- LInstance := @FExtendedEqualityComparerInstances[ATypeInfo.Kind];
- Result := LInstance.Instance;
- if LInstance.Selector then
- begin
- TMethod(LSelectMethod).Code := LInstance.SelectorInstance;
- TMethod(LSelectMethod).Data := Self;
- Result := LSelectMethod(GetTypeData(ATypeInfo), ASize, AConstParaRef);
- end;
- end;
- end;
- class constructor TExtendedHashService<T>.Create;
- begin
- FExtendedEqualityComparer_Int8_VMT := ExtendedEqualityComparer_Int8_VMT ;
- FExtendedEqualityComparer_Int16_VMT := ExtendedEqualityComparer_Int16_VMT ;
- FExtendedEqualityComparer_Int32_VMT := ExtendedEqualityComparer_Int32_VMT ;
- FExtendedEqualityComparer_Int64_VMT := ExtendedEqualityComparer_Int64_VMT ;
- FExtendedEqualityComparer_UInt8_VMT := ExtendedEqualityComparer_UInt8_VMT ;
- FExtendedEqualityComparer_UInt16_VMT := ExtendedEqualityComparer_UInt16_VMT ;
- FExtendedEqualityComparer_UInt32_VMT := ExtendedEqualityComparer_UInt32_VMT ;
- FExtendedEqualityComparer_UInt64_VMT := ExtendedEqualityComparer_UInt64_VMT ;
- FExtendedEqualityComparer_Single_VMT := ExtendedEqualityComparer_Single_VMT ;
- FExtendedEqualityComparer_Double_VMT := ExtendedEqualityComparer_Double_VMT ;
- FExtendedEqualityComparer_Extended_VMT := ExtendedEqualityComparer_Extended_VMT ;
- FExtendedEqualityComparer_Currency_VMT := ExtendedEqualityComparer_Currency_VMT ;
- FExtendedEqualityComparer_Comp_VMT := ExtendedEqualityComparer_Comp_VMT ;
- FExtendedEqualityComparer_Binary_VMT := ExtendedEqualityComparer_Binary_VMT ;
- FExtendedEqualityComparer_DynArray_VMT := ExtendedEqualityComparer_DynArray_VMT ;
- FExtendedEqualityComparer_Class_VMT := ExtendedEqualityComparer_Class_VMT ;
- FExtendedEqualityComparer_ShortString1_VMT := ExtendedEqualityComparer_ShortString1_VMT ;
- FExtendedEqualityComparer_ShortString2_VMT := ExtendedEqualityComparer_ShortString2_VMT ;
- FExtendedEqualityComparer_ShortString3_VMT := ExtendedEqualityComparer_ShortString3_VMT ;
- FExtendedEqualityComparer_ShortString_VMT := ExtendedEqualityComparer_ShortString_VMT ;
- FExtendedEqualityComparer_AnsiString_VMT := ExtendedEqualityComparer_AnsiString_VMT ;
- FExtendedEqualityComparer_WideString_VMT := ExtendedEqualityComparer_WideString_VMT ;
- FExtendedEqualityComparer_UnicodeString_VMT := ExtendedEqualityComparer_UnicodeString_VMT;
- FExtendedEqualityComparer_Method_VMT := ExtendedEqualityComparer_Method_VMT ;
- FExtendedEqualityComparer_Variant_VMT := ExtendedEqualityComparer_Variant_VMT ;
- FExtendedEqualityComparer_Pointer_VMT := ExtendedEqualityComparer_Pointer_VMT ;
- /////
- FExtendedEqualityComparer_Int8_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Int16_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Int32_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Int64_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_UInt8_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_UInt16_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_UInt32_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_UInt64_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Single_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Double_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Extended_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Currency_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Comp_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Binary_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_DynArray_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Class_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_ShortString1_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_ShortString2_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_ShortString3_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_ShortString_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_AnsiString_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_WideString_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_UnicodeString_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Method_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Variant_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- FExtendedEqualityComparer_Pointer_VMT.__ClassRef := TExtendedHashFactoryClass(T.ClassType);
- ///////
- FExtendedEqualityComparer_Int8_Instance := @FExtendedEqualityComparer_Int8_VMT ;
- FExtendedEqualityComparer_Int16_Instance := @FExtendedEqualityComparer_Int16_VMT ;
- FExtendedEqualityComparer_Int32_Instance := @FExtendedEqualityComparer_Int32_VMT ;
- FExtendedEqualityComparer_Int64_Instance := @FExtendedEqualityComparer_Int64_VMT ;
- FExtendedEqualityComparer_UInt8_Instance := @FExtendedEqualityComparer_UInt8_VMT ;
- FExtendedEqualityComparer_UInt16_Instance := @FExtendedEqualityComparer_UInt16_VMT ;
- FExtendedEqualityComparer_UInt32_Instance := @FExtendedEqualityComparer_UInt32_VMT ;
- FExtendedEqualityComparer_UInt64_Instance := @FExtendedEqualityComparer_UInt64_VMT ;
- FExtendedEqualityComparer_Single_Instance := @FExtendedEqualityComparer_Single_VMT ;
- FExtendedEqualityComparer_Double_Instance := @FExtendedEqualityComparer_Double_VMT ;
- FExtendedEqualityComparer_Extended_Instance := @FExtendedEqualityComparer_Extended_VMT ;
- FExtendedEqualityComparer_Currency_Instance := @FExtendedEqualityComparer_Currency_VMT ;
- FExtendedEqualityComparer_Comp_Instance := @FExtendedEqualityComparer_Comp_VMT ;
- //FExtendedEqualityComparer_Binary_Instance := @FExtendedEqualityComparer_Binary_VMT ; // dynamic instance
- //FExtendedEqualityComparer_DynArray_Instance := @FExtendedEqualityComparer_DynArray_VMT ; // dynamic instance
- FExtendedEqualityComparer_ShortString1_Instance := @FExtendedEqualityComparer_ShortString1_VMT ;
- FExtendedEqualityComparer_ShortString2_Instance := @FExtendedEqualityComparer_ShortString2_VMT ;
- FExtendedEqualityComparer_ShortString3_Instance := @FExtendedEqualityComparer_ShortString3_VMT ;
- FExtendedEqualityComparer_ShortString_Instance := @FExtendedEqualityComparer_ShortString_VMT ;
- FExtendedEqualityComparer_AnsiString_Instance := @FExtendedEqualityComparer_AnsiString_VMT ;
- FExtendedEqualityComparer_WideString_Instance := @FExtendedEqualityComparer_WideString_VMT ;
- FExtendedEqualityComparer_UnicodeString_Instance := @FExtendedEqualityComparer_UnicodeString_VMT;
- FExtendedEqualityComparer_Method_Instance := @FExtendedEqualityComparer_Method_VMT ;
- FExtendedEqualityComparer_Variant_Instance := @FExtendedEqualityComparer_Variant_VMT ;
- FExtendedEqualityComparer_Pointer_Instance := @FExtendedEqualityComparer_Pointer_VMT ;
- //////
- FExtendedEqualityComparerInstances[tkUnknown] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectBinaryEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkInteger] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectIntegerEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkChar] := TInstance.Create(False, @FExtendedEqualityComparer_UInt8_Instance);
- FExtendedEqualityComparerInstances[tkEnumeration] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectIntegerEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkFloat] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectFloatEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkSet] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectBinaryEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkMethod] := TInstance.Create(False, @FExtendedEqualityComparer_Method_Instance);
- FExtendedEqualityComparerInstances[tkSString] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectShortStringEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkLString] := TInstance.Create(False, @FExtendedEqualityComparer_AnsiString_Instance);
- FExtendedEqualityComparerInstances[tkAString] := TInstance.Create(False, @FExtendedEqualityComparer_AnsiString_Instance);
- FExtendedEqualityComparerInstances[tkWString] := TInstance.Create(False, @FExtendedEqualityComparer_WideString_Instance);
- FExtendedEqualityComparerInstances[tkVariant] := TInstance.Create(False, @FExtendedEqualityComparer_Variant_Instance);
- FExtendedEqualityComparerInstances[tkArray] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectBinaryEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkRecord] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectBinaryEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkInterface] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- FExtendedEqualityComparerInstances[tkClass] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- FExtendedEqualityComparerInstances[tkObject] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectBinaryEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkWChar] := TInstance.Create(False, @FExtendedEqualityComparer_UInt16_Instance);
- FExtendedEqualityComparerInstances[tkBool] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectIntegerEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkInt64] := TInstance.Create(False, @FExtendedEqualityComparer_Int64_Instance);
- FExtendedEqualityComparerInstances[tkQWord] := TInstance.Create(False, @FExtendedEqualityComparer_UInt64_Instance);
- FExtendedEqualityComparerInstances[tkDynArray] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectDynArrayEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkInterfaceRaw] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- FExtendedEqualityComparerInstances[tkProcVar] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- FExtendedEqualityComparerInstances[tkUString] := TInstance.Create(False, @FExtendedEqualityComparer_UnicodeString_Instance);
- FExtendedEqualityComparerInstances[tkUChar] := TInstance.Create(False, @FExtendedEqualityComparer_UInt16_Instance);
- FExtendedEqualityComparerInstances[tkHelper] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- FExtendedEqualityComparerInstances[tkFile] := TInstance.CreateSelector(TMethod(TSelectMethod(TExtendedHashService<T>.SelectBinaryEqualityComparer)).Code);
- FExtendedEqualityComparerInstances[tkClassRef] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- FExtendedEqualityComparerInstances[tkPointer] := TInstance.Create(False, @FExtendedEqualityComparer_Pointer_Instance);
- end;
- { TEqualityComparer<T> }
- class function TEqualityComparer<T>.Default: IEqualityComparer<T>;
- begin
- if GetTypeKind(T) in TComparerService.UseBinaryMethods then
- Result := TBinaryEqualityComparer<T>.Create(Nil)
- else
- Result := _LookupVtableInfo(giEqualityComparer, TypeInfo(T), SizeOf(T), ConstParamIsRef<T>());
- end;
- class function TEqualityComparer<T>.Default(AHashFactoryClass: THashFactoryClass): IEqualityComparer<T>;
- begin
- if GetTypeKind(T) in TComparerService.UseBinaryMethods then
- Result := TBinaryEqualityComparer<T>.Create(AHashFactoryClass)
- else if AHashFactoryClass.InheritsFrom(TExtendedHashFactory) then
- Result := _LookupVtableInfoEx(giExtendedEqualityComparer, TypeInfo(T), SizeOf(T), ConstParamIsRef<T>(), AHashFactoryClass)
- else if AHashFactoryClass.InheritsFrom(THashFactory) then
- Result := _LookupVtableInfoEx(giEqualityComparer, TypeInfo(T), SizeOf(T), ConstParamIsRef<T>(), AHashFactoryClass);
- end;
- class function TEqualityComparer<T>.Construct(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>): IEqualityComparer<T>;
- begin
- Result := TDelegatedEqualityComparerEvents<T>.Create(AEqualityComparison, AHasher);
- end;
- class function TEqualityComparer<T>.Construct(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>): IEqualityComparer<T>;
- begin
- Result := TDelegatedEqualityComparerFunc<T>.Create(AEqualityComparison, AHasher);
- end;
- { TDelegatedEqualityComparerEvents<T> }
- function TDelegatedEqualityComparerEvents<T>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := FEqualityComparison(ALeft, ARight);
- end;
- function TDelegatedEqualityComparerEvents<T>.GetHashCode(const AValue: T): UInt32;
- begin
- Result := FHasher(AValue);
- end;
- constructor TDelegatedEqualityComparerEvents<T>.Create(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>);
- begin
- FEqualityComparison := AEqualityComparison;
- FHasher := AHasher;
- end;
- { TDelegatedEqualityComparerFunc<T> }
- function TDelegatedEqualityComparerFunc<T>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := FEqualityComparison(ALeft, ARight);
- end;
- function TDelegatedEqualityComparerFunc<T>.GetHashCode(const AValue: T): UInt32;
- begin
- Result := FHasher(AValue);
- end;
- constructor TDelegatedEqualityComparerFunc<T>.Create(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>);
- begin
- FEqualityComparison := AEqualityComparison;
- FHasher := AHasher;
- end;
- { TDelegatedExtendedEqualityComparerEvents<T> }
- function TDelegatedExtendedEqualityComparerEvents<T>.GetHashCodeMethod(const AValue: T): UInt32;
- var
- LHashList: array[0..1] of Int32;
- LHashListParams: array[0..3] of Int16 absolute LHashList;
- begin
- LHashListParams[0] := -1;
- FExtendedHasher(AValue, @LHashList[0]);
- Result := LHashList[1];
- end;
- function TDelegatedExtendedEqualityComparerEvents<T>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := FEqualityComparison(ALeft, ARight);
- end;
- function TDelegatedExtendedEqualityComparerEvents<T>.GetHashCode(const AValue: T): UInt32;
- begin
- Result := FHasher(AValue);
- end;
- procedure TDelegatedExtendedEqualityComparerEvents<T>.GetHashList(const AValue: T; AHashList: PUInt32);
- begin
- FExtendedHasher(AValue, AHashList);
- end;
- constructor TDelegatedExtendedEqualityComparerEvents<T>.Create(const AEqualityComparison: TOnEqualityComparison<T>;
- const AHasher: TOnHasher<T>; const AExtendedHasher: TOnExtendedHasher<T>);
- begin
- FEqualityComparison := AEqualityComparison;
- FHasher := AHasher;
- FExtendedHasher := AExtendedHasher;
- end;
- constructor TDelegatedExtendedEqualityComparerEvents<T>.Create(const AEqualityComparison: TOnEqualityComparison<T>;
- const AExtendedHasher: TOnExtendedHasher<T>);
- begin
- Create(AEqualityComparison, GetHashCodeMethod, AExtendedHasher);
- end;
- { TDelegatedExtendedEqualityComparerFunc<T> }
- function TDelegatedExtendedEqualityComparerFunc<T>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := FEqualityComparison(ALeft, ARight);
- end;
- function TDelegatedExtendedEqualityComparerFunc<T>.GetHashCode(const AValue: T): UInt32;
- var
- LHashList: array[0..1] of Int32;
- LHashListParams: array[0..3] of Int16 absolute LHashList;
- begin
- if not Assigned(FHasher) then
- begin
- LHashListParams[0] := -1;
- FExtendedHasher(AValue, @LHashList[0]);
- Result := LHashList[1];
- end
- else
- Result := FHasher(AValue);
- end;
- procedure TDelegatedExtendedEqualityComparerFunc<T>.GetHashList(const AValue: T; AHashList: PUInt32);
- begin
- FExtendedHasher(AValue, AHashList);
- end;
- constructor TDelegatedExtendedEqualityComparerFunc<T>.Create(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AHasher: THasherFunc<T>; const AExtendedHasher: TExtendedHasherFunc<T>);
- begin
- FEqualityComparison := AEqualityComparison;
- FHasher := AHasher;
- FExtendedHasher := AExtendedHasher;
- end;
- constructor TDelegatedExtendedEqualityComparerFunc<T>.Create(const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AExtendedHasher: TExtendedHasherFunc<T>);
- begin
- Create(AEqualityComparison, nil, AExtendedHasher);
- end;
- { TExtendedEqualityComparer<T> }
- class function TExtendedEqualityComparer<T>.Default: IExtendedEqualityComparer<T>;
- begin
- if GetTypeKind(T) in TComparerService.UseBinaryMethods then
- Result := TBinaryExtendedEqualityComparer<T>.Create(Nil)
- else
- Result := _LookupVtableInfo(giExtendedEqualityComparer, TypeInfo(T), SizeOf(T), ConstParamIsRef<T>());
- end;
- class function TExtendedEqualityComparer<T>.Default(
- AExtenedHashFactoryClass: TExtendedHashFactoryClass
- ): IExtendedEqualityComparer<T>;
- begin
- if GetTypeKind(T) in TComparerService.UseBinaryMethods then
- Result := TBinaryExtendedEqualityComparer<T>.Create(Nil)
- else
- Result := _LookupVtableInfoEx(giExtendedEqualityComparer, TypeInfo(T), SizeOf(T), ConstParamIsRef<T>(), AExtenedHashFactoryClass);
- end;
- class function TExtendedEqualityComparer<T>.Construct(
- const AEqualityComparison: TOnEqualityComparison<T>; const AHasher: TOnHasher<T>;
- const AExtendedHasher: TOnExtendedHasher<T>): IExtendedEqualityComparer<T>;
- begin
- Result := TDelegatedExtendedEqualityComparerEvents<T>.Create(AEqualityComparison, AHasher, AExtendedHasher);
- end;
- class function TExtendedEqualityComparer<T>.Construct(
- const AEqualityComparison: TEqualityComparisonFunc<T>; const AHasher: THasherFunc<T>;
- const AExtendedHasher: TExtendedHasherFunc<T>): IExtendedEqualityComparer<T>;
- begin
- Result := TDelegatedExtendedEqualityComparerFunc<T>.Create(AEqualityComparison, AHasher, AExtendedHasher);
- end;
- class function TExtendedEqualityComparer<T>.Construct(
- const AEqualityComparison: TOnEqualityComparison<T>;
- const AExtendedHasher: TOnExtendedHasher<T>): IExtendedEqualityComparer<T>;
- begin
- Result := TDelegatedExtendedEqualityComparerEvents<T>.Create(AEqualityComparison, AExtendedHasher);
- end;
- class function TExtendedEqualityComparer<T>.Construct(
- const AEqualityComparison: TEqualityComparisonFunc<T>;
- const AExtendedHasher: TExtendedHasherFunc<T>): IExtendedEqualityComparer<T>;
- begin
- Result := TDelegatedExtendedEqualityComparerFunc<T>.Create(AEqualityComparison, AExtendedHasher);
- end;
- { TBinaryComparer<T> }
- function TBinaryComparer<T>.Compare(const ALeft, ARight: T): Integer;
- begin
- Result := BinaryCompare(@ALeft, @ARight, SizeOf(T));
- end;
- { TBinaryEqualityComparer<T> }
- constructor TBinaryEqualityComparer<T>.Create(AHashFactoryClass: THashFactoryClass);
- begin
- if not Assigned(AHashFactoryClass) then
- FHashFactory := TDefaultHashFactory
- else
- FHashFactory := AHashFactoryClass;
- end;
- function TBinaryEqualityComparer<T>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := CompareMem(@ALeft, @ARight, SizeOf(T));
- end;
- function TBinaryEqualityComparer<T>.GetHashCode(const AValue: T): UInt32;
- begin
- Result := FHashFactory.GetHashCode(@AValue, SizeOf(T), 0);
- end;
- { TBinaryExtendedEqualityComparer<T> }
- constructor TBinaryExtendedEqualityComparer<T>.Create(AHashFactoryClass: TExtendedHashFactoryClass);
- begin
- if not Assigned(AHashFactoryClass) then
- FExtendedHashFactory := TDelphiDoubleHashFactory
- else
- FExtendedHashFactory := AHashFactoryClass;
- inherited Create(FExtendedHashFactory);
- end;
- procedure TBinaryExtendedEqualityComparer<T>.GetHashList(const AValue: T; AHashList: PUInt32);
- begin
- FExtendedHashFactory.GetHashList(@AValue, SizeOf(T), AHashList, []);
- end;
- { TDelphiHashFactory }
- class function TDelphiHashFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TDelphiHashFactory>;
- end;
- class function TDelphiHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32): UInt32;
- begin
- Result := DelphiHashLittle(AKey, ASize, AInitVal);
- end;
- { TGenericsHashFactory }
- class function TGenericsHashFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TGenericsHashFactory>;
- end;
- class function TGenericsHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32): UInt32;
- begin
- Result := mORMotHasher(AInitVal, AKey, ASize);
- end;
- { TxxHash32HashFactory }
- class function TxxHash32HashFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TxxHash32HashFactory>;
- end;
- class function TxxHash32HashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt;
- AInitVal: UInt32): UInt32;
- begin
- Result := xxHash32(AInitVal, AKey, ASize);
- end;
- { TxxHash32PascalHashFactory }
- class function TxxHash32PascalHashFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TxxHash32PascalHashFactory>;
- end;
- class function TxxHash32PascalHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt;
- AInitVal: UInt32): UInt32;
- begin
- Result := xxHash32Pascal(AInitVal, AKey, ASize);
- end;
- { TAdler32HashFactory }
- class function TAdler32HashFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TAdler32HashFactory>;
- end;
- class function TAdler32HashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt;
- AInitVal: UInt32): UInt32;
- begin
- Result := Adler32(AKey, ASize);
- end;
- { TSdbmHashFactory }
- class function TSdbmHashFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TSdbmHashFactory>;
- end;
- class function TSdbmHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt;
- AInitVal: UInt32): UInt32;
- begin
- Result := sdbm(AKey, ASize);
- end;
- { TSimpleChecksumFactory }
- class function TSimpleChecksumFactory.GetHashService: THashServiceClass;
- begin
- Result := THashService<TSimpleChecksumFactory>;
- end;
- class function TSimpleChecksumFactory.GetHashCode(AKey: Pointer; ASize: SizeInt;
- AInitVal: UInt32): UInt32;
- begin
- Result := SimpleChecksumHash(AKey, ASize);
- end;
- { TDelphiDoubleHashFactory }
- class function TDelphiDoubleHashFactory.GetHashService: THashServiceClass;
- begin
- Result := TExtendedHashService<TDelphiDoubleHashFactory>;
- end;
- class function TDelphiDoubleHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32): UInt32;
- begin
- Result := DelphiHashLittle(AKey, ASize, AInitVal);
- end;
- class procedure TDelphiDoubleHashFactory.GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32;
- AOptions: TGetHashListOptions);
- var
- LHash: UInt32;
- AHashListParams: PUInt16 absolute AHashList;
- begin
- {$WARNINGS OFF}
- case AHashListParams[0] of
- -2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, LHash, AHashList[1]);
- Exit;
- end;
- -1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- 0: Exit;
- 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- 2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 0;
- AHashList[2] := 0;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- {.$WARNINGS ON} // do not enable warnings ever in this unit, or you will get many warnings about uninitialized TEqualityComparerVMT fields
- end;
- { TDelphiQuadrupleHashFactory }
- class function TDelphiQuadrupleHashFactory.GetHashService: THashServiceClass;
- begin
- Result := TExtendedHashService<TDelphiQuadrupleHashFactory>;
- end;
- class function TDelphiQuadrupleHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32): UInt32;
- begin
- Result := DelphiHashLittle(AKey, ASize, AInitVal);
- end;
- class procedure TDelphiQuadrupleHashFactory.GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32;
- AOptions: TGetHashListOptions);
- var
- LHash: UInt32;
- AHashListParams: PInt16 absolute AHashList;
- begin
- case AHashListParams[0] of
- -4:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 1988;
- LHash := 2004;
- DelphiHashLittle2(AKey, ASize, LHash, AHashList[1]);
- Exit;
- end;
- -3:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 2004;
- LHash := 1988;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- -2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, LHash, AHashList[1]);
- Exit;
- end;
- -1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- 0: Exit;
- 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- 2:
- begin
- case AHashListParams[1] of
- 0, 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 0;
- AHashList[2] := 0;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- 2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 2004;
- AHashList[2] := 1988;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- end;
- 4:
- case AHashListParams[1] of
- 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 0;
- AHashList[2] := 0;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- 2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[3] := 2004;
- AHashList[4] := 1988;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[3], AHashList[4]);
- Exit;
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- end;
- { TDelphiSixfoldHashFactory }
- class function TDelphiSixfoldHashFactory.GetHashService: THashServiceClass;
- begin
- Result := TExtendedHashService<TDelphiSixfoldHashFactory>;
- end;
- class function TDelphiSixfoldHashFactory.GetHashCode(AKey: Pointer; ASize: SizeInt; AInitVal: UInt32): UInt32;
- begin
- Result := DelphiHashLittle(AKey, ASize, AInitVal);
- end;
- class procedure TDelphiSixfoldHashFactory.GetHashList(AKey: Pointer; ASize: SizeInt; AHashList: PUInt32;
- AOptions: TGetHashListOptions);
- var
- LHash: UInt32;
- AHashListParams: PInt16 absolute AHashList;
- begin
- case AHashListParams[0] of
- -6:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 2;
- LHash := 1;
- DelphiHashLittle2(AKey, ASize, LHash, AHashList[1]);
- Exit;
- end;
- -5:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 1;
- LHash := 2;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- -4:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 1988;
- LHash := 2004;
- DelphiHashLittle2(AKey, ASize, LHash, AHashList[1]);
- Exit;
- end;
- -3:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 2004;
- LHash := 1988;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- -2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, LHash, AHashList[1]);
- Exit;
- end;
- -1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- 0: Exit;
- 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- AHashList[1] := 0;
- LHash := 0;
- DelphiHashLittle2(AKey, ASize, AHashList[1], LHash);
- Exit;
- end;
- 2:
- begin
- case AHashListParams[1] of
- 0, 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 0;
- AHashList[2] := 0;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- 2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 2004;
- AHashList[2] := 1988;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- end;
- 6:
- case AHashListParams[1] of
- 1:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[1] := 0;
- AHashList[2] := 0;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[1], AHashList[2]);
- Exit;
- end;
- 2:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[3] := 2004;
- AHashList[4] := 1988;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[3], AHashList[4]);
- Exit;
- end;
- 3:
- begin
- if not (ghloHashListAsInitData in AOptions) then
- begin
- AHashList[5] := 1;
- AHashList[6] := 2;
- end;
- DelphiHashLittle2(AKey, ASize, AHashList[5], AHashList[6]);
- Exit;
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- else
- raise EArgumentOutOfRangeException.CreateRes(@SArgumentOutOfRange);
- end;
- end;
- { TOrdinalComparer<T, THashFactory> }
- class constructor TOrdinalComparer<T, THashFactory>.Create;
- begin
- if THashFactory.InheritsFrom(TExtendedHashService) then
- begin
- FExtendedEqualityComparer := TExtendedEqualityComparer<T>.Default(TExtendedHashFactoryClass(THashFactory));
- FEqualityComparer := IEqualityComparer<T>(FExtendedEqualityComparer);
- end
- else
- FEqualityComparer := TEqualityComparer<T>.Default(THashFactory);
- FComparer := TComparer<T>.Default;
- end;
- { TGStringComparer<T, THashFactory> }
- class destructor TGStringComparer<T, THashFactory>.Destroy;
- begin
- if Assigned(FOrdinal) then
- FOrdinal.Free;
- end;
- class function TGStringComparer<T, THashFactory>.Ordinal: TCustomComparer<T>;
- begin
- if not Assigned(FOrdinal) then
- FOrdinal := TGOrdinalStringComparer<T, THashFactory>.Create;
- Result := FOrdinal;
- end;
- { TGOrdinalStringComparer<T, THashFactory> }
- function TGOrdinalStringComparer<T, THashFactory>.Compare(const ALeft, ARight: T): Integer;
- begin
- Result := FComparer.Compare(ALeft, ARight);
- end;
- function TGOrdinalStringComparer<T, THashFactory>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := FEqualityComparer.Equals(ALeft, ARight);
- end;
- function TGOrdinalStringComparer<T, THashFactory>.GetHashCode(const AValue: T): UInt32;
- begin
- Result := FEqualityComparer.GetHashCode(AValue);
- end;
- procedure TGOrdinalStringComparer<T, THashFactory>.GetHashList(const AValue: T; AHashList: PUInt32);
- begin
- FExtendedEqualityComparer.GetHashList(AValue, AHashList);
- end;
- { TGIStringComparer<T, THashFactory> }
- class destructor TGIStringComparer<T, THashFactory>.Destroy;
- begin
- if Assigned(FOrdinal) then
- FOrdinal.Free;
- end;
- class function TGIStringComparer<T, THashFactory>.Ordinal: TCustomComparer<T>;
- begin
- if not Assigned(FOrdinal) then
- FOrdinal := TGOrdinalIStringComparer<T, THashFactory>.Create;
- Result := FOrdinal;
- end;
- { TGOrdinalIStringComparer<T, THashFactory> }
- function TGOrdinalIStringComparer<T, THashFactory>.Compare(const ALeft, ARight: T): Integer;
- begin
- Result := FComparer.Compare(ALeft.ToLower, ARight.ToLower);
- end;
- function TGOrdinalIStringComparer<T, THashFactory>.Equals(const ALeft, ARight: T): Boolean;
- begin
- Result := FEqualityComparer.Equals(ALeft.ToLower, ARight.ToLower);
- end;
- function TGOrdinalIStringComparer<T, THashFactory>.GetHashCode(const AValue: T): UInt32;
- begin
- Result := FEqualityComparer.GetHashCode(AValue.ToLower);
- end;
- procedure TGOrdinalIStringComparer<T, THashFactory>.GetHashList(const AValue: T; AHashList: PUInt32);
- begin
- FExtendedEqualityComparer.GetHashList(AValue.ToLower, AHashList);
- end;
- function BobJenkinsHash(const AData; ALength, AInitData: Integer): Integer;
- begin
- Result := DelphiHashLittle(@AData, ALength, AInitData);
- end;
- function BinaryCompare(const ALeft, ARight: Pointer; ASize: PtrUInt): Integer;
- begin
- Result := CompareMemRange(ALeft, ARight, ASize);
- end;
- function _LookupVtableInfo(AGInterface: TDefaultGenericInterface; ATypeInfo: PTypeInfo; ASize: SizeInt; AConstParaRef: Boolean): Pointer;
- begin
- Result := _LookupVtableInfoEx(AGInterface, ATypeInfo, ASize, AConstParaRef, nil);
- end;
- function _LookupVtableInfoEx(AGInterface: TDefaultGenericInterface; ATypeInfo: PTypeInfo; ASize: SizeInt;
- AConstParaRef: Boolean; AFactory: THashFactoryClass): Pointer;
- begin
- case AGInterface of
- giComparer:
- Exit(
- TComparerService.LookupComparer(ATypeInfo, ASize, AConstParaRef));
- giEqualityComparer:
- begin
- if AFactory = nil then
- AFactory := TDefaultHashFactory;
- Exit(
- AFactory.GetHashService.LookupEqualityComparer(ATypeInfo, ASize, AConstParaRef));
- end;
- giExtendedEqualityComparer:
- begin
- if AFactory = nil then
- AFactory := TDelphiDoubleHashFactory;
- Exit(
- TExtendedHashServiceClass(AFactory.GetHashService).LookupExtendedEqualityComparer(ATypeInfo, ASize, AConstParaRef));
- end;
- else
- System.Error(reRangeError);
- Exit(nil);
- end;
- end;
- end.
|