Reputation: 3139
How can I create a random 64-bit integer value in Delphi 2006? The built-in integer-based Random() function seems to return only values between 0 and 2^31.
Upvotes: 5
Views: 3350
Reputation: 612824
Generate two 32 bit randoms and splice them together.
EDIT
Similar to @Andreas's answer I like the following (equivalent) implementation:
function Random64: UInt64;
var
Overlay: packed record
a, b: UInt32;
end absolute Result;
begin
Assert(SizeOf(Overlay)=SizeOf(Result));
Overlay.a := Random32;
Overlay.b := Random32;
end;
Upvotes: 10
Reputation: 108928
Simple:
function Random64: UInt64;
begin
PCardinal(@result)^ := Random32;
PCardinal(cardinal(@result) + 4)^ := Random32;
end;
where Random32
is your favourite 32-bit unsigned integer random number function.
Upvotes: 3
Reputation: 1513
You can generate 64 random bits and interpret the result as an integer. (63 bits if you are working with signed integers and want the result to be non-negative.) Equivalently you can take two random integers in the range 0..2^31-1, plus two extra random bits, and concatenate them to get a random 64-bit integer.
EDIT: I was curious about the statistical properties of pseudo-random numbers generated by concatenating pseudo-random components and found that (apparently) this approach might not work well depending on your pseudo-random generator (of course for true random number generation, as from atmospheric noise, concatenating random bits is no problem). For recreational use, the loss of various statistical properties might be acceptable, but for more serious use you might end up needing a custom pseudo-random generator as @gabr suggested. Here is a related question: Best method of generating a number with 256 random bits?
Upvotes: 4
Reputation: 3139
To answer my own question I came up with the following code:
function GetRandomInt64() : int64;
begin
Int64Rec(result).Words[0] := Random(High(Word));
Int64Rec(result).Words[1] := Random(High(Word));
Int64Rec(result).Words[2] := Random(High(Word));
Int64Rec(result).Words[3] := Random(High(Word));
end;
Not sure if this is a valid solution or it will always create the same follow-up number X+1 after a given result number X.
Upvotes: 4
Reputation: 26830
You can use my GpRandomGen. It implements Marsaglia/Zaman/James algorithm, is extremely fast and supposedly very random. Released as a freeware.
Upvotes: 16