Bladeren bron

Grundgeruest. Random Maze wird generiert.

ateubert 7 jaren geleden
bovenliggende
commit
cdbb811130
1 gewijzigde bestanden met toevoegingen van 131 en 0 verwijderingen
  1. 131 0
      Vorüberlegung_Maze.py

+ 131 - 0
Vorüberlegung_Maze.py

@@ -0,0 +1,131 @@
1
+#!/usr/bin/env python
2
+# -*- coding: utf-8 -*-
3
+
4
+import random
5
+
6
+
7
+class Maze(object):
8
+
9
+    def __init__(self, width=21, height=21, exit_cell=(21, 1)):
10
+        self.width = width
11
+        self.height = height
12
+        self.exit_cell = exit_cell
13
+        self.create()
14
+
15
+    def create(self):
16
+        self.maze = [[1] * self.width for _ in range(self.height)] 
17
+        self.start_cell = None
18
+        self.steps = None
19
+        self.recursion_depth = None
20
+        self._visited_cells = []
21
+        self._visit_cell(self.exit_cell)
22
+
23
+    def _visit_cell(self, cell, depth=0):
24
+        x, y = cell
25
+        self.maze[y][x] = 0 # Wand entfernen
26
+        self._visited_cells.append(cell)
27
+        neighbors = self._get_neighbors(cell)
28
+        random.shuffle(neighbors)
29
+        for neighbor in neighbors:
30
+            if not neighbor in self._visited_cells:
31
+                self._remove_wall(cell, neighbor)
32
+                self._visit_cell(neighbor, depth+1)
33
+        self._update_start_cell(cell, depth)
34
+
35
+    def _get_neighbors(self, cell):
36
+        """
37
+        Die benachbarten Zellen nehmen.
38
+        Beispiel:
39
+          b sind die benachbarten Zellen von a 
40
+          # # # # # # #     # # # # # # #
41
+          # # # b # # #     # a # b # # #
42
+          # # # # # # #     # # # # # # #
43
+          # b # a # b #     # b # # # # #
44
+          # # # # # # #     # # # # # # #
45
+          # # # b # # #     # # # # # # #
46
+          # # # # # # #     # # # # # # #
47
+        """
48
+        x, y = cell
49
+        neighbors = []
50
+
51
+        # Links
52
+        if x - 2 > 0:
53
+            neighbors.append((x-2, y))
54
+        # Rechts
55
+        if x + 2 < self.width:
56
+            neighbors.append((x+2, y))
57
+        # Hoch
58
+        if y - 2 > 0:
59
+            neighbors.append((x, y-2))
60
+        # Runter
61
+        if y + 2 < self.height:
62
+            neighbors.append((x, y+2))
63
+
64
+        return neighbors
65
+
66
+    def _remove_wall(self, cell, neighbor):
67
+        """
68
+        Entfernen der Wand zwischen zwei Zellen
69
+        Example:
70
+          gegeben sind die Zellen a und b
71
+          Die Wand dazwischen ist w
72
+          # # # # #
73
+          # # # # #
74
+          # a w b #
75
+          # # # # #
76
+          # # # # #
77
+        """
78
+        x0, y0 = cell
79
+        x1, y1 = neighbor
80
+        # Vertikal
81
+        if x0 == x1:
82
+            x = x0
83
+            y = (y0 + y1) / 2
84
+        # Horizontal
85
+        if y0 == y1:
86
+            x = (x0 + x1) / 2
87
+            y = y0
88
+        self.maze[y][x] = 0 # Wand entfernen
89
+
90
+    def _update_start_cell(self, cell, depth):
91
+        if depth > self.recursion_depth:
92
+            self.recursion_depth = depth
93
+            self.start_cell = cell
94
+            self.steps = depth * 2 # Wand + Zelle
95
+
96
+    def show(self, verbose=False):
97
+        MAP = {0: ' ', # Durchgang
98
+               1: '#', # Wand
99
+               2: 'B', # Ausgang
100
+               3: 'A', # Start
101
+              }
102
+        x0, y0 = self.exit_cell
103
+        self.maze[y0][x0] = 2
104
+        x1, y1 = self.start_cell
105
+        self.maze[y1][x1] = 3
106
+        for row in self.maze:
107
+            print ' '.join([MAP[col] for col in row])
108
+        if verbose:
109
+            print "Schritte von A nach B:", self.steps
110
+
111
+
112
+if __name__ == '__main__':
113
+
114
+    from optparse import OptionParser
115
+    parser = OptionParser(description="Maze random generator")
116
+    parser.add_option('-W', '--width', type=int, default=21,
117
+                      help="maze width (muss ungerade sein)")
118
+    parser.add_option('-H', '--height', type=int, default=21,
119
+                      help="maze height (muss ungerade sein)")
120
+    parser.add_option('-v', '--verbose', action='store_true',
121
+                      help="zeigt Schritte von Start bis Ziel")
122
+    args, _ = parser.parse_args()
123
+
124
+    for arg in ('width', 'height'):
125
+        if getattr(args, arg) % 2 == 0:
126
+            setattr(args, arg, getattr(args, arg) + 1)
127
+            print "Warnung: %s muss ungerade sein, benutze %d stattdessen" % (arg, getattr(args, arg))
128
+
129
+    exit_cell = (args.width-2, args.height-2)
130
+    maze = Maze(args.width, args.height, exit_cell)
131
+    maze.show(args.verbose)