A lottery algorithm is implemented by the interval distribution of random numbers. Accept a list that contains the odds of winning a prize and return the prize.
Define an abstract award category first.
Public abstract class Abstractprize {
/**
* Prize probability * *
private double probability;
Public double getprobability () {return
probability;
}
public void setprobability (double probability) {
this.probability = probability;
}
}
Lottery algorithm, the idea is through the prize jackpot probability of the maximum number of digits to obtain a base, such as prizes for a,b,c,d,e winning probability is 0.3,0.050,0.1,0.3,0.25, then get the base is 1000, the prize distribution between the 0<=a< 300,300<b<350,350<=c<450,450<=d<750,750<=e<1000, then gets a 0-1000 random number, sequentially traversing the prize (very important, not multi-threaded traversal), <300 return a,<350 return b,<450 return c,<750 return to d,<1000 return E.
/** *
Lottery algorithm
* @param prizes
* @param <T> *
@return
* @throws illegalargumentexception
*/< C6/>public static <T> T lotteryfunction (list<? extends Abstractprize> Prizes) throws illegalargumentexception{
Prizes = Prizes.stream (). Filter (e-> e.getprobability ()!= 0d). Collect (Collectors.tolist ());
Double base = this.verification (prizes);
int index = 0;
if (base!= 0d) {
BigDecimal fixrate = new BigDecimal ("0");
Generate random number
Random Random = new Random ();
Long result = Nextlong (random, Base.longvalue ());
BigDecimal res = new BigDecimal (string.valueof (Result));
Calculate the prize range for
(abstractprize prize:prizes) {
if (prize.getprobability () = 0d) {
continue;
}
Fixrate = Fixrate.add (New BigDecimal (String.valueof (Prize.getprobability ()))
. Multiply (New BigDecimal ( String.valueof (base)));
Boolean flag = Res.compareto (fixrate) = = 1;
if (flag) {break
;
}
index++;
}
if (index <= prizes.size ()-1) {return
(T) prizes.get (index);
}
}
return null;
}
/** * Produces a long random number within a specified range * @param rng * @param n * @return */private static long Nextlong (Random rng, long N) {
Long Bits, Val;
do {bits = (Rng.nextlong () << 1) >>> 1;
val = bits% n;
while (bits-val+ (n-1) < 0L);
return Val; /** * Calculates cardinality accuracy, verifies all probabilities and cannot exceed 1 * @param prizes * @return * @throws illegalargumentexception * * private static Double ve Rification (list< extends abstractprize> prizes) throws illegalargumentexception{BigDecimal ratesum = new Bigde
Cimal ("0");
Double base = 0d; for (Abstractprize prize:prizes) {ratesum = Ratesum.add (New BigDecimal (String.valueof ()))
; Boolean verify = prize.getprobability () < 0 | |
Ratesum.compareto (New BigDecimal ("1")) = = 1;
if (verify) {throw new IllegalArgumentException ("Probability error");
String str = prize.getprobability () + "";
int len = str.length ()-Str.indexof (".")-1; The minimum cardinality is 100, as if there is no need Double temp = Math.pow (10,len < 2 2:len);
if (Temp > Base) {base = temp;
} return base; }