Die Programmiersprache Ruby (German Edition)
1.1 Eine Tour durch Ruby
Dieser Abschnitt ist eine geführte, aber nicht geradlinige Tour durch einige der interessantesten Merkmale von Ruby. Alles, was hier besprochen wird, wird später in diesem Buch ausführlich dokumentiert, aber dieser erste Überblick liefert Ihnen einen Vorgeschmack der Sprache.
1.1.1 Ruby ist objektorientiert
Wir beginnen mit der Tatsache, dass Ruby eine vollständig objektorientierte Sprache ist. Jeder Wert ist ein Objekt, selbst einfache numerische Literale sowie die Werte
true
,
false
und
nil
(
nil
ist ein spezieller Wert, der die Abwesenheit eines konkreten Wertes anzeigt; es handelt sich um die Ruby-Version von
null
). Hier rufen wir eine Methode namens
class
für diese Werte auf. Kommentare beginnen in Ruby mit
#
, und die Pfeile(
=>)
in den Kommentaren zeigen den Wert an, den der kommentierte Code zurückgibt (diese Konvention wird im gesamten Buch verwendet):
1.class # => Fixnum: die Zahl 1 ist eine Fixnum
0.0.class # => Float: Fließkommazahlen gehören zur Klasse Float
true.class # => TrueClass: true ist die Singleton-Instanz von TrueClass
false.class # => FalseClass
nil.class # => NilClasss
In vielen Sprachen benötigen Funktions- und Methodenaufrufe Klammern, aber im obigen Code gibt es keine Klammern. In Ruby sind Klammern normalerweise optional und werden häufig weggelassen, besonders dann, wenn die aufgerufene Methode keine Argumente erwartet. Die Tatsache, dass die Klammern hier in den Methodenaufrufen weggelassen werden, lässt diese wie Referenzen auf benannte Felder oder Variaben des Objekts aussehen. Das ist Absicht, aber in Wirklichkeit ist Ruby sehr streng, was die Kapselung von Objekten angeht; von außerhalb eines Objekts ist kein Zugriff auf seinen internen Zustand möglich. Jeder solche Zugriff muss durch eine Akzessormethode wie die oben gezeigte Methode
class
vermittelt werden.
1.1.2 Blöcke und Iteratoren
Die Tatsache, dass wir Methoden von Integer-Werten aufrufen können, ist nicht etwa ein esoterischer Aspekt von Ruby, sondern etwas, das Ruby-Programmierer sogar recht häufig tun:
3.times { print "Ruby! " } # Gibt "Ruby! Ruby! Ruby! " aus
1.upto(9) {|x| print x } # Gibt "123456789" aus
times
und
upto
sind Methoden, die durch Integer-Objekte implementiert werden. Sie gehören zu einer besonderen Art von Methoden namens Iteratoren , die sich wie Schleifen verhalten. Der Code in geschweiften Klammern – Block genannt – ist mit dem Methodenaufruf verknüpft und bildet den Rumpf der Schleife. Die Verwendung von Iteratoren und Blöcken ist ein weiteres bemerkenswertes Feature von Ruby; die Sprache unterstützt zwar auch gewöhnliche
while
-Schleifen, aber es ist üblicher, Schleifen mithilfe von Konstrukten auszuführen, die eigentlich Methodenaufrufe sind.
Integer sind nicht die einzigen Werte mit Iteratormethoden. Arrays (und ähnliche »Aufzählungs«-Objekte) definieren einen Iterator namens
each
, der den zugehörigen Block einmal für jedes Element des Arrays aufruft. Jeder Aufruf des Blocks erhält ein einzelnes Element aus dem Array:
a = [3, 2, 1] # Dies ist ein Array-Literal
a[3] = a[2] - 1 # Eckige Klammern zum Abfragen und Setzen von Array-Elementen
a.each do |elt| # each ist ein Iterator. Der Block hat den Parameter elt
print elt+1 # Gibt "4321" aus
end # Dieser Block wurde durch do/end statt {} begrenzt
Diverse weitere nützliche Iteratoren sind als Erweiterungen von
each
definiert:
a = [1,2,3,4] # Mit einem Array beginnen
b = a.map {|x| x*x } # Quadrate der Elemente: b ist [1,4,9,16]
c = a.select {|x| x%2==0 } # Gerade Elemente auswählen: c ist [2,4]
a.inject do |sum,x| # Die Summe der Elemente berechnen => 10
sum + x
end
Hashes sind wie Arrays eine grundlegende Datenstruktur in Ruby. Wie ihr Name vermuten lässt, basieren sie auf der Hashtable-Datenstruktur und dienen dazu, beliebigen Schlüsselobjekten Wertobjekte zuzuordnen. (Anders ausgedrückt können wir sagen, dass ein Hash beliebige Wertobjekte mit Schlüsselobjekten verknüpft.) Hashes verwenden wie Arrays eckige Klammern, um Werte innerhalb des Hashes abzufragen und zu setzen. Statt eines Integer-Index erwarten sie Schlüsselobjekte innerhalb der eckigen Klammern. Wie die Klasse
Array
definiert auch die Klasse
Hash
eine
each
-Iteratormethode. Diese Methode ruft den zugehörigen Codeblock einmal für jedes Schlüssel/Wert-Paar im Hash auf und (darin unterscheidet sie sich von
Array
) liefert sowohl den Schlüssel als auch den Wert als Parameter an den Block:
h = { # Ein Hash,
Weitere Kostenlose Bücher