We can't find the internet
Attempting to reconnect
Something went wrong!
Attempting to reconnect
← Batching and the Data Path step 5 of 5
Shuffle the same way twice
A random generator has state. Drawing a permutation advances that state, so calling randperm twice on one generator does not restart the sequence. To repeat a shuffle, start each call from the same generator state:
import torch
n = 6
g1 = torch.Generator().manual_seed(42)
first = torch.randperm(n, generator=g1)
_ = torch.rand(10) # Draws from the default CPU generator, not g1.
g2 = torch.Generator().manual_seed(42)
second = torch.randperm(n, generator=g2)
print(torch.equal(first, second)) # True
This keeps the shuffle independent of unrelated default-generator draws. It does not make the generator immutable: any code given g1 can advance it.
Seeds, state and call order
Global seeding can reproduce a sequence when the operations and their order stay the same. An extra draw from the same generator changes its state and can change subsequent results. PyTorch has separate default generators for CPU and accelerator devices; not every random operation uses one shared stream. Python and NumPy also have their own random state.
An explicit generator lets you control which operations share a stream. For the same n and compatible runtime, fresh CPU generators initialized with the same seed produce the same permutation. Reusing one generator without resetting it gives successive draws, which can occasionally coincide. Exact sequences are not guaranteed across PyTorch releases or devices.
Data loading and numerical determinism
DataLoader's generator can control its random sampler and the base seeds used for multiprocessing workers. DataLoader seeds workers automatically; worker_init_fn lets you initialize additional random sources used by your own dataset code. Those sources and worker lifetime also matter for reproducibility. Seeding the sampler alone does not control every possible augmentation library.
Random draws are only part of repeatability. Some operations can produce
different numerical results because their execution order varies.
torch.use_deterministic_algorithms(True) selects deterministic alternatives
for supported operations and raises for known unsupported cases by default.
It is useful, but is not a guarantee that a whole program reproduces across
different hardware, library versions or external data sources.
Your task
def shuffles(n: int, seed: int) -> dict
Produce two CPU permutations of the integers from zero through n-1 using
fresh generators with the supplied seed. Keep the starter's unrelated global
random draws. Return the permutations as lists under first and second,
and their equality as the boolean agree.
The starter reseeds the global generator before its second shuffle, then draws one random value before calling randperm. That extra draw changes the starting state for the second permutation. The permutations may still match by chance; for n=1 there is only one possible order.
The harness checks that both lists are valid permutations and that they actually agree. It does not require a particular order, which avoids tying the expected output to one PyTorch version's random sequence.
Understand the ideas behind this exercise. The Problem tab contains the exact implementation requirements.
A random generator has state. Drawing a permutation advances that state, so calling randperm twice on one generator does not restart the sequence. To repeat a shuffle, start each call from the same generator state:
import torch
n = 6
g1 = torch.Generator().manual_seed(42)
first = torch.randperm(n, generator=g1)
_ = torch.rand(10) # Draws from the default CPU generator, not g1.
g2 = torch.Generator().manual_seed(42)
second = torch.randperm(n, generator=g2)
print(torch.equal(first, second)) # True
This keeps the shuffle independent of unrelated default-generator draws. It does not make the generator immutable: any code given g1 can advance it.
Seeds, state and call order
Global seeding can reproduce a sequence when the operations and their order stay the same. An extra draw from the same generator changes its state and can change subsequent results. PyTorch has separate default generators for CPU and accelerator devices; not every random operation uses one shared stream. Python and NumPy also have their own random state.
An explicit generator lets you control which operations share a stream. For the same n and compatible runtime, fresh CPU generators initialized with the same seed produce the same permutation. Reusing one generator without resetting it gives successive draws, which can occasionally coincide. Exact sequences are not guaranteed across PyTorch releases or devices.
Data loading and numerical determinism
DataLoader's generator can control its random sampler and the base seeds used for multiprocessing workers. DataLoader seeds workers automatically; worker_init_fn lets you initialize additional random sources used by your own dataset code. Those sources and worker lifetime also matter for reproducibility. Seeding the sampler alone does not control every possible augmentation library.
Random draws are only part of repeatability. Some operations can produce
different numerical results because their execution order varies.
torch.use_deterministic_algorithms(True) selects deterministic alternatives
for supported operations and raises for known unsupported cases by default.
It is useful, but is not a guarantee that a whole program reproduces across
different hardware, library versions or external data sources.
Your code, saved here
Sign in to access your accepted solutions and saved draft history. You can keep reading the lesson without an account.
Sign in to your accountStuck?
PyTorch reference solution
Sign in to track your attempts toward unlocking the reference solution.