質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.49%
Ruby

Rubyはプログラミング言語のひとつで、オープンソース、オブジェクト指向のプログラミング開発に対応しています。

Q&A

解決済

1回答

1600閲覧

ATC001-A 深さ優先探索 REとWA発生したけど原因がわからない

amatsukixprog

総合スコア17

Ruby

Rubyはプログラミング言語のひとつで、オープンソース、オブジェクト指向のプログラミング開発に対応しています。

0グッド

0クリップ

投稿2019/05/19 02:36

編集2019/05/19 09:38

前提・実現したいこと

AtCoderのATC001-A問題です。
問題文

上記のページを参考に、コードを作成したのですが提出した際にREとWAが発生します。
REが発生した時はエラーメッセージもなく、WAが発生した時はどのような入力がされたときなのかわかりません。
エラーメッセージの確認方法などの、原因を特定する方法があれば教えていただきたいです。
また、ソースコードにおかしい点があれば指摘して頂けますと幸いです。

該当のソースコード

Ruby

1$H,$W=gets.chomp.split.map(&:to_i) 2$map=$H.times.map { gets.chomp.chars } 3$reached=Array.new($H){Array.new($W,0)} 4$a=false 5 6# 探索するメソッド 7def t(y,x) 8 return if y<0 || y>=$H # 枠外 9 return if x<0 || x>=$W # 枠外 10 return if $map[y][x]=='#' #壁 11 return if $reached[y][x]==1 # 来た時があったら 12 $a=true if $map[y][x]=='g' 13 14 $reached[y][x]=1 15 16 t(y-1,x)#上 17 t(y,x+1)#右 18 t(y+1,x)#下 19 t(y,x-1)#左 20end 21 22#startの座標取得 23x = -1 24y = -1 25catch :out do #ループから抜け出すための処理 26 $H.times do |j| 27 $W.times do |i| 28 if $map[i][j]=='s' 29 x=j 30 y=i 31 throw :out 32 end 33 end 34 end 35end 36 37t(y,x) 38puts $a ? 'Yes' : 'No' 39

試したこと

・問題文に掲載されている入力例からは正しく出力されていました。

・テストケースが保存されている場所は見つけましたが、今回の問題は置いていないようでした。
テストケース

ご指摘いただき、修正したコード

Ruby

1$H,$W=gets.chomp.split.map(&:to_i) 2$map=$H.times.map { gets.chomp.chars } 3$reached=Array.new($H){Array.new($W,0)} 4$a=false 5 6def t(y,x) 7 return if y<0 || y>=$H 8 return if x<0 || x>=$W 9 return if $map[y][x]=='#' 10 return if $reached[y][x]==1 11 $a=true if $map[y][x]=='g' 12 13 $reached[y][x]=1 14 15 t(y-1,x) 16 t(y,x+1) 17 t(y+1,x) 18 t(y,x-1) 19end 20 21y,x = $map.each_with_index{|line, ix| 22 found = line.index('s') 23 break [ix,found] if found 24} 25 26t(y,x) 27puts $a ? 'Yes' : 'No'

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

ruby

1catch :out do #ループから抜け出すための処理 2 $H.times do |j| 3 $W.times do |i| 4 if $map[i][j]=='s' 5 x=j 6 y=i 7 throw :out 8 end 9 end 10 end 11end

ここが間違いですね。
縦横逆です。

ちなみに、私ならば

ruby

1y,x = $map.each_with_index{|line, ix| 2 found = line.index('s') 3 break [ix,found] if found 4 }

投稿2019/05/19 06:37

asm

総合スコア15147

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

amatsukixprog

2019/05/19 09:31

間違いの箇所を見つけていただき、ありがとうございます! 配列から該当するキーの受け取る方法や、複数の値を受け取る方法など勉強になりました。 asmさんのコードの方がとてもわかりやすいと思います! こちらの部分を修正しWAはなくなりましたが、 REはまだ起きているようでした。 他におかしい箇所はありますでしょうか。。。
asm

2019/05/19 10:20

最大サイズ500*500なので 深さ優先探索だとスタックが足りない可能性がある気もするので H=500 W=500 のテストケースを作って試してみてください
amatsukixprog

2019/05/19 11:23

H=500 W=500 でテストいたしました。 stack level too deepとエラーが出ていましたので、 asmさんの想定どおり、スタックが足りていないようです! ご指摘いただき、ありがとうございました。 今回のようなサイズが大きい場合は、 深さ優先探索では不可能ということでしょうか。
asm

2019/05/19 11:45

再帰を用いた深さ優先探索の場合はそうですね。 言語や環境によりどこまで再帰できるかが決まりますが 特にRubyの場合は制限がきつめなように思います
amatsukixprog

2019/05/19 12:48

Rubyではこういう問題で、少し不利になるのですね。。。 また別の解法を考えてみることにします! 丁寧に教えていただき、ありがとうございました。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.49%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問