Ciekawym przypadkiem standardowych list są pierścienie. Jeśli znasz się trochę na programowaniu, to mogło się zdarzyć, że miałeś do czynienia z buforami cyklicznymi lub tablicami cyklicznymi. Tutaj przyjrzymy się tylko pierścieniowi - jest krótki i prosty.
W poprzedniej sekcji dotyczącej list widzieliśmy, w jaki sposób możemy wyciągać z nich elementy, korzystając z mechanizmu indeksowania:
puts [52, 55, 59][1]
A co się stanie, jeśli chciałbyś pozycję spod indeksu 100
? Dobrze, więc na pozycji 100 nie ma żadnego elementu, jako że lista posiada w sobie tylko trzy elementy. Sonic Pi zwróci więc wartość nil
, co oznacza nic.
Jednakże biorąc pod uwagę, że masz licznik taki, jak aktualne uderzenie, które nieustannie rośnie. Spróbujmy go utworzyć oraz do tego listę:
counter = 0
notes = [52, 55, 59]
Możemy teraz użyć naszego licznika, aby dostać się do nuty znajdującej się w naszej liście:
puts notes[counter]
Super, otrzymaliśmy 52
! Teraz, spróbujmy zwiększyć nasz licznik i dostać się do kolejnej nuty:
counter = (inc counter)
puts notes[counter]
Wspaniale, teraz otrzymaliśmy 55
i jeśli dokonamy tego jeszcze raz, otrzymamy liczbę 59
. Jednakże jeśli to zrobimy, wyskoczymy poza liczby znajdujące się w naszej liście i otrzymamy nil
. A co, jeśli chcieliśmy tylko stworzyć pętlę, wrócić do początku i zacząć na samym początku listy od nowa? Do tego właśnie służą pierścienie.
Możemy tworzyć pierścienie na dwa sposoby. Albo użyjemy funkcji ring
, podając elementy dla danego pierścienia jako parametry:
(ring 52, 55, 59)
Albo możemy wziąć normalną listę i przekształcić ją w pierścień poprzez wysłanie do niej wiadomości .ring
:
[52, 55, 59].ring
Gdy już masz pierścień, możesz go używać dokładnie w ten sam sposób, w jaki używasz normalnej listy, z tym jednym wyjątkiem, że masz możliwość korzystania z indeksów ujemnych oraz takich, które są większe niż ilość elementów w danym pierścieniu, a będą one powtarzać się cyklicznie i zawsze będą wskazywać na jeden z elementów pierścienia:
(ring 52, 55, 59)[0] #=> 52
(ring 52, 55, 59)[1] #=> 55
(ring 52, 55, 59)[2] #=> 59
(ring 52, 55, 59)[3] #=> 52
(ring 52, 55, 59)[-1] #=> 59
Przyjmijmy, że używamy zmiennej do reprezentacji aktualnego numeru uderzenia. Możemy użyć jej jako indeksu w naszym pierścieniu, aby wydobywać kolejne nuty do zagrania, czasy zanikania albo cokolwiek innego przydatnego, co załadowaliśmy do naszego pierścienia, niezależnie od numeru uderzenia (beat), przy którym aktualnie się znajdujemy.
Przydatną rzeczą jest wiedza o tym, że listy zwracane przez skale scale
oraz akordy chord
są również pierścieniami i pozwalają Ci na dostęp do nich z wykorzystaniem bezwzględnych indeksów.
Oprócz funkcji ring
istnieje również kilka innych funkcji, które pozwalają nam na tworzenie pierścieni.
range
wymaga, abyś określił punkt startu, końca oraz rozmiar kroku.bools
pozwala Ci na użycie wartości 1
i 0
, aby treściwie reprezentować wartości logiczne (boolean).knit
pozwala Ci na spajanie sekwencji powtarzalnych wartości.spread
tworzy pierścień wartości logicznych o rozkładzie euklidesowym.Przyjrzyj się poszczególnym dokumentacjom dla uzyskania większej ilości informacji.