Randomizare
O modalitate de a face muzica ta mai interesanta este sa adaugi niste numere aleatoare (random). Sonic Pi ofera functii puternice pentru adaugarea unui caracter aleatoriu muzicii, dar inainte de a incepe trebuie sa aflam un lucru socant: in Sonic Pi aleator nu inseamna cu adevarat aleator. Ce naiba mai inseamna si asa? Ei bine, sa vedem.
Repetabilitate
O functie cu adevarat utila este ārrandā, care va intoarce o valoare aleatoare intre doua numere - un min si un max. (ārrandā este prescurtarea de la ranged random - aleator intr-un interval). Sa incercam sa redam o nota aleatoare:
play rrand(50, 95)
O, a cantat o nota aleatoare. A cantat nota ā83.7527ā. O nota draguta aleasa aleator intre 50 si 95. Hei, stai asa, tocmai am prezis nota exacta pe care ai obtinut-o si tu? Ceva nu e in regula aici. Incearca sa mai executi codul o data. Ce? A ales 83.7527
din nou? Asta nu poate fi aleator!
Raspunsul este ca nu este cu adevarat aleator, ci pseudo-aleator. Sonic Pi va genera numere aparent aleatoare intr-un mode repetabil. Acest lucru este util daca vrei sa te asiguri ca muzica pe care ai creat-o pe calculatorul tau va suna identica pe oricare alt calculator - chiar si atunci cand ai introdus un pic de aleatorism in compozitia ta.
Desigur, intr-o piesa oarecare, daca alege mereu āaleatorā valoarea 83.7527
, nu este prea interesant. Totusi, nu se intampla asa. Incearca asta:
live_loop :flibble do
sample :bd_haus, rate: 1
sleep 0.5
end
Da! In fine, suna aleator. In cadrul unei executii a codului, apelurile succesive ale functiilor vor intoarce valori aleatoare. Totusi, la urmatoarea rulare vor fi generate aceleasi numere aleatoare si sunetul va fi exact la fel. Este ca si cand Sonic Pi s-ar intoarce in timp exact in acelasi punct de fiecare data cand apesi butonu Executa (Run). Este Ziua Cartitei pentru compozitia muzicala!
Clopotele bantuite
Un ilustrare draguta a aleatorismului este exemplul cu clopotele bantuite care reda in bucla esantionul :perc_bell
folosind valori aleatoare pentru viteza si pentru durata pauzelor intre sunete:
loop do
sample :perc_bell, rate: (rrand 0.125, 1.5)
sleep rrand(0.2, 2)
end
Intrerupere (cutoff) aleatoare
Un alt exemplu de utilizare a randomizarii este modificarea aleatoare a momentului de cutoff pentru un sintetizator. Un sintetizator potrivit pentru a incerca asta este emulatorul ā:tb303ā:
live_loop :flibble do
sample :bd_haus, rate: 1
sleep 0.5
end
~~~~
~~~~
Valoarea de initializare (seed) a secventei aleatoare
Deci, ce faci faca nu-ti place o anumita secventa de numere aleatoare produsa de Sonic Pi? Ei bine, este posibil sa alegi un alt punct de pornire folosind āuse_random_seedā. Valoarea implicita este 0, deci alege o alta valoare pentru seed si vei avea o secventa aleatoare diferita!
Priveste aceasta bucata de cod:
5.times do
play rrand(50, 100)
sleep 0.5
end
De fiecare data cand vei exexuta acest cod, vei auzi aceeasi secventa de 5 note. Pentru a obtine o secventa diferita schimba valoarea pentru seed:
use_random_seed 40
5.times do
play rrand(50, 100)
sleep 0.5
end
Aceasta va produce o alta secventa de 5 note. Schimband valoarea de initializare si ascultand rezultatul poti gasi ceva ce iti place - iar cand vei transmite altora piesa, ei vor auzi exact acelasi lucru pe care l-ai auzit si tu.
Sa aruncam o privire si asupra altor functii utile pentru numere aleatoare.
choose (alege)
O situatie des intalnita este cea in care vrem sa alegem un element la intamplare dintr-o lista predefinita. De exemplu, vreau sa redau o nota dintre urmatoarele: 60, 65 sau 72. Poti face acest lucru folosind āchooseā care imi permite sa aleg un element dintr-o lista. Mai intai, trebuie sa trec numerele intr-o lista, introducandu-le intre paranteze patrate si separandu-le cu virgule: ā[60, 65, 72]ā. Apoi le transmit functiei āchooseā:
choose([60, 65, 72])
Sa ascultam sunetul obtinut:
loop do
play choose([60, 65, 72])
sleep 1
end
rrand
Am discutat deja despre functia ārrandā, dar sa ne mai oprim putin asupra ei. Functia intoarce un numar aleator dintr-un interval deschis. Asta inseamna ca nu va intoarce niciodata valoarea minima sau pe cea maxima - intotdeauna va fi un numar intre cele doua. Numarul va fi intotdeauna de tipul float (cu virgula mobila) - insemnand ca nu este un numar intreg, ci are si o parte zecimala. Exemple de numere de tip float returnate de ārrand(20, 110)ā:
- 87.5054931640625
- 86.05255126953125
- 61.77825927734375
rrand_i
Vor fi si situatii in care vei dori un numar aleator intreg, nu unul cu virgula. Aici intervine ārrand_iā. Functioneaza la fel ca ārrandā, doar ca poate returna si valorile minima sau maxima (foloseste un interval inchis de valori). Exemple de numere returnate de rrand_i(20, 110)
:
rand
Va returna un numar tip float intre 0 (inclusiv) si valoarea maxima pe care o specifici (exclusiv). Implicit va returna o valoare intre 0 si 1. Este deci util pentru alegerea aleatoare a valorilor pentru āamp:ā:
loop do
play 60, amp: rand
sleep 0.25
end
rand_i
Asemanator cu ārrand_iā pentru ārrandā, exista ārand_iā care va returna o valoare intreaga intre 0 si valoarea maxima pe care i-o transmiti.
dice
Uneori vrei sa simulezi ca dai cu zarul - este un caz particular pentru ārrand_iā in care valoarea minima este mereu 1. Un apel al functiei ādiceā cere sa specifici numarul de fete ale zarului. Un zar standard are 6 fete, deci ādice(6)ā va avea un comportament asemanator - va returna valorile 1, 2, 3, 4, 5 sau 6. Totusi, la fel ca in jocurile fantasy ai putea considera util un zar cu 4 fete, sau cu 12, sau 20 - poate chiar cu 120 de fete!
one_in
In fine, poate doresti sa emulezi obtinerea scorului maxim la un zar, cum ar fi 6 in cazul celui standard. āone_inā returneaza true cu o probabilitate de 1 din numarul de fete ale zarului. Astfel, āone_in(6)ā va returna true cu probabilitate de 1 din 6 si false in celelalte cazuri. True si false (adevarat si fals) sunt valori utile pentru instructiunile āifā (daca) despre care vom vorbi mai tarziu in acest tutorial.
Acum, poti incepe sa zapacesti codul tau cu putin aleatorism!