📄 sockets.pas
字号:
begin
if (Index < 0) or (Index >= FCount) then
Exit;
Temp := Items[Index];
Dec(FCount);
if Index < FCount then
System.Move(FList^[Index + 1], FList^[Index],
(FCount - Index) * SizeOf(Pointer));
if Temp <> nil then
Notify(Temp, lnDeleted);
end;
procedure TList.Exchange(Index1, Index2: Integer);
var
Item: Pointer;
begin
if (Index1 < 0) or (Index1 >= FCount) then
Exit;
if (Index2 < 0) or (Index2 >= FCount) then
Exit;
Item := FList^[Index1];
FList^[Index1] := FList^[Index2];
FList^[Index2] := Item;
end;
function TList.Expand: TList;
begin
if FCount = FCapacity then
Grow;
Result := Self;
end;
function TList.First: Pointer;
begin
Result := Get(0);
end;
function TList.Get(Index: Integer): Pointer;
begin
Result := nil;
if (Index < 0) or (Index >= FCount) then
Exit;
Result := FList^[Index];
end;
procedure TList.Grow;
var
Delta: Integer;
begin
if FCapacity > 64 then
Delta := FCapacity div 4
else
if FCapacity > 8 then
Delta := 16
else
Delta := 4;
SetCapacity(FCapacity + Delta);
end;
function TList.IndexOf(Item: Pointer): Integer;
begin
Result := 0;
while (Result < FCount) and (FList^[Result] <> Item) do
Inc(Result);
if Result = FCount then
Result := -1;
end;
procedure TList.Insert(Index: Integer; Item: Pointer);
begin
if (Index < 0) or (Index > FCount) then
Exit;
if FCount = FCapacity then
Grow;
if Index < FCount then
System.Move(FList^[Index], FList^[Index + 1],
(FCount - Index) * SizeOf(Pointer));
FList^[Index] := Item;
Inc(FCount);
if Item <> nil then
Notify(Item, lnAdded);
end;
function TList.Last: Pointer;
begin
Result := Get(FCount - 1);
end;
procedure TList.Move(CurIndex, NewIndex: Integer);
var
Item: Pointer;
begin
if CurIndex <> NewIndex then
begin
if (NewIndex < 0) or (NewIndex >= FCount) then
Exit;
Item := Get(CurIndex);
FList^[CurIndex] := nil;
Delete(CurIndex);
Insert(NewIndex, nil);
FList^[NewIndex] := Item;
end;
end;
procedure TList.Put(Index: Integer; Item: Pointer);
var
Temp: Pointer;
begin
if (Index < 0) or (Index >= FCount) then
Exit;
if Item <> FList^[Index] then
begin
Temp := FList^[Index];
FList^[Index] := Item;
if Temp <> nil then
Notify(Temp, lnDeleted);
if Item <> nil then
Notify(Item, lnAdded);
end;
end;
function TList.Remove(Item: Pointer): Integer;
begin
Result := IndexOf(Item);
if Result >= 0 then
Delete(Result);
end;
procedure TList.Pack;
var
I: Integer;
begin
for I := FCount - 1 downto 0 do
if Items[I] = nil then
Delete(I);
end;
procedure TList.SetCapacity(NewCapacity: Integer);
begin
if (NewCapacity < FCount) or (NewCapacity > MaxListSize) then
Exit;
if NewCapacity <> FCapacity then
begin
ReallocMem(FList, NewCapacity * SizeOf(Pointer));
FCapacity := NewCapacity;
end;
end;
procedure TList.SetCount(NewCount: Integer);
var
I: Integer;
begin
if (NewCount < 0) or (NewCount > MaxListSize) then
Exit;
if NewCount > FCapacity then
SetCapacity(NewCount);
if NewCount > FCount then
FillChar(FList^[FCount], (NewCount - FCount) * SizeOf(Pointer), 0)
else
for I := FCount - 1 downto NewCount do
Delete(I);
FCount := NewCount;
end;
procedure QuickSort(SortList: PPointerList; L, R: Integer;
SCompare: TListSortCompare);
var
I, J: Integer;
P, T: Pointer;
begin
repeat
I := L;
J := R;
P := SortList^[(L + R) shr 1];
repeat
while SCompare(SortList^[I], P) < 0 do
Inc(I);
while SCompare(SortList^[J], P) > 0 do
Dec(J);
if I <= J then
begin
T := SortList^[I];
SortList^[I] := SortList^[J];
SortList^[J] := T;
Inc(I);
Dec(J);
end;
until I > J;
if L < J then
QuickSort(SortList, L, J, SCompare);
L := I;
until I >= R;
end;
procedure TList.Sort(Compare: TListSortCompare);
begin
if (FList <> nil) and (Count > 0) then
QuickSort(FList, 0, Count - 1, Compare);
end;
function TList.Extract(Item: Pointer): Pointer;
var
I: Integer;
begin
Result := nil;
I := IndexOf(Item);
if I >= 0 then
begin
Result := Item;
FList^[I] := nil;
Delete(I);
Notify(Result, lnExtracted);
end;
end;
procedure TList.Notify(Ptr: Pointer; Action: TListNotification);
begin
//nothing
end;
procedure TList.Assign(ListA: TList; AOperator: TListAssignOp; ListB: TList);
var
I: Integer;
LTemp, LSource: TList;
begin
if ListB <> nil then
begin
LSource := ListB;
Assign(ListA);
end
else
LSource := ListA;
case AOperator of
laCopy:
begin
Clear;
Capacity := LSource.Capacity;
for I := 0 to LSource.Count - 1 do
Add(LSource[I]);
end;
laAnd:
for I := Count - 1 downto 0 do
if LSource.IndexOf(Items[I]) = -1 then
Delete(I);
laOr:
for I := 0 to LSource.Count - 1 do
if IndexOf(LSource[I]) = -1 then
Add(LSource[I]);
laXor:
begin
LTemp := TList.Create;
try
LTemp.Capacity := LSource.Count;
for I := 0 to LSource.Count - 1 do
if IndexOf(LSource[I]) = -1 then
LTemp.Add(LSource[I]);
for I := Count - 1 downto 0 do
if LSource.IndexOf(Items[I]) <> -1 then
Delete(I);
I := Count + LTemp.Count;
if Capacity < I then
Capacity := I;
for I := 0 to LTemp.Count - 1 do
Add(LTemp[I]);
finally
LTemp.Free;
end;
end;
laSrcUnique:
for I := Count - 1 downto 0 do
if LSource.IndexOf(Items[I]) <> -1 then
Delete(I);
laDestUnique:
begin
LTemp := TList.Create;
try
LTemp.Capacity := LSource.Count;
for I := LSource.Count - 1 downto 0 do
if IndexOf(LSource[I]) = -1 then
LTemp.Add(LSource[I]);
Assign(LTemp);
finally
LTemp.Free;
end;
end;
end;
end;
{ TThread }
type
TSyncProc = record
Thread: TThread;
Signal: THandle;
end;
PSyncProc = ^TSyncProc;
var
ProcPosted: Boolean;
SyncList: TList = nil;
ThreadLock: TRTLCriticalSection;
ThreadCount: Integer;
WakeMainThread: TNotifyEvent = nil;
procedure AddThread;
begin
EnterCriticalSection(ThreadLock);
try
if (ThreadCount = 0) and (SyncList = nil) then
SyncList := TList.Create;
Inc(ThreadCount);
finally
LeaveCriticalSection(ThreadLock);
end;
end;
procedure RemoveThread;
begin
EnterCriticalSection(ThreadLock);
try
Dec(ThreadCount);
finally
LeaveCriticalSection(ThreadLock);
end;
end;
function CheckSynchronize: Boolean;
var
SyncProc: PSyncProc;
begin
Result := False;
if GetCurrentThreadID <> MainThreadID then
Exit;
if ProcPosted then
begin
EnterCriticalSection(ThreadLock);
try
Result := (SyncList <> nil) and (SyncList.Count > 0);
if Result then
begin
while SyncList.Count > 0 do
begin
SyncProc := SyncList[0];
SyncList.Delete(0);
try
SyncProc.Thread.FMethod;
except
SyncProc.Thread.FSynchronizeException := AcquireExceptionObject;
end;
SetEvent(SyncProc.signal);
end;
ProcPosted := False;
end;
finally
LeaveCriticalSection(ThreadLock);
end;
end else Result := False;
end;
function ThreadProc(Thread: TThread): Integer;
var
FreeThread: Boolean;
begin
try
if not Thread.Terminated then
try
Thread.Execute;
except
Thread.FFatalException := AcquireExceptionObject;
end;
finally
FreeThread := Thread.FFreeOnTerminate;
Result := Thread.FReturnValue;
Thread.FFinished := True;
Thread.DoTerminate;
if FreeThread then Thread.Free;
EndThread(Result);
end;
end;
constructor TThread.Create(CreateSuspended: Boolean);
begin
inherited Create;
AddThread;
FSuspended := CreateSuspended;
FCreateSuspended := CreateSuspended;
FHandle := BeginThread(nil, 0, @ThreadProc, Pointer(Self), CREATE_SUSPENDED, FThreadID);
end;
destructor TThread.Destroy;
begin
if (FThreadID <> 0) and not FFinished then
begin
Terminate;
if FCreateSuspended then
Resume;
WaitFor;
end;
if FHandle <> 0 then CloseHandle(FHandle);
inherited Destroy;
FFatalException.Free;
RemoveThread;
end;
procedure TThread.AfterConstruction;
begin
if not FCreateSuspended then
Resume;
end;
procedure TThread.CheckThreadError(ErrCode: Integer);
begin
end;
procedure TThread.CheckThreadError(Success: Boolean);
begin
if not Success then
CheckThreadError(GetLastError);
end;
procedure TThread.CallOnTerminate;
begin
if Assigned(FOnTerminate) then FOnTerminate(Self);
end;
procedure TThread.DoTerminate;
begin
if Assigned(FOnTerminate) then Synchronize(CallOnTerminate);
end;
const
Priorities: array [TThreadPriority] of Integer =
(THREAD_PRIORITY_IDLE, THREAD_PRIORITY_LOWEST, THREAD_PRIORITY_BELOW_NORMAL,
THREAD_PRIORITY_NORMAL, THREAD_PRIORITY_ABOVE_NORMAL,
THREAD_PRIORITY_HIGHEST, THREAD_PRIORITY_TIME_CRITICAL);
function TThread.GetPriority: TThreadPriority;
var
P: Integer;
I: TThreadPriority;
begin
P := GetThreadPriority(FHandle);
CheckThreadError(P <> THREAD_PRIORITY_ERROR_RETURN);
Result := tpNormal;
for I := Low(TThreadPriority) to High(TThreadPriority) do
if Priorities[I] = P then Result := I;
end;
procedure TThread.SetPriority(Value: TThreadPriority);
begin
CheckThreadError(SetThreadPriority(FHandle, Priorities[Value]));
end;
procedure TThread.Synchronize(Method: TThreadMethod);
var
SyncProc: TSyncProc;
begin
SyncProc.Signal := CreateEvent(nil, True, False, nil);
try
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -