ListBox 의 사용자정의 정렬은 TStringList 의 CustomSort 메소드를 이용하시면 가능합니다.
TStringList 객체는 소팅 순서를 마음대로 조정할 수 있는 CustomSort 메소드를
지원하는데, 이 CustomSort 메소드의 인자로는 TStringList 내의 두 아이템을
비교해서 결과값을 돌려주는 함수가 넘어갑니다.
함수를 생성한후, CustomSort의 인자로 그 함수를 집어 넣어주면 됩니다.
두 아이템을 비교해서 index1이 더 크면(더 뒤에 나와야하면)
0보다 큰 값을 Index2의 값이 더 크면 0보다 작은 값을 리턴하면 됩니다.
같으면 0을 리턴하구요.
CustomSort는 내부적으로 퀵소트를 사용하기 때문에 성능도 아주 좋다구 합니다.
아래는 ListBox 의 사용자정의 정렬을 하는 예시입니다.
{ To sort Date values:}
function CompareDates(List: TStringList; Index1, Index2: Integer): Integer;
var
d1, d2: TDateTime;
begin
d1 := StrToDate(List[Index1]);
d2 := StrToDate(List[Index2]);
if d1 < d2 then
Result := -1
else if d1 > d2 then Result := 1
else
Result := 0;
end;
{ To sort Integer values:}
function CompareInt(List: TStringList; Index1, Index2: Integer): Integer;
var
d1, d2: Integer;
r1, r2: Boolean;
function IsInt(AString : string; var AInteger : Integer): Boolean;
var
Code: Integer;
begin
Val(AString, AInteger, Code);
Result := (Code = 0);
end;
begin
r1 := IsInt(List[Index1], d1);
r2 := IsInt(List[Index2], d2);
Result := ord(r1 or r2);
if Result <> 0 then
begin
if d1 < d2 then
Result := -1
else if d1 > d2 then
Result := 1
else
Result := 0;
end else
Result := lstrcmp(PChar(List[Index1]), PChar(List[Index2]));
end;
function MyCompareStr(List:TStringList; Index1,Index2:Integer) : Integer;
var
S1 , S2 : string;
begin
S1 := List[Index1];
S2 := List[Index2];
if Length(S1)=Length(S2) then
begin
if CompareStr(S1,S2)<0 then Result := -1
else if CompareStr(S1,S2)>0 then Result := 1
else Result :=0
end else
begin
if Length(S1)<Length(S2) then Result := -1
else if Length(S1)>Length(S2) then Result := 1
end;
end;
Delphi Help에서 TStringList의 CustomSort가 뮌지 잘 몰랐었는데..
뉴스그룹의 내용을 퍼서 대충 번역해두었던 내용입니다.
보시고 참고하셔서 즐거운 프로그래밍 하시길..
ListBox 의 사용자정의 정렬은 TStringList 의 CustomSort 메소드를 이용하시면 가능합니다.
TStringList 객체는 소팅 순서를 마음대로 조정할 수 있는 CustomSort 메소드를
지원하는데, 이 CustomSort 메소드의 인자로는 TStringList 내의 두 아이템을
비교해서 결과값을 돌려주는 함수가 넘어갑니다.
type TStringListSortCompare = function(List: TStringList; Index1, Index2: Integer): Integer;
procedure CustomSort(Compare: TStringListSortCompare); virtual;
함수를 생성한후, CustomSort의 인자로 그 함수를 집어 넣어주면 됩니다.
두 아이템을 비교해서 index1이 더 크면(더 뒤에 나와야하면)
0보다 큰 값을 Index2의 값이 더 크면 0보다 작은 값을 리턴하면 됩니다.
같으면 0을 리턴하구요.
CustomSort는 내부적으로 퀵소트를 사용하기 때문에 성능도 아주 좋다구 합니다.
아래는 ListBox 의 사용자정의 정렬을 하는 예시입니다.
{ To sort Date values:}
function CompareDates(List: TStringList; Index1, Index2: Integer): Integer;
var
d1, d2: TDateTime;
begin
d1 := StrToDate(List[Index1]);
d2 := StrToDate(List[Index2]);
if d1 < d2 then
Result := -1
else if d1 > d2 then Result := 1
else
Result := 0;
end;
procedure TForm1.Button1Click(Sender: TObject);
var
sl: TStringList;
begin
sl := TStringList.Create;
try
// listbox1.Sorted := False !
sl.Assign(listbox1.Items);
sl.CustomSort(CompareDates);
listbox1.Items.Assign(sl);
finally
sl.Free
end;
end;
end.
{ To sort Integer values:}
function CompareInt(List: TStringList; Index1, Index2: Integer): Integer;
var
d1, d2: Integer;
r1, r2: Boolean;
function IsInt(AString : string; var AInteger : Integer): Boolean;
var
Code: Integer;
begin
Val(AString, AInteger, Code);
Result := (Code = 0);
end;
begin
r1 := IsInt(List[Index1], d1);
r2 := IsInt(List[Index2], d2);
Result := ord(r1 or r2);
if Result <> 0 then
begin
if d1 < d2 then
Result := -1
else if d1 > d2 then
Result := 1
else
Result := 0;
end else
Result := lstrcmp(PChar(List[Index1]), PChar(List[Index2]));
end;
procedure TForm1.Button1Click(Sender: TObject);
var
sl: TStringList;
begin
sl := TStringList.Create;
try
// listbox1.Sorted := False;
sl.Assign(listbox1.Items);
sl.CustomSort(CompareInt);
listbox1.Items.Assign(sl);
finally
sl.Free;
end;
end;