/
1025.nako3
364 lines (337 loc) · 17.4 KB
/
1025.nako3
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
### [作品情報]
### 掲載URL=https://n3s.nadesi.com/id.php?1025
### タイトル=迷路いろいろ
### 作者=雪乃☆雫(user_id=3)
### ライセンス=CC0
### 説明=迷路を自動生成してみたり解いてみたりします。クラスタリング法とゆうのを試しました。棒倒し法と穴掘り法はだいたい501、502のクジラ飛行机氏のサンプルどうりですが、島や小部屋が出来ないようにちょこっと修正しています。/アドベントカレンダー用に壁伸ばし法の追加。
### 対象バージョン=3.4.1
### URL=https://qiita.com/snowdrops89/items/41c7682e27b07f85e74f
### 種類=wnako
### タグ=アドベントカレンダー2022,迷路
### 更新日時=2022-12-16 23:58:08
###
#自動生成
##クラスタリング法
●(サイズの)クラスタリング法迷路作成
変数 [道,壁]=[0,1]。
変数 [迷路幅,迷路高]=サイズ。
変数 迷路=空配列。
変数 壁データ=空配列。
変数 部屋番号=空配列。
# 最初に全てを壁にする。
行を0から(迷路高-1)まで繰り返す。:
迷路[行]=空配列
列を0から(迷路幅-1)まで繰り返す。:
迷路[行][列]=壁。
変数 部屋数x=迷路幅/2を整数変換。
変数 部屋数y=迷路高/2を整数変換。
行を0から(部屋数y-1)まで繰り返す。:
列を0から(部屋数x-1)まで繰り返す。:
# 部屋を作る
迷路[行*2+1][列*2+1]=道。
# 壊す壁のデータを作る
もし、行=部屋数y-1でなければ、:
壁データに[行,列,行+1,列]を配列追加。# 部屋行,列とその下隣との間の壁。
もし、列=部屋数x-1でなければ、:
壁データに[行,列,行,列+1]を配列追加。# 部屋行,列とその右隣との間の壁。
# 部屋に通し番号を付ける
部屋番号=0から(部屋数x*部屋数y)までの配列連番作成。
# ランダムに壁を壊していく
壁データを配列シャッフル。
壁データを反復。:
変数 [Y1,X1,Y2,X2]=対象。
変数 部屋番1=部屋番号[Y1+X1*部屋数y]。
変数 部屋番2=部屋番号[Y2+X2*部屋数y]。
もし、部屋番1=部屋番2ならば、続ける。# 部屋番号が同じなら壊さない。
もし、X1=X2ならば、:
迷路[Y1*2+2][X1*2+1]=道。# 同じ列なら下の壁を壊す。
違えば、:
迷路[Y1*2+1][X1*2+2]=道。# 同じ行なら右の壁を壊す。
# 部屋繋げる(クラスタリング)
変数 [統合先,統合元]=[部屋番1,部屋番2]。
もし、部屋番1>部屋番2ならば、:
統合先=部屋番2。統合元=部屋番1。
# 部屋番号が大きい方(統合元)を小さい方(統合先)の番号に全て変更する。
部屋番号の要素数回:
もし、部屋番号[回数-1]=統合元ならば、部屋番号[回数-1]=統合先。
迷路で戻る。
ここまで。
##棒倒し法
●(サイズの)棒倒し法迷路作成とは:
変数 [道,壁]=[0,1]。
変数 [迷路幅,迷路高]=サイズ。
変数 迷路=空配列。
# 外周を壁、それ以外を道とする。
行を0から(迷路高-1)まで繰り返す。:
迷路[行]=空配列。
列を0から(迷路幅-1)まで繰り返す。:
# 最初に全部を道にする。
迷路[行][列]=道。
# それから外周を壁にする。
もし、(列=0)または(行=0)または(列=迷路幅-1)または(行=迷路高-1)ならば、:
迷路[行][列]=壁。
# 行も列も偶数なら柱を立てる(壁にする)
行を2から(迷路高-3)まで繰り返す。:
列を2から(迷路幅-3)まで繰り返す。:
もし(列%2=1)または(行%2=1)ならば続ける。
# まず柱を立てる。
迷路[行][列]=壁。
# 上下左右のいずれかに向かって棒を倒す(壁にする)。
上下左右=[[0,-1],[0,1],[-1,0],[1,0]]。
# ただし2段目以降は上には倒さない。
もし、行>2ならば、上下左右の0を配列削除。
方向=上下左右を配列シャッフル。
方向の要素数回:
x,y=方向[回数-1]。
# 既に壁がある方向へは倒さない
もし、迷路[行+y][列+x]=壁でなければ、:
迷路[行+y][列+x]=壁。
抜ける。
迷路で戻る。
##穴掘り法
●(サイズの)穴掘り法迷路作成とは:
変数 [道,壁]=[0,1]。
変数 [迷路幅,迷路高]=サイズ。
変数 迷路=空配列。
# 最初に全部を壁にする。
行を0から(迷路高-1)まで繰り返す。:
迷路[行]=空配列。
列を0から(迷路幅-1)まで繰り返す。:
迷路[行][列]=壁。
# 左上を起点として穴掘りをはじめる
迷路[1][1]=道。# 起点をまず掘る。
[1,1]から迷路の迷路掘削処理。
●(起点から迷路の)迷路掘削処理とは:
変数 [道,壁]=[0,1]。
変数 [列,行]=起点。# 起点は[x,y]の配列。
変数 [迷路幅,迷路高さ]=[迷路[0]の要素数,迷路の要素数]。
変数 上下左右=[[0,-1],[0,1],[-1,0],[1,0]]
変数 方向=上下左右の配列シャッフル。
方向を反復:
RX,RY=対象。
X1=RX+列。Y1=RY+行。
X2=RX*2+列。Y2=RY*2+行。
# 2マス先を調べて壁でなければ中止
もし、(X2≦0)または(X2≧迷路幅-1)ならば続ける。# 迷路の外
もし、(Y2≦0)または(Y2≧迷路高-1)ならば続ける。
もし、迷路[Y2][X2]=道ならば続ける。
# 穴を掘る
迷路[Y1][X1]=道。
迷路[Y2][X2]=道。
# 再帰的に掘削する
[X2,Y2]から迷路の迷路掘削処理。
迷路で戻る。
##壁伸ばし法
●(サイズの)壁伸ばし法迷路作成とは:
変数 [道,壁]=[0,1]。
変数 [迷路幅,迷路高]=サイズ。
変数 迷路=空配列。
変数 壁建設開始候補地=空配列。
# 外周を壁、それ以外を道とする。
行を0から(迷路高-1)まで繰り返す。:
迷路[行]=空配列。
列を0から(迷路幅-1)まで繰り返す。:
# 外周を壁にする。
もし、(列=0)または(行=0)または(列=迷路幅-1)または(行=迷路高-1)ならば、:
迷路[行][列]=壁。
# 残りを全部を道にする。
違えば、:
迷路[行][列]=道。
# 行も列もともに偶数なら壁建設開始候補地として記録する
もし(列%2=0)かつ(行%2=0)ならば、壁建設開始候補地に[列,行]を配列追加。
((壁建設開始候補地の要素数)>0)の間:
壁建設開始候補地を配列シャッフル。
変数 [列,行]=壁建設開始候補地[0]。
壁建設開始候補地から0を配列削除。
もし、迷路[行][列]=道ならば、[列,行]から迷路に壁建設処理。
迷路で戻る。
●(起点から迷路に)壁建設処理とは:
変数 [道,壁,建設中]=[0,1,9]。
変数 [列,行]=起点。# 起点は[x,y]の配列。
変数 [迷路幅,迷路高さ]=[迷路[0]の要素数,迷路の要素数]。
変数 上下左右=[[0,-1],[0,1],[-1,0],[1,0]]
変数 方向=上下左右の配列シャッフル。
方向を反復:
もし、迷路[行][列]=道でなければ、戻る。
変数 [RX,RY]=対象。
変数 [X1,Y1]=[RX+列,RY+行]。
変数 [X2,Y2]=[RX*2+列,RY*2+行]。
迷路[Y2][X2]で条件分岐:
建設中ならば、:
続ける。
道ならば、:
迷路[行][列]=建設中。
迷路[Y1][X1]=建設中。
# 再帰的に建設する
[X2,Y2]から迷路に壁建設処理。
壁ならば、:
迷路[行][列]=建設中。
迷路[Y1][X1]=建設中。
行を0から(迷路高-1)まで繰り返す。:
列を0から(迷路幅-1)まで繰り返す。:
もし、迷路[行][列]=建設中ならば、迷路[行][列]=壁。
行を0から(迷路高-1)まで繰り返す。:
列を0から(迷路幅-1)まで繰り返す。:
もし、迷路[行][列]=建設中ならば、迷路[行][列]=道。
#探索
変数 調査済み迷路=空配列。
●(現地点から出口まで迷路の)迷路深さ優先探索とは:
調査済み迷路=迷路を配列複製。
変数 [今x,今y]=現地点。
変数 [終x,終y]=出口。
変数 仮迷路=迷路を配列複製。
変数 [道,壁,調査済み]=[0,1,9]。# 地形の定義。
変数 上下左右=[[0,-1],[0,1],[-1,0],[1,0]]。
上下左右を反復:
x,y=対象。
次x,次y=[今x+x,今y+y]。
もし、(次x=終x)かつ(次y=終y)ならば、:
仮迷路[今y][今x]=調査済。
仮迷路[次y][次x]=調査済。
調査済み迷路=仮迷路を配列複製。
抜ける。
もし、調査済み迷路[終y][終x]=調査済みならば、抜ける。
もし、仮迷路[次y][次x]=壁ならば、続ける。
もし、仮迷路[次y][次x]>0ならば、続ける。
仮迷路[今y][今x]=調査済。
[次x,次y]から出口まで仮迷路の迷路深さ優先探索。
調査済み迷路で戻る。
●(入口から出口まで迷路の)迷路幅優先探索とは:
調査済み迷路=迷路を配列複製。
変数 [終x,終y]=出口。
変数 [道,壁,調査中]=[0,1,8]。# 地形の定義。
変数 上下左右=[[0,-1],[0,1],[-1,0],[1,0]]。
変数 仮迷路=迷路を配列複製。
変数 調査中迷路=迷路を配列複製。
変数 迷路調査リスト=空配列。
迷路調査リストに入口を配列追加。
((迷路調査リストの配列要素数)>0)の間:
今x,今y=迷路調査リスト[0]。
仮迷路[今y][今x]=調査中。
迷路調査リストの0を配列削除。
上下左右を反復:
x,y=対象。
次x,次y=[今x+x,今y+y]。
もし、(次x=終x)かつ(次y=終y)ならば、:
調査中迷路[次y][次x]=[今x,今y]。
調査中迷路の入口から出口まで最短ルート反映。
それで戻る。
もし、仮迷路[次y][次x]=道でなければ、続ける。
迷路調査リストに[次x,次y]を配列追加。
調査中迷路[次y][次x]=[今x,今y]
●(調査中迷路の入口から出口まで)最短ルート反映:
始x,始y=入口。
今x,今y=出口。
永遠の間:
前x,前y=調査中迷路[今y,今x]。
調査済み迷路[今y,今x]=9。
もし、(今x=始x)かつ(今y=始y)ならば、抜ける。
今x,今y=[前x,前y]。
調査済み迷路で戻る。
#表示
変数 迷路表示色定義=[白色,茶色,青色,紫色,緑色,灰色,オリーブ色,水色,黄色,赤色]。
変数 迷路表示文字定義=[空,空,"S","G",空,空,空,空,空,空]。
●(迷路を道幅で|道幅の)迷路表示とは:
変数 [迷路幅,迷路高さ]=[迷路[0]の要素数,迷路の要素数]。
もし、道幅=空ならば、道幅=8。
描画中キャンバスの「width」に迷路幅*道幅をDOM属性設定。
描画中キャンバスの「height」に迷路高さ*道幅をDOM属性設定。
行を0から(迷路高-1)まで繰り返す:
列を0から(迷路幅-1)まで繰り返す:
地形=迷路[行][列]。
空に線色設定。
ベージュ色に塗り色設定
数を0から9まで繰り返す:
もし、地形=数ならば、迷路表示色定義[数]に塗り色設定。
x=列*道幅。y=行*道幅。
[x,y,道幅,道幅]に四角描画。
黒色に塗り色設定。道幅に描画フォント設定。
[x,y+道幅-2]に迷路表示文字定義[地形]を文字描画。
#以下はテスト
もし、プラグイン名が「メイン」ならば、
変数 初期x=43。
変数 初期y=33。
変数 マス幅=8。
迷路=[初期x,初期y]のクラスタリング法迷路作成。
迷路をマス幅で迷路表示。
迷路種別ラベル=「クラスタリング法」のラベル作成。
改行作成。改行作成。
「迷路サイズ:」のラベル作成。
xエディタ=初期xのエディタ作成。
xエディタの「幅」に「32px」をDOMスタイル設定。
xエディタの「行揃え」に「右」をDOMスタイル設定。
「×」のラベル作成。
yエディタ=初期yのエディタ作成。
yエディタの「幅」に「32px」をDOMスタイル設定。
yエディタの「行揃え」に「右」をDOMスタイル設定。
「(5以上の奇数)」のラベル作成。
改行作成。
「迷路の生成:」のラベル作成。
棒倒しボタン=「棒倒し法」のボタン作成。
穴掘りボタン=「穴掘り法」のボタン作成。
壁伸ばしボタン=「壁伸ばし法」のボタン作成。
クラスタリングボタン=「クラスタリング法」のボタン作成。
改行作成。
「ルート探索:」のラベル作成。
深さ優先探索ボタン=「深さ優先探索」のボタン作成。
幅優先探索ボタン=「幅優先探索」のボタン作成。
「|」のラベル作成。
戻すボタン=「ルート消去」のボタン作成。
改行作成。
「迷路を保存:」のラベル作成。
コピーボタン=「テキストコピー」のボタン作成。
保存ボタン=「画像保存」のボタン作成。
棒倒しボタンをクリックした時には、:
迷路種別ラベルに「棒倒し法」をテキスト設定。
x=xエディタのテキスト取得。
y=yエディタのテキスト取得。
迷路=[x,y]の棒倒し法迷路作成。
迷路をマス幅で迷路表示。
穴掘りボタンをクリックした時には、:
迷路種別ラベルに「穴掘り法」をテキスト設定。
x=xエディタのテキスト取得。
y=yエディタのテキスト取得。
迷路=[x,y]の穴掘り法迷路作成。
迷路をマス幅で迷路表示。
壁伸ばしボタンをクリックした時には、:
迷路種別ラベルに「壁伸ばし法」をテキスト設定。
x=xエディタのテキスト取得。
y=yエディタのテキスト取得。
迷路=[x,y]の壁伸ばし法迷路作成。
迷路をマス幅で迷路表示。
クラスタリングボタンをクリックした時には、:
迷路種別ラベルに「クラスタリング法」をテキスト設定。
x=xエディタのテキスト取得。
y=yエディタのテキスト取得。
迷路=[x,y]のクラスタリング法迷路作成。
迷路をマス幅で迷路表示。
深さ優先探索ボタンをクリックした時には、:
変数 [迷路幅,迷路高さ]=[迷路[0]の要素数,迷路の要素数]。
変数 [入口,出口]=[[1,1],[迷路幅-2,迷路高-2]]。
入口から出口まで迷路の迷路深さ優先探索。
それをマス幅で迷路表示。
幅優先探索ボタンをクリックした時には、:
変数 [迷路幅,迷路高さ]=[迷路[0]の要素数,迷路の要素数]。
変数 [入口,出口]=[[1,1],[迷路幅-2,迷路高-2]]。
入口から出口まで迷路の迷路幅優先探索。
それをマス幅で迷路表示。
戻すボタンをクリックした時には、:
迷路をマス幅で迷路表示。
コピーボタンをクリックした時には、:
CSV=迷路を配列複製。
CSVを表CSV変換して、クリップボード設定。
「クリップボードにコピーしました」を言う。
保存ボタンをクリックした時には、:
描画ダウンロード。
スタイル=「style」のDOM部品作成。
CSS=「.nako3_div {波カッコ}
font-size:1em;
line-height:1.1em;
{波カッコ閉じ}
.nako3_div > button {波カッコ}
font-size:0.9em;
margin:4px;
padding:4px;
{波カッコ閉じ}」
スタイルにCSSをHTML設定。
ここまで。