Ruby/Powrót do prostych przykładów: Różnice pomiędzy wersjami

Usunięta treść Dodana treść
Szymon wro (dyskusja | edycje)
Szymon wro (dyskusja | edycje)
Linia 142:
</pre>
 
W linii 6 w warunku dla pętli ''while'' zakodowanyzakodowana jest "na sztywno" wartość ''true'', co w efekcie daje nam nieskończoną pętlę. Aby więc przerwać wykonywanie pętli umieściliśmy instrukcje ''break'' w liniach 8 i 10. Te dwie instrukcje są również przykładem "modyfikatorów ''if''". ''Modyfikator if'' wykonuje wyrażenie po swojej lewej stronie wtedy i tylko wtedy, gdy określony warunek jest prawdziwy. Konstrukcja ta jest niezwykła, gdyż działa logicznie od prawej do lewej strony, ale jest dostępna, ponieważ wielu ludziom przypomina ona podobne wzorce obecne w mowie potocznej. Dodatkowo jest ona zwięzła - nie potrzebuje wyrażenia ''end'' by wskazać interpretatorowi ile kodu następującego po ''if'' ma być traktowane jako warunek. Modyfikator ''Modyfikator if'' jest wygodnym sposobem używanym w sytuacjach, gdzie wyrażenie i warunek są wystarczająco krótkie by zmieścić się razem w jednej linii skryptu.
 
Rozważ zmiany w interfejsie użytkownika w stosunku do poprzedniego skryptu-zgadywanki. Bieżący interfejs pozwala użytkownikowi zakończyć program poprzez wciśnięcie klawisza Enter (Return) przy pustej linii. Sprawdzamy czy każda linia z wejścia jest pustym łańcuchem, a nie czy nie istnieje.
Note the difference in the user interface compared to the string-guessing script. This one lets the user quit by hitting the Return key on an empty line. We testing for emptiness of the input string, not for its nonexistence.
 
W liniach 7 i 9 mamy "nie-destruktywny" ''chop''; znów, pozbywamy się niechcianego znaku końca linii, który zawsze otrzymujemy od ''gets''. Dodajmy wykrzyknik i będziemy mieli "destruktywny" ''chop''. Jaka to różnica? W Rubim istnieje konwencja dołączania znaków '!' lub '?' do końca nazw pewnych metod. Wykrzyknik (!, czasami wymawiany jako "bang!") oznacza coś potencjalnie destruktywnego, można powiedzieć, coś co może zmienić wartość przylegającego wyrażenia. ''chop!'' zmienia łańcuch bezpośrednio, ale ''chop'' daje ci obciętą kopie bez psucia oryginału. Oto ilustracja tej różnicy.
In lines 7 and 9 we have a "non-destructive" chop; again, we're getting rid of the unwanted newline character we always get from gets. Add the explanation point, and we have a "destructive" chop. What's the difference? In ruby, we conventionally attach '!' or '?' to the end of certain method names. The exclamation point (!, sometimes pronounced aloud as "bang!") indicates something potentially destructive, that is to say, something that can change the value of what it touches. chop! affects a string directly, but chop gives you a chopped copy without damaging the original. Here is an illustration of the difference.
 
<pre>
ruby> s1 = "forth"
"forth"
ruby> s1.chop! # ThisTo changeszmienia s1.
"fort"
ruby> s2 = s1.chop # ThisTo putstworzy azmienioną changedkopię copy inpod s2,
"for"
ruby> s1 # ... withoutbez disturbingwpływu na s1.
"fort"
</pre>
 
