I have a Java program that loads thirdparty class files (classes I did not write) and executes them. These classes often use java.util.Random
, which by default generates random starting seed values every time it gets instantiated. For reasons of reproducability, I want to give these classes the same starting seed every time, changing it only at my discretion.
Here are some of the obvious solutions, and why they don't work:
Use a different Random class in the thirdparty classfiles. The problem here is I only load the class files, and cannot modify the source.
Use a custom classloader to load our own Random class instead of the JVM's version. This approach will not work because Java does not allow classloaders to override classes in the java
package.
Swap out the rt.jar's java.util.Random
implementation for our own, or putting files into trusted locations for the JVM. These approaches require the user of the application messing with the JVM install on their machine, and are no good.
Adding a custom java.util.Random
class to the bootclasspath. While this would technically work, for this particular application, it is impractical because this application is intended for end users to run from an IDE. I want to make running the app convenient for users, which means forcing them to set their bootclasspath is a pain. I can't hide this in a script, because it's intended to be run from an IDE like Eclipse (for easy debugging.)
So how can I do this?
There are two ways we can generate random number using seed. Random random = new Random(long seed); Random random1 = new Random(); random1. setSeed(seed); The seed is the initial value of the internal state of the pseudorandom number generator which is maintained by method next(int).
The "random" numbers generated by the mathematical algorithm are given a starting number (called the "seed") and always generates the same sequence of numbers. Since the same sequence is generated each time the seed remains the same, the sequence of random numbers is referred to as being a pseudo-random sequence.
For most purposes you don't need to retrieve the current seed. For example if your purpose is to have two Random generators which generate the same sequence of values, then you don't need to retrieve the random seed: you just create those two Random objects with the same (pre-set) seed.
In Java Edition, the player can enter the command /seed to view the world's seed. This command is available in singleplayer worlds even if cheats are off. The player can also select 'Re-create' in the Worlds menu to see the seed.
Your option 2 will actually work, with the following directions.
You will need ( as anjab said ) to change the bootstrap class path .
In the command line of the program you need to add the following:
java -Xbootclasspath/p:C:\your\random_impl.jar YourProgram
Assuming you're on Windown machine or the path for that matter in any OS.
That option adds the classes in jar files before the rt.jar are loaded. So your Random will be loaded before the rt.jar Random class does.
The usage is displayed by typing :
java -X
It displays all the X(tra) features de JVM has. It may by not available on other VM implementations such as JRockit or other but it is there on Sun JVM.
-Xbootclasspath/p: prepend in front of bootstrap class path
I've use this approach in an application where the default ORB class should be replaced with others ORB implementation. ORB class is part of the Java Core and never had any problem.
Good luck.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With