Вы должны быть в состоянии использовать отражение для этого:
Random r = new Random(1);
Field f;
try {
f = r.getClass().getDeclaredField("seed");
f.setAccessible(true);
AtomicLong seed = (AtomicLong) f.get(r);
System.out.println("seed: " + seed);
f = r.getClass().getDeclaredField("mask");
f.setAccessible(true);
Long mask = (Long) f.get(r);
System.out.println("mask: " + mask);
f = r.getClass().getDeclaredField("multiplier");
f.setAccessible(true);
Long multiplier = (Long) f.get(r);
System.out.println("multiplier: " + multiplier);
long initialSeed = (seed.longValue()^multiplier);
System.out.println("restored initial seed: " + initialSeed);
} catch (NoSuchFieldException e1) {
} catch (SecurityException e2) {
} catch (IllegalAccessException e3) {
} catch (IllegalArgumentException e4) {
}
Выход на моей машине:
seed: 25214903916
mask: 281474976710655
multiplier: 25214903917
restored initial seed: 1
Когда seed
установлен, то значение скремблировавшего:
public Random(long seed) {
if (getClass() == Random.class)
this.seed = new AtomicLong(initialScramble(seed));
else {
// subclass might have overriden setSeed
this.seed = new AtomicLong();
setSeed(seed);
}
}
private static long initialScramble(long seed) {
return (seed^multiplier) & mask; // (seed XOR multiplier) AND mask
}
Однако mask
и multiplier
определяются как:
private static final long mask = (1L << 48) - 1;
private static final long multiplier = 0x5DEECE66DL;
Как mask
это все 1
s для младших 48 бит и XOR является обратимым, вы можете получить обратно начальное семя, если (и только если!) Он был меньше, чем (1L < < 48) , то есть 2^48:
выход для:
Random r = new Random((1L << 48)-1);
seed: 281449761806738
mask: 281474976710655
multiplier: 25214903917
restored initial seed: 281474976710655
и:
Random r = new Random((1L << 48));
seed: 25214903917
mask: 281474976710655
multiplier: 25214903917
restored initial seed: 0
См. Также this answer on StackOverflow
Считаете ли вы, что это легко с 'getLong'? Кроме того, вы имеете в виду при первом вызове 'getInt' или произвольном вызове? –
http://stackoverflow.com/questions/15236151/inverse-function-of-javas-random-function И вызов getInt() без параметров 2 раза – mcat