This is very convenient in Python
HTML-код
- Опубликовано: 9 июн 2024
- In this video we will be looking at some really cool functionality that we can use in Python to get consistent results from random number generation. This is really good to know if you need to test scripts and want to "freeze" the results while testing.
Alyce's awesome Python blog: garden-silk.vercel.app/
▶ Become job-ready with Python:
www.indently.io
▶ Follow me on Instagram:
/ indentlyreels
What I still find amusing is that unless explicitly told something else, pretty much everyone will use 42 as the random state. Almost as certainly as a standard print will be "Hello world".
nah, I usually use 0xDEADBEEF
When asking people for a random number between 1 and 100, the most common answer, by far, is 37. IIRC 42 was 2nd place. Veritasium made a nice video about it.
Nahh I’d use 232323
My random string is always “Farts”
@@arkie87i use hi because it’s quick to type on one hand
There are probably better use cases, but it looks a bit overly complicated here.
If you want some reproducible random sequence, set the seed to a number (as shown); if you want to restore default behavior, set it back to None.
This wraps it in a way you don't need try/catch in the main code, in case an exception occurs, it will always restore the state regardless when exiting the with... block.
Nice! random with seeds wpuld be so useful for testing
The generation of random numbers is too important to be left to chance.
…as TDD states ☝🏻
I would use the random.Random class instead. That would be much simpler.
Maybe you could share what you mean by that with the rest of us? :)
@@Indentlythe `Random` class is essentially a local PRNG that won't affect the global `random` - I believe you just instantiate it with a seed (optional iirc) and then call methods that are equivalent to the `random` module itself.
Apart from saving you a context manager and an indent, it also means that you can have multiple separate seeded randoms simultaneously without affecting each other.
@@Indently As @SleepyHarryZzzz said, it is a class in the random module;
You can instantiate like this
rand = random.Random(seed) # the seed is the seed that you chose
Now you have a Random instance (object) in the variable 'rand', from this object you can access any random method.
you can get randomness by any method like rand.random() or rand.randrange(10) or rand.expovariate() or rand.choice(["a","b","c"]) or whatever random function.
That object behaves like the whole random module and its state is initialized by the seed you chose; at any point in the code, you can also modify the seed by using rand.seed(your_new_seed)
You can also get its current state exactly by rand.getstate() or even modify it by rand.setstate(your_new_state)
The object behaves exactly like an independent random module with its own independent state.
You can instantiate as many *random.Random()* objects as you want. *Each one will behave independently and does not affect the state of the others nor the state of the whole random module.*
Really depends how far ahead you thought out your program then. With this context manager it doesn't matter what you named things, the seed will be applied inside the with block :)
There's two things I don't like about this solution:
1. It uses global state and 2. adding and removing a with block is a little cumbersome in python because you need to manually set the indentation instead of just setting the exact block that you want, and because there's no RAII. If this was C++ it'd be much easier because you don't even need to wrap the thing in a block, you can just plop it in whatever block you're currently working on.
Whenever I need this I just grab a default_rng(42) from numpy. That way I can set/unset the seed programmatically, without having to change the structure of the code.
Just here on time 😉
You can also use this as function decorator
Ahhh that's useful!
Where is the link to the blog?
Oh god, I forgot! (I will update the description now)
garden-silk.vercel.app/
Thanks @@Indently.
Not awake/no caffeine brain says "wait, shouldn't setting the seed happen first?" No, remember that this is a generator and what we're doing here: For the duration of the generator, we're changing the random seed to a fixed value-temporarily! We get the existing state so that we save the presumably actually random (or pretty close) randomness that actually exists in the system, then we change it to a fixed number. But in the finally block we have to put our saved state back so that future random calls outside of the context will be random again.
Thanks!
Thank you! :)
@@Indently On my way to watch your context manager video now!
So its its pretty much how random is dependent on seed in Minecraft?
Link to the github example would be also nice...
This seems like an abuse of a generator and using it for testing means you have to indent all the stuff you want to test to put it in the with block, and it obscures what’s going on. I don’t like it.
Well, you'd indent everything if all the code is thrown in the global scope, otherwise it would be as simple as wrapping the main function call with the context manager.
-> Nine
Ooooorrrr just write unit tests with your desired numbers, like you are supposed to anyway when developing anything
minecraft python edition?
useless. Just use random.seed = 42. Done.
Real