2017-05-19 11 views
0

Ich arbeite an einer manuellen Rotationsfunktion in Ruby. Aber ich habe festgestellt, dass in einigen Beispielen negative Offsets bestanden. Ist es möglich, von einer negativen Zahl bis zu einem bestimmten Index zu iterieren (nicht sicher, was dieser Index wäre)?Wie behandelt man negative Iterator in Funktion übergeben?

def my_rotate(arr, offset=1) 
    if offset < 1 
    for i in offset 
     arr.push(arr.shift) 
    end 
    else 
    for i in 1..offset 
     arr.push(arr.shift) 
    end 
    end 
    arr 
end 
+0

Warum nicht diesen funktionalen/prozeduralen Ansatz ablegen und die eingebauten Methoden auf Array verwenden? Z.B. 'arr.rotate (2)' – coreyward

+1

Auch die [Dokumentation für rotieren] (https://ruby-doc.org/core-2.4.0/Array.html#method-irotate) hat die Quelle für die Methode , so können Sie ziemlich einfach den Algorithmus/Ansatz sehen. – coreyward

Antwort

2

Nach mit Ihrem Code können Sie verwenden Array#pop und Array#unshift (das sind die Gegensätze von Array#push und Array#shift):

def my_rotate(array, offset=1) 
    arr = array.dup 

    if offset < 1 
    for i in 1..offset.abs 
     arr.unshift(arr.pop) 
    end 
    else 
    for i in 1..offset 
     arr.push(arr.shift) 
    end 
    end 
    arr 
end 

Beachten Sie die Änderung in Zeile 5 for i in 1..offset.abs Schleife in der Lage sein das Array und die Hinzufügung von Zeile 2 arr = array.dup, um zu verhindern, dass das ursprüngliche Array mutiert wird.

+0

Danke, um es zu testen. – KingKrypton

1

Das ist so ziemlich wie Array#rotate tut es (in C).

-Code

class Array 
    def my_rotate(n=1) 
    n %= self.size 
    self[n..-1].concat(self[0,n]) 
    end 
end 

Beispiele

arr = [1,2,3,4] 

arr.my_rotate 0 #=> [1,2,3,4] 

arr.my_rotate  #=> [2, 3, 4, 1] 
arr.my_rotate 1 #=> [2, 3, 4, 1] 
arr.my_rotate 4 #=> [1, 2, 3, 4] 
arr.my_rotate 5 #=> [2, 3, 4, 1] 
arr.my_rotate 9 #=> [2, 3, 4, 1] 

arr.my_rotate -1 #=> [4, 1, 2, 3] 
arr.my_rotate -4 #=> [1, 2, 3, 4] 
arr.my_rotate -5 #=> [4, 1, 2, 3] 
arr.my_rotate -9 #=> [4, 1, 2, 3] 

Erklärung

Die Linie

n %= self.size 

die Parser erweitert Ruby zu

n = n % self.size 

wandelt n in eine ganze Zahl zwischen 0 und self.size - 1. Dies gilt auch für positive und negative Werte von n.

Die Linie

self[n..-1].concat(self[0,n]) 

anhängt, die ersten Elemente der narr zu einer Anordnung der letzten Elemente der arr.size - narr besteht. Das resultierende Array wird dann von der Methode zurückgegeben.

Wenn Sie diese Methode nicht zu der Klasse Array hinzufügen möchten, können Sie sie natürlich def my_rotate(arr, n)... definieren.

+0

Danke für die Erklärung. Schätze es wirklich. – KingKrypton

Verwandte Themen