2016-12-07 4 views
0

私は、引数として配列を取り、偶数のインデックス番号と偶数の両方の値を持つ引数の数値の配列を返します。私は理由は分かりませんが、5行目に "undefined method%"というエラーが表示されています。誰かがこの問題をどのように修正できるか説明できますか?ルビのモジュラスメソッドのエラー

def odd_value_and_position(array) 
    newArray=[] #create new array 
    i=0 #i=0 
    while i <= array.length #loop while 
     newArray.push(array[i]) if array[i] % 2 != 0 
     i = i + 2 
    end 

    return newArray 
end 

puts odd_value_and_position([0,1,2,3,4,5]) 
+1

これは、I = 6ループが実行され、 '配列は、[6]' 'nil'使用は'私は engineersmnky

+0

共通array.length'でいるときので、常にこれらの注意する必要があります! – Anthony

+1

.evenを使用する必要がありますか?メソッドを使用する代わりに – Gregory

答えて

1

iarray.lengthに等しい、array[i]はゼロです。

nil % 2とは何ですか?これは未定義です。

def odd_value_and_position(array) 
    newArray=[] #create new array 
    i=0 #i=0 
    while i < array.length #loop while 
     newArray.push(array[i]) if array[i] % 2 != 0 
     i = i + 2 
    end 

    return newArray 
end 

puts odd_value_and_position([0,1,2,3,4,5]) #=> [] 
puts odd_value_and_position([1,2,3,4,5]) #=> [1,3,5] 

Ruby Arrayの最初の要素がインデックスとして0なので、期待した結果が得られないのではないかと思います。コードの例を参照してください。

よりRubyish例は次のようになります。これを行うには

def odd_value_and_position(array) 
    array.select.with_index(1){|x,i| x.odd? && i.odd?} 
end 

puts odd_value_and_position([1,2,3,4,5]) #=> [1,3,5] 
+2

質問は* "偶数のインデックス番号と偶数の値" *であるので、質問とメソッドは誤解を招きますが、メソッド名は反対の(あなたが投稿した)ことを示しますが、メソッド本体は奇数のインデックスも検索しています。私は今何が起こっているのか分かりませんが、合理的な説明のために+1します。 – engineersmnky

+1

メソッドは 'even_or_odd_or_something'と呼ばれるべきです –

4

別の方法:

def evens arr 
    arr.select.with_index { |e,i| e.even? && i.even? } 
end 

evens [0,1,2,3,4,5] #=> [0,2,4] 
+0

ニース。いいえ、OPが本当に望んでいたものを見てみましょう。最初のインデックスは奇数か偶数か? :) –

1

私は右の質問を理解していれば、私のようなものでいいと思う:

def some_method_name(array) 
    array.select.with_index { |*ij| 
    ij.all?(&:even?) 
    } 
end 

puts some_method_name([0, 1, 2, 3, 4, 5, 10, 13, 21, 22, 30]) 

# >> 0 
# >> 2 
# >> 4 
# >> 10 
# >> 30 
ここで

は、それがやっているものです:

def some_method_name(array) 
    array.select.with_index { |*ij| 
    ij    # => [0, 0], [1, 1], [2, 2], [3, 3], [4, 4], [5, 5], [10, 6], [13, 7], [21, 8], [22, 9], [30, 10] 
    ij.all?(&:even?) # => true, false, true, false, true, false, true, false, false, false, true 
    } 
end 

puts some_method_name([0, 1, 2, 3, 4, 5, 10, 13, 21, 22, 30]) 

# >> 0 
# >> 2 
# >> 4 
# >> 10 
# >> 30 

元のコードにはいくつか問題があります。

whileループを使用すると、off-by-oneエラー、またはトリガしないループ、または決して終了しないループの問題が発生しやすくなります。

はRubyでそれに対処するために、我々は、次に、その上にロジックをベースアレイ上にループにeachmapselectreject又は同様のイテレータを使用し、各要素を処理します。

array.select各要素を見て、ブロック内の論理を適用すること、「truthy」結果を探しています。 with_indexは、反復のインデックスをブロックに渡された第2の値として追加します。 *idは、2つの値を配列に渡すので、all?とそのeven?テストを簡単に適用できます。 even?戻りtrueall?両方その後にトリガする場合、配列の要素を返すためにselectに信号true再度を返します。

+0

この質問に対して3つの同等の回答。しかし、正確に何が問題なのですか?それは疑問です:D –

+1

あなたのメソッド名はコードに適合しません。 –

+0

ちょっと気味悪い私たちは? –