Delphi中Stringlist的自定义排序(将函数地址做为参数)
Posted lzszs
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Delphi中Stringlist的自定义排序(将函数地址做为参数)相关的知识,希望对你有一定的参考价值。
近日,在编制一个程序过程,因为数据量较小,就使用了stringlist来暂存数据。在使用过程中,遇到了一个问题。Stringlist字符串列表的默认排序方法是按ASCII码的方式进行排序,如3,10,9排序时,结果为10,3,9.不符合程序的要求,于是尝试着使用字符串列表的自主义排序方法,这时需要传入一个function类的参数,因为习惯于使用PYTHON语言,所以直接编写民了一个按数值降序排列的排序函数,并将函数名传给了stringlistrr的CustomSort方法,结果提示:Incompatible types: ‘regular procedure and method pointer‘。大致意思是:不匹配的类型:需要一个方法、过程的指针类型。
为了解决这个问题,到网上查找资料,发现这个问题经常会遇到,但是各个解答要不就是看不懂,要不就是运行不成功,经过多次尝试,最终解决了这个问题。
通过分析源代码,结合网上程序,理清了网上的解决思路:1、在type处,定义一个function类型,.如:Tfunc=function(list: TStringList; index1,index2: Integer): Integer; 2、定义一个全局变量:如:myfunc:Tfunc;
3、编写一个自定义的排序程序:如以下程序
function curmsort(list: TStringList; index1, index2: Integer): Integer; var value1, value2: Integer; begin value1 := StrToInt(list.Strings[index1]); value2 := StrToInt(list.Strings[index2]); if value1> value2 then Result := -1 else if value1< value2 then Result := 1 else Result := 0; end;
4、在排序时,首先执行myfunc:=curmsort;(将自定义的函数名赋值给myfunc变量。)list.sorted:=False;,关闭排序,然后执行list.CustomSort(myfunc);
按照这个思路,最终也完成了自定义排序(将函数地址传参)的功能。
完成后,回顾整个程序,通过对比、思考、实验,发现第一、二步和最后一步的将函数名赋值给函数类型的变量都是可以省略的,关键的是自己定义的排序函数curmsort不能进行声明,只要声明了就不好使,个人感觉应该是因为在不声明的情况下,函数名仅代表的是函数的内存地址,而不是执行函数的返回值。前边的失败是因为将函数进行了声明,这时函数名代表了函数执行后的返回值,所以才导致类型不匹配。
例程如下:
unit Unit1; interface uses Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls; type TForm1 = class(TForm) lst1: TListBox; lst2: TListBox; btn1: TButton; procedure btn1Click(Sender: TObject); private //注意,自定义的函数curmsort不能进行声明。 { Private declarations } public { Public declarations } end; var Form1: TForm1; implementation {$R *.dfm} function curmsort(list: TStringList; index1, index2: Integer): Integer; //写函数时,函数名前不能加Tform1等限制。 var value1, value2: Integer; begin value1 := StrToInt(list.Strings[index1]); value2 := StrToInt(list.Strings[index2]); if value1> value2 then Result := -1 else if value1< value2 then Result := 1 else Result := 0; end; procedure TForm1.btn1Click(Sender: TObject); var list:TStringList;i:Integer; begin list:=TStringList.Create; for i:=0 to 30 do begin list.Add(IntToStr(Random(3000))); end; lst1.Items.Assign(list); list.Sorted:=False; list.CustomSort(curmsort); lst2.Items.Assign(list); end; end.
以上是关于Delphi中Stringlist的自定义排序(将函数地址做为参数)的主要内容,如果未能解决你的问题,请参考以下文章