Czasem będziesz też widział w użyciu ''chomp'' i ''chomp!''. Te dwa są bardziej selektywne: końcówka łańcucha jest obcinana tylko wtedy, gdy jest znakiem końca linii. Dla przykładu, ''"XYZ".chomp!'' nie robi nic. Jeżeli potrzebujesz jakiegoś triku by zapamiętać różnice, pomyśl o osobie lub zwierzęciu, które smakuje coś nim zdecyduje się to ugryźć (ang. ''chomp'' - "jeść niechlujnie"), a toporze rąbiącym jak popadnie (ang. ''chop'' - odrąbanie).
You'll also sometimes see chomp and chomp! used. These are more selective: the end of a string gets bit off only if it happens to be a newline. So for example, "XYZ".chomp! does nothing. If you need a trick to remember the difference, think of a person or animal tasting something before deciding to take a bite, as opposed to an axe chopping indiscriminately.
 
ThePozostałe otherkonwencje methodnazywania namingmetod conventionpojawiają appearssię inw linesliniach 8 andi 10. AZnak question markzapytania (?, sometimesczasem pronouncedwymawiany aloudw asangielskim jako "huh?") indicatesoznacza ametodę - "predicatepredykat" method,(orzekającą oneo thatczymś), canktóra returnzwraca eitheralbo prawdę (''true'') oralbo fałsz (''false'').
 
Linia 11 tworzy obiekt będący wyrażeniem regularnym z łańcucha podanego przez użytkownika. Cała właściwa praca wykonywana jest wreszcie w linii 12, która używa ''gsub'' do globalnego podstawienia każdego spasowania naszego wyrażenia z samym sobą, ale otoczonego przez znaczniki ansi; również ta sama linia wyświetla wyniki.
Line 11 creates a regular expression object out of the string supplied by the user. The real work is finally done in line 12, which uses gsub to globally substitute each match of that expression with itself, but surrounded by ansi markups; also the same line outputs the results.
 
Mogli byśmy podzielić linię 12 na osobne linie, tak jak tutaj:
We could have broken up line 12 into separate lines like this:
 
<pre>
highlighted = str.gsub(re,"#{st}\\&#{en}")
puts highlighted
</pre>
 
orlub inw "destructivedestruktywnym" stylestylu:
 
<pre>
str.gsub!(re,"#{st}\\&#{en}")
puts str
</pre>
 
Spójrz ponownie na ostatnią część linii 12. ''st'' i ''en'' były zdefiniowane w liniach 1-2 jako sekwencje ANSI które odwracają i przywracają kolor tekstu. W linii 12 są one zawarte w ''#{}'' aby zapewnić, że są one w ten sposób właściwie zinterpretowane (i nie zobaczymy zamiast nich nazw zmiennych). Pomiędzy nimi widzimy ''\\&''. To jest trochę podstępne. Ponieważ podstawiany łańcuch zawarty jest w cudzysłowach (podwójnych), para odwróconych ukośników będzie zinterpretowana jako jeden ukośnik; co ''gsub'' zobaczy właściwie jako ''\&'', i co spowoduje powstanie specjalnego kodu, który z kolei odwoła się do czegokolwiek, co pierwsze spełni wzorzec. Tak więc nowy łańcuch, gdy będzie wyświetlony będzie wyglądał tak jak pierwszy z wyjątkiem tego, że te fragmenty które pasują do wzorca będą wyświetlone w odwróconych kolorach.
Look again at the last part of line 12. st and en were defined in lines 1-2 as the ANSI sequences that make text color-inverted and normal, respectively. In line 12 they are enclosed in #{} to ensure that they are actually interpreted as such (and we do not see the variable names printed instead). Between these we see \\&. This is a little tricky. Since the replacement string is in double quotes, the pair of backslashes will be interpreted as a single backslash; what gsub actually sees will be \&, and that happens to be a special code that refers to whatever matched the pattern in the first place. So the new string, when displayed, looks just like the old one, except that the parts that matched the given pattern are highlighted in inverse video.
<noinclude>
{{ProstaNawigacja|spis=Ruby|poprzart=Ruby/Tablice|poprz=Tablice|nastart=Ruby/Struktury sterujące|nast=Struktury sterujące}}