CodeBlanks Logo Icon CodeBlanks

CNN model

Define a CNN with Conv2d and MaxPool2d.

The CNN model

A small model of two convolution blocks and a linear classifier is enough. The 16×16 image is halved at every pooling: 16 → 8 → 4:

model = nn.Sequential(
    nn.Conv2d(1, 8, 3, padding=1), nn.ReLU(), nn.MaxPool2d(2),    # (8, 8, 8)
    nn.Conv2d(8, 16, 3, padding=1), nn.ReLU(), nn.MaxPool2d(2),   # (16, 4, 4)
    nn.Flatten(),                                                 # 256
    nn.Linear(16 * 4 * 4, 2))

After training, the first layer's filters start to look like horizontal and vertical edge detectors.

Printing intermediate shapes

The modules of an nn.Sequential can be walked one by one; printing the shape after each layer is a fast way to verify the architecture:

x = torch.zeros(1, 1, 16, 16)
for katman in model:
    x = katman(x)
    print(type(katman).__name__, tuple(x.shape))

The parameter count of the weighted layers is also computed to check the total model size.

Practice Build the model

For the given model, print the shape of a (1, 1, 16, 16) input after every MaxPool2d on separate lines. Then print the model's total parameter count.

Starter code

model.py
import torch
from torch import nn

torch.manual_seed(0)
def veri(n):
    X = torch.rand(n, 1, 16, 16) * 0.3
    y = torch.randint(0, 2, (n,))
    for k in range(n):
        if y[k] == 0:
            X[k, 0, 7:9, :] += 1.0
        else:
            X[k, 0, :, 7:9] += 1.0
    return X, y

X_train, y_train = veri(256)
X_test, y_test = veri(64)

model = nn.Sequential(
    nn.Conv2d(1, 8, 3, padding=1), nn.ReLU(), nn.MaxPool2d(2),
    nn.Conv2d(8, 16, 3, padding=1), nn.ReLU(), nn.MaxPool2d(2),
    nn.Flatten(), nn.Linear(16 * 4 * 4, 2))

# buraya yaz

Sample solution

model.py
import torch
from torch import nn

torch.manual_seed(0)
def veri(n):
    X = torch.rand(n, 1, 16, 16) * 0.3
    y = torch.randint(0, 2, (n,))
    for k in range(n):
        if y[k] == 0:
            X[k, 0, 7:9, :] += 1.0
        else:
            X[k, 0, :, 7:9] += 1.0
    return X, y

X_train, y_train = veri(256)
X_test, y_test = veri(64)

model = nn.Sequential(
    nn.Conv2d(1, 8, 3, padding=1), nn.ReLU(), nn.MaxPool2d(2),
    nn.Conv2d(8, 16, 3, padding=1), nn.ReLU(), nn.MaxPool2d(2),
    nn.Flatten(), nn.Linear(16 * 4 * 4, 2))

x = torch.zeros(1, 1, 16, 16)
for katman in model:
    x = katman(x)
    if isinstance(katman, nn.MaxPool2d):
        print(x.shape)
print(sum(p.numel() for p in model.parameters()))

Expected output

torch.Size([1, 8, 8, 8])
torch.Size([1, 16, 4, 4])
1762

Questions and answers

Review the lesson questions together with their answers. To test yourself, solve the lesson interactively.

1 How many features are there after Flatten in this model?

  • 1024
  • 64
  • 256 Correct answer
  • 16

Explanation: 16 channels × 4 × 4 = 256.

2 Print the layer's name.

Question
print(type(katman).____, tuple(x.shape))
Answer
print(type(katman).__name__, tuple(x.shape))

Explanation: __name__ gives the class's name.

3 Match the shapes (input 1×16×16).

Term Meaning
Conv2d(1, 8) + Pool (8, 8, 8)
Conv2d(8, 16) + Pool (16, 4, 4)
Flatten 256
Linear 2

All lessons in Advanced