2016-05-05 4 views
1

Rubyで基本的なバブルソートアルゴリズムを問題なく構築しました。コードは次のようになります:Ruby無限ループのバブルソートアルゴリズム

def bubble_sort(arr) 
swapped=true 
while swapped 
    swapped=false 
    for j in 0..arr.length-2 do 
     if arr[j]>arr[j+1] 
     arr[j], arr[j+1] = arr[j+1], arr[j] 
     swapped=true 
     end 
    end 
end 
arr 
end 

私は同じ方法を実装しようとしていますが、コードブロックを受け入れる機能を実装しようとしています。コードブロックの部分は正常に動作しますが、コードブロックが提供されていない場合、メソッドは上記と同じように見えますが、何らかの理由で無限ループに入ります:

"そうでない場合は、条件をチェックし、必要に応じてポジションを入れ替え、歩留まり部分をスキップします。私はrdebuggerでステップバイステップのデバッグを試みたが、理由を見つけることができなかった。

def bubble_sort_by(arr) 
    swapped = true 
    while swapped 
    swapped=false 
    for i in 0..arr.length-2 do 
     unless block_given? 
     arr[i], arr[i+1] = arr[i+1], arr[i] if arr[i] < arr[i+1] 
     swapped=true 
     end #unless 
    if block_given? 
     if yield(arr[i], arr[i+1])>0 
     arr[i], arr[i+1] = arr[i+1], arr[i] 
     swapped=true 
     end #if yield 
    end #if block_given? 
    end #for 
    end #while 
puts arr 
return arr 
end 

答えて

1

クイック答えは:

arr[i], arr[i+1] = arr[i+1], arr[i] if arr[i] < arr[i+1] 
swapped=true 

に置き換えてください:何が​​起こっていることは、あなたが要素がスワップされていない場合でも、trueswappedを設定し、常にをだある

if arr[i] < arr[i+1] 
    arr[i], arr[i+1] = arr[i+1], arr[i] 
    swapped=true 
end 

。だからあなたは無限ループに陥るでしょう。

そして今、コードのクリーンアップのビットのために...まず、むしろ書き込みより:

if(foo) 
    # ... 
end 
unless(foo) 
    # ... 
end 

のは、それif/else声明作ってみましょう:あなたが再可能性が

def bubble_sort_by(arr) 
    swapped = true 

    while swapped 
    swapped=false 
    for i in 0..arr.length-2 do 
     if block_given? 
     if yield(arr[i], arr[i+1])>0 
      arr[i], arr[i+1] = arr[i+1], arr[i] 
      swapped=true 
     end 
     else 
     if arr[i] < arr[i+1] 
      arr[i], arr[i+1] = arr[i+1], arr[i] 
      swapped=true 
     end 
     end 
    end #for 
    end #while 

    return arr 
end 

@Aetherusが示唆しているようにループをwhileというループから削除するようにしましたが、実際のバグが修正されたことに感謝しました。

+0

あなたの時間をありがとうTom、私の質問に答えるだけでなく、私のような初心者のための非常に貴重なヒントを提供しました。あなたの幸せを祈ります! – devwanderer

0

あなたのコードはblock_given?あまりにも多くを持っている、とあなたはブール変数swappedを必要とする理由私は理解していません。

バブルソートは私のバージョンです(配列を所定の場所に並べ替えるため、名前にバングを付けました)。

def bubble_sort!(arr, &compare) 
    # Provide a default comparison algorithm 
    compare ||= proc {|a, b| a <=> b} 

    (1...arr.length).each do |i| 
    (0...i).each do |j| 
     arr[i], arr[j] = arr[j], arr[i] if compare.call(arr[i], arr[j]) < 0 
    end 
    end 

    arr 
end 
+0

洗練されたレスポンスのおかげで、私はこれまでのベストプラクティスにはほど遠く、すべてのことで快適になるためにはもっと勉強する必要があることを認識しています。私はあなたのフィードバックに感謝します。 – devwanderer