diff --git a/minesweeper.py b/minesweeper.py
new file mode 100644
index 0000000..8d301e3
--- /dev/null
+++ b/minesweeper.py
@@ -0,0 +1,73 @@
+""" Игра Сапер
+    
+https://stepik.org/lesson/701975/step/12?unit=702076
+"""
+
+import random
+
+
+class Cell:
+    def __init__(self, around_mines, mine):
+        self.around_mines, self.mine = around_mines, mine
+        self.fl_open = False
+
+
+class GamePole:
+    around_offsets = (
+        (-1, -1),
+        (-1, 0),
+        (-1, 1),
+        (0, -1),
+        (0, 1),
+        (1, -1),
+        (1, 0),
+        (1, 1),
+    )
+
+    def __init__(self, N, M):
+        self.N, self.M = N, M
+        self.init()
+
+    def init(self):
+        gen = iter(range(1, self.M + 1))
+        flat_pole = [
+            Cell(0, bool(next(gen, 0))) for _ in range(self.N) for _ in range(self.N)
+        ]
+        random.shuffle(flat_pole)
+        self.pole = [flat_pole[i : i + self.N] for i in range(0, self.N**2, self.N)]
+        self.fill_around()
+
+    def fill_around(self):
+        for i in range(self.N):
+            for j in range(self.N):
+                self.pole[i][j].around_mines = self.count_around(i, j)
+
+    def count_around(self, x, y):
+        return sum(
+            (
+                self.pole[x + i][y + j].mine
+                for i, j in GamePole.around_offsets
+                if 0 <= x + i < self.N and 0 <= y + j < self.N
+            )
+        )
+
+    def open(self):
+        for i in range(self.N):
+            for j in range(self.N):
+                self.pole[i][j].fl_open = True
+
+    def show(self):
+        for row in self.pole:
+            print(
+                *map(
+                    lambda x: (
+                        "#" if not x.fl_open else x.around_mines if not x.mine else "*"
+                    ),
+                    row,
+                )
+            )
+
+
+pole_game = GamePole(10, 12)
+pole_game.open()
+pole_game.show()