有关电脑填彩票的小算法--给定数列,输出其随机数列
前几天有个朋友没事要我帮他填彩票,这事可真难倒了我,最好没事,所以花了点时间写了这个程序:即
给定一整数数列,随机输出其中几个/全部元素的算法.
是用 带头结点的单链表 加点面向对象的思想,
希望各位大侠们多多指点指教
type
TForm1 = class(TForm)
Button1: TButton;
Edit1: TEdit;
Label1: TLabel;
procedure Button1Click(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
type
point = ^node;
node=record
data:integer;
next:point;
end;
type
TLLine = class//Type of Linked Circle Line
private
TLLName : String;
TLLCount : Integer;
TLLpoint : point;
public
CONSTRUCTOR Create(data :array of integer);
DESTRUCTOR Destroy; override;
property Count :Integer read TLLCount WRITE TLLCount;
property Name : String read TLLName WRITE TLLName;
PROCEDURE RandomOut(var Changedarray: array of Integer );overload;
PROCEDURE RandomOut(num :Integer); overload;
end;
var
Form1: TForm1;
implementation {$R *.dfm}
PROCEDURE TLLine.RandomOut(var Changedarray: array of Integer ); //把输入数组元素打乱,结果放在所需要的数组里
VAR
I ,j : Integer;
RandomInt : Integer;
tempLinePoint : point;
ttP: point;
BEGIN
tempLinePoint := new(point); //欲删除的结点元素
ttP := new(point); //创建单链表的临时访问指针,主要为删除结点元素所点的指针
RandSeed:= DateTimeToTimeStamp(Now).Time; //随机数种子,把时间转换为毫秒数 = (时*60 + 分)*60*1000
Randomize; //随机数产生器
FOR I := 0 TO self.Count - 1 DO // Iterate
BEGIN
tempLinePoint := self.TLLpoint; //每次从单链表头结点开始
RandomInt := 1 + Random(self.Count - I);
FOR j := 1 TO RandomInt -1 DO // Iterate
BEGIN
tempLinePoint:= tempLinePoint.next ;
END; // for j
ttP := tempLinePoint.next;
Changedarray[low(Changedarray) + I] := ttp.data;
tempLinePoint.next := ttP.next;
dispose(ttP);
END; // for i
self.Count := 0;
end;
DESTRUCTOR TLLine.Destroy;
VAR
I: Integer;
tempLinePoint : point;
BEGIN
IF self.Count<> 0 THEN // 循环链队里还有元素时,删除所有元素,使之为空
BEGIN
FOR I := 1 TO self.Count DO // Iterate
BEGIN
tempLinePoint := self.TLLpoint.next; //每次从队结点开始
self.TLLpoint.next := tempLinePoint.next;
dispose(tempLinePoint);
END; // for
END;
dispose(self.TLLpoint);
INHERITED Destroy;
end;
CONSTRUCTOR TLLine.Create(data:ARRAY OF integer);
VAR
I : Integer;
tempP : Point;
BEGIN
INHERITED Create;
TLLpoint := new(point);
TLLpoint.next := TLLpoint;
TLLpoint.data := 0; //创建循环链表的队指针
FOR I := Low(data) TO High(data) DO // Iterate
BEGIN
tempP := new(point); //创建循环链表的元素结点
tempP.next := TLLpoint.next; TLLpoint.next := tempP;
tempP.data := data[I];
END; // for
self.Count := High(data) - Low(data) + 1;
TLLpoint.data := High(data) - Low(data) + 1;
end;
PROCEDURE TLLine.RandomOut(num:Integer); //按给定输入数组中,按要求输出其中几个不重复的随机项
VAR
s: STRING;
I ,j : Integer;
RandomInt : Integer;
tempLinePoint : point;
ttP: point;
BEGIN
s := '';
tempLinePoint := new(point); //欲删除的结点元素
ttP := new(point); //创建循环链表的临时访问指针,主要为删除结点元素所点的指针
IF num > self.Count THEN num := self.Count;
RandSeed:= DateTimeToTimeStamp(Now).Time; //随机数种子,把时间转换为毫秒数 = (时*60 + 分)*60*1000
Randomize; //随机数产生器
FOR I := 0 TO num - 1 DO // Iterate
BEGIN
tempLinePoint := self.TLLpoint; //每次从队结点开始
RandomInt := 1 + Random(self.Count - I);
FOR j := 1 TO RandomInt -1 DO // Iterate
BEGIN
tempLinePoint:= tempLinePoint.next ;
END; // for j
ttP := tempLinePoint.next;
s := s + IntToStr(ttp.data) + ' ';
tempLinePoint.next := ttP.next;
dispose(ttP);
END; // for i
ShowMessage(s);
self.Count := self.Count - num ;
end;
procedure TForm1.Button1Click(Sender: TObject);
VAR
I: Integer;
LLine : TLLine ;
arr:array[1..100] of integer;
arr2: array [2..8]of Integer;
S: STRING;
begin
// FOR I := 1 TO 100 DO arr[i] := 100 - i +1; // Iterate // for
// LLine := TLLine.Create(arr); // [54,34,3,72,1,0,11 ]
LLine := TLLine.Create([34,3,72,1,0,11,54 ]);
// ShowMessage(IntToStr(LLine.Count));
// LLine.RandomOut(StrToInt(Edit1.text)); //按给定输入数组中,按要求输出其中几个不重复的随机项
LLine.RandomOut(arr2); //结果放在所需要的数组里
FOR I := low(arr2) TO high(arr2) DO s := s + IntToStr(arr2[I]) + ' ' ;
ShowMessage(s);
//ShowMessage(IntToStr(LLine.Count));
LLine.Destroy;
end;
end.
PM 10:43 2005/10/23