Skip to content

Commit bbaec5f

Browse files
committed
implemented optimized ToArray for partition
1 parent c0412e0 commit bbaec5f

File tree

1 file changed

+34
-4
lines changed

1 file changed

+34
-4
lines changed

Source/Base/Collections/Spring.Collections.Base.pas

Lines changed: 34 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -320,6 +320,7 @@ TIteratorBase<T> = class abstract(TEnumerableBase<T>)
320320
fKind: TIteratorKind;
321321

322322
function GetElementType: PTypeInfo; override;
323+
function PartitionToArray(var values: TArray<T>): Boolean;
323324
public
324325
function GetEnumerator: IEnumerator<T>;
325326
function Skip(count: Integer): IEnumerable<T>;
@@ -748,7 +749,7 @@ function SupportsIndexedAccess(const source: IInterface): Boolean;
748749
if not Result then
749750
begin
750751
entry := obj.GetInterfaceEntry(IPartitionOfTGuid);
751-
Result := Assigned(entry) and (IPartition<Integer>(PByte(obj) + entry.IOffset).GetCountFast >= 0);
752+
Result := Assigned(entry) and (IEnumerable(PByte(obj) + entry.IOffset).GetCountFast >= 0);
752753
end;
753754
end;
754755

@@ -1751,7 +1752,6 @@ function TEnumerableBase<T>.ToArray: TArray<T>;
17511752
enumerator: IEnumerator<T>;
17521753
count, capacity: Integer;
17531754
begin
1754-
Result := nil;
17551755
count := 0;
17561756
capacity := 0;
17571757
enumerator := IEnumerable<T>(this).GetEnumerator;
@@ -3569,32 +3569,62 @@ function TIteratorBase<T>.Take(count: Integer): IEnumerable<T>;
35693569
Result := inherited Take(count);
35703570
end;
35713571

3572+
function TIteratorBase<T>.PartitionToArray(var values: TArray<T>): Boolean;
3573+
var
3574+
count, index, i: Integer;
3575+
source: Pointer;
3576+
begin
3577+
Result := SupportsIndexedAccess(fSource);
3578+
if Result then
3579+
begin
3580+
index := fIndex;
3581+
count := fSource.Count - index;
3582+
if count > fCount then
3583+
count := fCount
3584+
else if count < 0 then
3585+
count := 0;
3586+
SetLength(values, count);
3587+
source := Pointer(fSource);
3588+
for i := 0 to count - 1 do
3589+
begin
3590+
IEnumerable<T>(source).TryGetElementAt(values[i], index);
3591+
Inc(index);
3592+
end;
3593+
Result := True;
3594+
end;
3595+
end;
3596+
35723597
function TIteratorBase<T>.ToArray: TArray<T>;
35733598
begin
35743599
case fKind of
3600+
TIteratorKind.Partition:
3601+
if PartitionToArray(Result) then Exit;
35753602
TIteratorKind.Array:
35763603
begin
35773604
Result := fItems;
35783605
SetLength(Result, Length(Result));
3606+
Exit;
35793607
end;
35803608
TIteratorKind.Ordered:
35813609
begin
35823610
Result := fSource.ToArray;
35833611
TArray.Sort<T>(Result, IComparer<T>(fPredicate));
3612+
Exit;
35843613
end;
35853614
TIteratorKind.Reversed:
35863615
begin
35873616
Result := fSource.ToArray;
35883617
TArray.Reverse<T>(Result);
3618+
Exit;
35893619
end;
35903620
TIteratorKind.Shuffled:
35913621
begin
35923622
Result := fSource.ToArray;
35933623
TArray.Shuffle<T>(Result);
3624+
Exit;
35943625
end;
3595-
else
3596-
Result := inherited ToArray;
35973626
end;
3627+
Result := inherited ToArray;
35983628
end;
35993629

36003630
function TIteratorBase<T>.TryGetElementAt(var value: T; index: Integer): Boolean;

0 commit comments

Comments
 (0)