Die Programmiersprache Ruby (German Edition)
aufrufen:
sequence({:n=>3, :m=>5}) # => [0, 5, 10]
Um diesen Programmierstil besser zu unterstützen, erlaubt Ruby Ihnen, die geschweiften Klammern um das Hash-Literal wegzulassen, wenn es das letzte Argument der Methode ist (oder wenn das einzige nachfolgende Argument ein Blockargument mit dem Präfix
&
ist). Ein Hash ohne geschweifte Klammern wird manchmal als blanker Hash (englisch bare hash ) bezeichnet. Wenn wir einen solchen verwenden, sieht es so aus, als übergäben wir einzelne benannte Argumente, die wir anordnen können, wie wir möchten:
sequence(:m=>3, :n=>5) # => [0, 3, 6, 9, 12]
Genau wie bei anderen Ruby-Methoden können wir auch die Klammern weglassen:
# Ruby 1.9 Hash-Syntax
sequence c:1, m:3, n:5 # => [1, 4, 7, 10, 13]
Wenn Sie die Klammern weglassen, dann müssen Sie die geschweiften Klammern weglassen. Wenn geschweifte Klammern außerhalb runder Klammern auf den Methodennamen folgen, denkt Ruby, dass Sie der Methode einen Block übergeben:
sequence {:m=>3, :n=>5} # Syntaxfehler!
6.4.5 Blockargumente
Wie Sie in „5.3 Iteratoren und Aufzählungsobjekte“ erfahren haben, ist ein Block eine Abfolge von Ruby-Code, der mit einem Methodenaufruf verknüpft ist, und ein Iterator eine Methode, die einen Block erwartet. Ein Block kann auf jeden beliebigen Methodenaufruf folgen, und eine Methode, mit der ein Block verknüpft ist, kann den Code in diesem Block mithilfe der Anweisung
yield
aufrufen. Um Ihre Erinnerung aufzufrischen, ist der folgende Code eine blockorientierte Variante der weiter oben in diesem Kapitel entwickelten Methode
sequence
:
# Eine Sequenz von n Zahlen m*i + c erzeugen und an den Block übergeben
def sequence2(n, m, c)
i = 0
while(i < n) # n-mal wiederholen
yield i*m + c # Nächstes Element der Sequenz an den Block übergeben
i += 1
end
end
# Sie können diese Version der Methode wie folgt verwenden.
sequence2(5, 2, 2) {|x| puts x } # Gibt die Zahlen 2, 4, 6, 8, 10 aus
----
Proc-Objekte explizit übergeben
Wenn Sie Ihr eigenes
Proc
-Objekt erzeugen (wir werden später in diesem Kapitel sehen, wie das geht) und es explizit einer Methode übergeben möchten, können Sie das genauso machen wie bei der Übergabe jeden anderen Wertes – eine
Proc
ist ein Objekt wie jedes andere. In diesem Fall sollten Sie kein Und-Zeichen in der Methodendefinition verwenden:
# Diese Version erwartet ein explizit erzeugtes Proc-Objekt, keinen Block.
def sequence4(n, m, c, b) # Kein Und-Zeichen für Argument b
i = 0
while(i < n)
b.call(i*m + c) # Proc wird explizit aufgerufen
i += 1
end
end
p = Proc.new {|x| puts x } # Explizit ein Proc-Objekt erzeugen
sequence4(5, 2, 2, p) # Und als normales Argument übergeben
----
Eines der Features von Blöcken ist ihre Anonymität. Sie werden nicht im traditionellen Sinn an die Methode übergeben, haben keinen Namen und werden durch ein Schlüsselwort statt durch eine Methode aufgerufen. Wenn Sie explizitere Kontrolle über einen Block wünschen (so dass Sie ihn beispielsweise an eine andere Methode übergeben können), fügen Sie ein letztes Argument zu Ihrer Methode hinzu und stellen Sie dem Argumentnamen ein kaufmännisches Und-Zeichen voran. [ 26 ] Wenn Sie das tun, verweist dieses Argument auf den Block – falls vorhanden -, der an die Methode übergeben wird. Der Wert des Arguments wird zu einem
Proc
-Objekt, und anstatt
yield
zu verwenden, rufen Sie die Methode
call
des
Proc
-Objektes auf:
def sequence3(n, m, c, &b) # Explizites Argument, um Blöcke als Proc zu erhalten
i = 0
while(i < n)
b.call(i*m + c) # Die Proc durch ihre call-Methode aufrufen
i += 1
end
end
# Beachten Sie, dass der Block noch immer außerhalb der Klammern übergeben wird.
sequence3(5, 2, 2) {|x| puts x }
Beachten Sie, dass die Verwendung des Und-Zeichens auf diese Weise nur die Methodendefinition verändert. Der Methodenaufruf bleibt gleich. Das Blockargument wird innerhalb der Klammern der Methodendefinition deklariert, aber der Block selbst wird immer noch außerhalb der Klammern des Methodenaufrufs angegeben.
In diesem Kapitel haben wir bereits zweimal gesagt, dass eine spezielle Art von Parameter zuletzt in der Parameterliste stehen muss. Blockargumente mit Und-Präfix müssen wirklich zuletzt kommen. Da Blöcke in Methodenaufrufen auf irreguläre Weise übergeben werden, sind benannte Blockargumente anders und geraten nicht mit Array- und Hash-Parametern durcheinander, bei denen die eckigen beziehungsweise geschweiften Klammern weggelassen wurden. Die
Weitere Kostenlose Bücher