Generator and discriminator are two parts of a system that learn together. The generator tries to create fake data that looks real, and the discriminator tries to tell real data from fake data.
Generator and discriminator in PyTorch
class Generator(nn.Module): def __init__(self): super().__init__() # define layers def forward(self, x): # generate fake data return generated_data class Discriminator(nn.Module): def __init__(self): super().__init__() # define layers def forward(self, x): # predict real or fake return prediction
The generator creates fake data from random noise.
The discriminator outputs a score showing if data is real or fake.
class Generator(nn.Module): def __init__(self): super().__init__() self.linear = nn.Linear(100, 28*28) def forward(self, x): x = self.linear(x) x = torch.sigmoid(x) return x.view(-1, 1, 28, 28)
class Discriminator(nn.Module): def __init__(self): super().__init__() self.linear = nn.Linear(28*28, 1) def forward(self, x): x = x.view(-1, 28*28) x = self.linear(x) return torch.sigmoid(x)
This code shows a simple training step for generator and discriminator. The discriminator learns to tell real from fake data. The generator learns to fool the discriminator.
import torch import torch.nn as nn import torch.optim as optim class Generator(nn.Module): def __init__(self): super().__init__() self.linear = nn.Linear(100, 28*28) def forward(self, x): x = self.linear(x) x = torch.sigmoid(x) return x.view(-1, 1, 28, 28) class Discriminator(nn.Module): def __init__(self): super().__init__() self.linear = nn.Linear(28*28, 1) def forward(self, x): x = x.view(-1, 28*28) x = self.linear(x) return torch.sigmoid(x) # Create models G = Generator() D = Discriminator() # Optimizers opt_G = optim.Adam(G.parameters(), lr=0.001) opt_D = optim.Adam(D.parameters(), lr=0.001) # Loss function criterion = nn.BCELoss() # Fake noise input noise = torch.randn(4, 100) # Real data (random for example) real_data = torch.rand(4, 1, 28, 28) # Labels real_labels = torch.ones(4, 1) fake_labels = torch.zeros(4, 1) # Train Discriminator opt_D.zero_grad() # Real data loss output_real = D(real_data) loss_real = criterion(output_real, real_labels) # Fake data loss fake_data = G(noise).detach() # detach to avoid training G here output_fake = D(fake_data) loss_fake = criterion(output_fake, fake_labels) # Total loss and backward loss_D = loss_real + loss_fake loss_D.backward() opt_D.step() # Train Generator opt_G.zero_grad() fake_data = G(noise) output = D(fake_data) loss_G = criterion(output, real_labels) # want D to think fake is real loss_G.backward() opt_G.step() print(f"Discriminator loss: {loss_D.item():.4f}") print(f"Generator loss: {loss_G.item():.4f}") print(f"Discriminator real output: {output_real.detach().cpu().numpy().flatten()}") print(f"Discriminator fake output: {output_fake.detach().cpu().numpy().flatten()}")
The generator and discriminator train in turns to improve each other.
Use sigmoid activation in the last layer of discriminator for probability output.
Detach fake data when training discriminator to avoid updating generator weights.
The generator creates fake data from random noise.
The discriminator tries to tell real data from fake data.
They train together to improve the quality of generated data.
Practice
generator in a GAN (Generative Adversarial Network)?Solution
Step 1: Understand the generator's purpose
The generator's job is to produce new data that looks like the real data by starting from random noise.Step 2: Differentiate from discriminator's role
The discriminator's role is to tell real data from fake, not to create data.Final Answer:
To create fake data from random noise -> Option CQuick Check:
Generator creates fake data = B [OK]
- Confusing generator with discriminator
- Thinking generator classifies data
- Assuming generator preprocesses data
Solution
Step 1: Check PyTorch model class structure
A PyTorch model must inherit from nn.Module and call super().__init__() in __init__.Step 2: Verify forward method and layers
class Discriminator(nn.Module): def __init__(self): super().__init__() self.fc = nn.Linear(784, 1) def forward(self, x): return torch.sigmoid(self.fc(x)) correctly defines the class with inheritance, super call, layer, and forward method.Final Answer:
Correct PyTorch discriminator class with inheritance and super call -> Option DQuick Check:
Proper nn.Module subclass = A [OK]
- Forgetting to inherit nn.Module
- Missing super().__init__() call
- Defining forward outside class
fake_output?
noise = torch.randn(16, 100) generator = Generator() fake_data = generator(noise) discriminator = Discriminator() fake_output = discriminator(fake_data)Assume generator outputs shape (16, 784) and discriminator outputs shape (batch_size, 1).
Solution
Step 1: Understand generator output shape
The generator outputs fake data with shape (16, 784), meaning batch size 16 and 784 features.Step 2: Understand discriminator input and output shape
The discriminator takes input of shape (16, 784) and outputs shape (16, 1), one score per sample.Final Answer:
torch.Size([16, 1]) -> Option AQuick Check:
Discriminator output shape = (batch_size, 1) = A [OK]
- Confusing input and output shapes
- Mixing batch size and feature dimensions
- Assuming output shape matches noise size
optimizer.zero_grad() output = discriminator(fake_data) loss = criterion(output, real_labels) loss.backward() optimizer.step()Assuming
fake_data is generated by the generator and real_labels are labels for real data.Solution
Step 1: Check input and labels for discriminator
The discriminator should compare fake_data with fake labels, not real_labels.Step 2: Identify label mismatch in loss calculation
Using real_labels with fake_data causes wrong loss and training signals.Final Answer:
Using real_labels for fake_data loss calculation -> Option AQuick Check:
Fake data needs fake labels = C [OK]
- Mixing real and fake labels
- Skipping zero_grad() call
- Forgetting loss.backward()
Solution
Step 1: Understand mode collapse and training stability
Mode collapse happens when generator produces limited outputs; discriminator tricks help prevent it.Step 2: Identify label smoothing effect
Label smoothing softens discriminator targets, preventing it from becoming too confident and stabilizing training.Final Answer:
Use label smoothing on discriminator targets -> Option BQuick Check:
Label smoothing stabilizes discriminator = D [OK]
- Ignoring discriminator role in stability
- Changing only generator learning rate
- Removing discriminator breaks GAN
Ready to prove it?
Pass the test and this pattern moves unknown
