Jesper Juellund Jensen      

Prolog-program til rytmemodeller

Simpel melodirytme


De specifikke regler for simpel melodirytme er:

f1) For en vilkårlig tone skal der gælde, at den ikke er en synkope

f2) En tone X er ikke en synkope, hvis der for alle positioner P mellem XPosition og XPosition+XLængde gælder, at P ikke er mere metrisk betonet end XPosition

 

g) For ethvert par af toner X, Y skal det gælde: XTeksttryk>YTeksttryk ⇒ XPosition er mere metrisk betonet end YPosition

 

h) For enhver tone X skal der gælde: XLængde ∈ {1·B, 2·B, 3·B}, hvor B er det laveste metriske lag

Disse regler vil nu – en efter en – blive omformet til Prolog.


1. Synkoper (regel f1-2)

Regel f1-2 handler om, at der ikke må være synkoper i en rytme.

En tone er en ikke-synkope

Regel f2 definerer, hvad det vil sige, at en tone ikke er en synkope:

f2) En tone X er ikke en synkope, hvis der for alle positioner P mellem XPosition og XPosition+XLængde gælder, at P ikke er mere metrisk betonet end XPosition

Endnu en gang kan reglen med fordel opdeles i to regler i en rekursiv definition:

f2+) Hvis en tone X ikke er en synkope, så er en tone, der er B længere heller ikke en synkope, hvis positionen XPosition+XLængde ikke er mere metrisk betonet end XPosition
– hvor B er det laveste metriske lag

f2°) En tone X er ikke en synkope, hvis dens længde er B
– hvor B er det laveste metriske lag

Man kan her erindre sig, at det laveste metriske lag i den valgte repræsentation er 1.

Af hensyn til den procedurale mening er reglerne dog omformet en smule ved oversættelsen til Prolog:

ikkeSynkope( tone(_,Position,LaengdePlus1) , Metrum ) :-
    laengde(LaengdePlus1),
    Laengde is LaengdePlus1-1,
    ikkeSynkope( tone(_, Position, Laengde), Metrum ),
    SidstePosition is Position+Laengde,
    erMereEllerLigesaaBetonet(Position, SidstePosition, Metrum).

ikkeSynkope( tone(_,_,1) , _).

Rytme uden synkoper

Regel f1 definerer, hvad det vil sige, at en hel rytme er uden synkoper:

f1) For en vilkårlig tone skal der gælde, at den ikke er en synkope

Igen kan reglen omformes til en rekursiv definition:

f1+) Hvis en rytme,R, ikke har synkoper, og en tone, T, ikke er en synkope, er der ikke synkoper i rytmen af T og R

f1°) En tom rytme, [], har ingen synkoper

Oversat til Prolog bliver det:

udenSynkoper([T|R], Metrum) :-
    ikkeSynkope(T, Metrum),
    udenSynkoper(R, Metrum).

udenSynkoper([],_).


2. Overensstemmelse mellem teksttryk og metrisk betoning (regel g)

Nu mangler blot definitionen af den sidste regel, nemlig:

g) For ethvert par af toner X, Y skal det gælde: XTeksttryk>YTeksttryk ⇒ XPosition er mere metrisk betonet end YPosition

Da ⇒ ikke er indbygget i Prolog, må reglen omformuleres, hvor det udnyttes, at A⇒B kan udtrykkes ¬A∨B. Desværre er der visse problemer med den procedurale mening af logiske udtryk, hvor der er flere muligheder for, at noget kan være opfyldt (man riskerer at få en masse ens løsninger), og ¬A∨B kan jo være opfyldt, både hvis ¬A, og hvis B. Udtrykket formuleres derfor i stedet som (¬A)∨(A∧B), der har samme logiske værdi som ¬A∨B (og dermed som A⇒B), da så kun en af de to dele ¬A og A∧B kan være opfyldt. Regel g kommer derfor til at lyde:

g) For ethvert par af toner X, Y skal mindst en af følgende betingelser være opfyldt:
    • XTeksttryk≤YTeksttryk
    • XTeksttryk>YTeksttryk og XPosition er mere betonet end YPosition

For at lette implementationen i Prolog opdeles reglen i to:

g1) Der er „overensstemmelse mellem teksttryk og metrisk betoning“ i et par af toner X og Y, hvis mindst en af følgende betingelser være opfyldt:
    • XTeksttryk≤YTeksttryk
    • XTeksttryk>YTeksttryk og XPosition er mere betonet end YPosition

 

g2) For ethvert par af toner skal der være overensstemmelse mellem teksttryk og metrisk betoning

Disse to regler giver således anledning til to Prolog-relationer:

Overensstemmelse mellem teksttryk og metrisk betoning for et tonepar

Denne relation handler om overensstemmelse mellem teksttryk og metrisk betoning i et par af toner i en betoningsstruktur (regel g1). Hver af de to betingelser giver anledning til en Prolog-regel:

overensstemmelseMellemTrykOgBetoning(tone(Xteksttryk,_,_), tone(Yteksttryk,_,_), _) :-
    Xteksttryk=<Yteksttryk.

Der er overensstemmelse mellem teksttryk og metrisk betoning for et tonepar, hvis den første tones teksttryk, Xteksttryk, er mindre end eller lig med den anden tones teksttryk, Yteksttryk.

overensstemmelseMellemTrykOgBetoning(tone(Xteksttryk,Xposition,_), tone(Yteksttryk,Yposition,_), Metrum) :-
    Xteksttryk>Yteksttryk,
    erMereBetonet(Xposition, Yposition, Metrum).

Der er overensstemmelse mellem teksttryk og metrisk betoning for et tonepar, hvis

  • den første tones teksttryk, Xteksttryk, er større end den anden tones teksttryk, Yteksttryk
  • den første tones position, Xposition, er på en metrisk mere betonet position end den anden tones position, Yposition, (i Metrum).

Overensstemmelse mellem teksttryk og metrisk betoning for en rytme

Spørgsmålet om overensstemmelse mellem teksttryk og metrisk betoning for en rytme med et givent metrum omformuleres nu til nok en rekursiv definition:

g2+) Der er overensstemmelse mellem teksttryk og metrisk betoning i en rytme af tonerne X og Y efterfulgt af restrytmen R, hvis:
  • Der er overensstemmelse mellem teksttryk og metrisk betoning for parret X og Y
  • Der er overensstemmelse mellem teksttryk og metrisk betoning for parret Y og X
  • Der er overensstemmelse mellem teksttryk og metrisk betoning i rytmen af X og R
  • Der er overensstemmelse mellem teksttryk og metrisk betoning i rytmen af Y og R

 

g2°) Der er overensstemmelse mellem teksttryk og metrisk betoning i en rytme af kun én tone

Implementationen til Prolog følger nu ret enkelt:

overensstemmelseMellemTrykOgBetoning([X,Y|R], Metrum):-
    overensstemmelseMellemTrykOgBetoning(X, Y, Metrum ),
    overensstemmelseMellemTrykOgBetoning(Y, X, Metrum ),
    overensstemmelseMellemTrykOgBetoning([X|R], Metrum),
    overensstemmelseMellemTrykOgBetoning([Y|R], Metrum).

overensstemmelseMellemTrykOgBetoning([_],_).


3. Jævn melodirytme (regel h)

Regel h, der siger, at toners længde skal være 1, 2 eller 3 gange det laveste metriske lag, er jo allerede indarbejdet i de generelle regler for rytme.


4. Simpel melodirytme

Nu er alle reglerne faktisk beskrevet i Prolog, og tilbage er nu blot at samle kravene i én relation, der beskriver, hvad en „simpel melodirytme“ er:

simpelMelodirytme(Rytme, Metrum):-
    rytmeMedStartIFoerstePeriode(Rytme, Metrum),
    udenSynkoper(Rytme, Metrum),
    overensstemmelseMellemTrykOgBetoning(Rytme, Metrum).

En simpel melodirytme er altså en rytme med start i første periode, hvor:

  • der ikke er synkoper (regel f1-2)
  • der er overensstemmelse mellem tryk og betoning (regel g)

Programmet for simpel melodirytme er nu komplet og kan findes i dokumentet „SimpelMelodirytme.pro“. Husk, at det skal anvedes sammen med grundreglerne for rytme.


5. Tjek af rytmer

Man kan nu for eksempel spørge Prolog-programmet, om en given rytme er en „simpel melodirytme“. Det kan for eksempel være rytmen |2/4 to 8.-delsnoder  fjerdedelsnode  | til en tekstryme, der er - u - (for eksempel ordet „fællesskab“). Det er her naturligt at sætte 8.-delsnode til metrummets laveste lag, og metrummet 2/4 kan derfor udtrykkes [4,2,1] svarende til [ halvnode  , fjerdedelsnode  , 8.-delsnode  ]. Hver tone skal nu omformuleres til den valgte repræsentation i Prolog:

        Teksttryk         Position         Længde         Prolog
1. tone (ottendedelsnode): - 5 „1-slaget” 0 8.-delsnode 1 tone(5,0,1)
2. tone (ottendedelsnode): u 2 „1og”     1 8.-delsnode 1 tone(2,1,1)
3. tone (fjerdedelsnode ): - 5 „2-slaget” 2 fjerdedelsnode 2 tone(5,2,2)

Hele rytmen er således: [tone(5,0,1),tone(2,1,1),tone(5,2,2)]. Vi ønsker nu at se, om målet simpelMelodirytme( [tone(5,0,1),tone(2,1,1),tone(5,2,2)], [4,2,1] ) kan opfyldes med de opstillede regler, altså om rytmen er en simpel melodirytme efter de opstillede regler. Dette gøres således:

?- simpelMelodirytme( [tone(5,0,1),tone(2,1,1),tone(5,2,2)], [4,2,1] ).

Prolog svarer:

yes

Rytmen er således en simpel melodirytme ifølge de opstillede regler.

Man kan i øvrigt (naturligvis) opstille mål for alle de opstillede klasuler, hvis man skulle have lyst. Man kan for eksempel undersøge, om [4,2,1] er et metrum:

?- metrum( [4,2,1] ).

Dette giver ikke overraskende svaret:

yes

Man kunne også undersøge, om [3,2,1] – svarende til [ fjerdedelsnode . ,  fjerdedelsnode  ,  8.-delsnode  ] – er et metrum:

?- metrum( [3,2,1] ).
no

Prolog svarer, at [3,2,1] ikke er et metrum, hvilket også er korrekt, da fjerdedelsnode .-laget ikke er et multiplum af det foregående lag, fjerdedelsnode -laget.


6. Generering af rytmer

Mere interessant er det, at man også kan få Prolog til at generere rytmer, der opfylder klausulen simpelMelodirytme. Dette gøres ved at erstatte en eller flere af værdierne med variabler.

Lad os for eksempel sige, at vi ønsker at finde alle de simple melodirytmer, der har tekstrytmen - u -, og som starter på 1-slaget i 2/4. Dette gøres ved at udskifte alle de tal, som vi ikke kender, men som vi gerne vil have svaret på, med variabelnavne efter eget valg. Rytmen |2/4 to 8.-delsnoder  fjerdedelsnode  | med tekstrytmen - u - var jo [tone(5,0,1),tone(2,1,1),tone(5,2,2)], og i denne rytme kan vi for eksempel udskifte den anden og den tredje tones positioner med variablenavnene P2 og P3, og de tre toners længder med L1, L2 og L3. Resultatet bliver følgende mål:

?- simpelMelodirytme( [tone(5,0,L1),tone(2,P2,L2),tone(5,P3,L3)], [4,2,1] ).

Målet er altså en rytme, hvor:

  • Første tone har teksttrykket 5 (-), positionen 0 (1-slaget i første takt) og længden L1.
  • Anden tone har teksttrykket 2 (u), positionen P2 og længden L2.
  • Tredje tone har teksttrykket 5 (-), positionen P3 og længden L3.
  • Metrummet er [4,2,1] svarende til [ halvnode  ,  fjerdedelsnode  ,  8.-delsnode  ].

Når Prolog skal opfylde et mål med variabler, forsøger det at udfylde variablerne med gyldige værdier. Svaret til ovenstående Prolog-mål er derfor:

L1 = 1
P2 = 1
L2 = 1
P3 = 2
L3 = 2

Disse værdier kan nu tolkes:

  • L1 = 1 Første tones længde er 1 8.-delsnode , dvs. 8.-delsnode
  • P2 = 1 Anden tones position er 1 8.-delsnode efter startpositionen, dvs. „1og“
  • L2 = 1 Anden tones længde er 1 8.-delsnode , dvs. 8.-delsnode
  • P3 = 2 Tredje tones position er 2 8.-delsnode efter startpositionen, dvs. „2-slaget“
  • L3 = 2 Tredje tones længde er 2 8.-delsnode , dvs. fjerdedelsnode

Med andre ord er rytmen |2/4 to 8.-delsnoder  fjerdedelsnode  | med tekstrytmen - u - en simpel melodirytme. Prolog har altså nu selv fundet den løsning, som vi havde ovenfor. Men man kan nu bede Prolog om yderligere svar:

L1 = 2
P2 = 2
L2 = 2
P3 = 4
L3 = 2

Dette resultat svarer til rytmen |2/4 fjerdedelsnode  fjerdedelsnode  | fjerdedelsnode  fjerdedelspause  |, der altså også med tekstrytmen - u - er en simpel melodirytme. Beder man om yderligere svar fås:

L1 = 3
P2 = 3
L2 = 1
P3 = 4
L3 = 2

Dette resultat svarer til rytmen |2/4 fjerdedelsnode . 8.-delsnode  | fjerdedelsnode  fjerdedelspause  |. Næste resultat er:

no

Dette resultat angiver, at der ikke er yderligere løsninger. Ifølge de opstillede regler kan tekstrytmen - u - i 2/4 med start på 1-slaget altså kun optræde på tre forskellige måder: |2/4 to 8.-delsnoder  fjerdedelsnode  |, |2/4 fjerdedelsnode  fjerdedelsnode  | fjerdedelsnode  fjerdedelspause  | og |2/4 fjerdedelsnode . 8.-delsnode  | fjerdedelsnode  fjerdedelspause  |.

Relation mellem tekstrytme og rytme

Eksemplet overfor var ret simpelt, da der kun var tre toner, og startpositionen var fastlagt på forhånd. Ved længere rytme bliver det hurtigt ret kompliceret at stille spørgsmål til Prolog, og jeg har derfor indført en „hjælperelation“ mellem en tekstrytme og en simpel melodirytme (i et metrum), der har samme tekstrytme:

simpelMelodirytmeMedTekstrytmen(Rytme, Tekstrytme, Metrum):-
    harTekstrytmen(Rytme,Tekstrytme),
    simpelMelodirytme(Rytme, Metrum).

Reglen siger (læst bagfra): Hvis Rytme er en simpel melodirytme i Metrum, og Rytme har samme tekstrytme som Tekstrytme, er Rytme en simpel melodirytme (i Metrum) med samme tekstrytme som Tekstrytme, hvilket jo er temmelig oplagt. Jeg vil ikke her gennemgå relationen harTekstrytme, da den er ret simpel, men blot henvis til programmets kildetekst.

Denne relation kan nu bruges til opstille mål, hvor man givet en tekstrytme og et metrum, får Prolog til at finde alle rytmer med simpel melodirytme. Som eksempel kan tages teksten »I skovens dybe stille ro« med følgende tekstrytme :

I skovens dybe stille ro

Til brug for Prolog-programmet omformuleres tekstrytmen til [2,6,2,4,2,5,2,4]. Vi vil nu for eksempel se på rytmer i 4/4, hvor der skelnes mellem betonede og ubetonede takter, hvilket kan udtrykkes som et metrum med lagene [ helnode helnode  , helnode  , halvnode  fjerdedelsnode  , 8.-delsnode  ], der i Prolog-repæsentationen er listen [16,8,4,2,1]. Man kan nu formulere målet om melodirytmer for ovenstående tekstrytme til Prolog-programmet således:

?- simpelMelodirytmeMedTekstrytmen( Rytme , [2,6,2,4,2,5,2,4] , [16,8,4,2,1] ).

Dette giver følgende 18 resultater:

Rytme = [tone(2,-2,2),tone(6,0,2),tone(2,2,2),tone(4,4,2),tone(2,6,2),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,2),tone(2,2,2),tone(4,4,2),tone(2,6,2),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,2),tone(2,2,2),tone(4,4,3),tone(2,7,1),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,2),tone(2,2,2),tone(4,4,3),tone(2,7,1),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,3),tone(2,3,1),tone(4,4,2),tone(2,6,2),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,3),tone(2,3,1),tone(4,4,2),tone(2,6,2),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,3),tone(2,3,1),tone(4,4,3),tone(2,7,1),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-2,2),tone(6,0,3),tone(2,3,1),tone(4,4,3),tone(2,7,1),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,1),tone(2,1,1),tone(4,2,1),tone(2,3,1),tone(5,4,1),tone(2,5,1),tone(4,6,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,2),tone(2,2,2),tone(4,4,2),tone(2,6,2),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,2),tone(2,2,2),tone(4,4,2),tone(2,6,2),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,2),tone(2,2,2),tone(4,4,3),tone(2,7,1),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,2),tone(2,2,2),tone(4,4,3),tone(2,7,1),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,3),tone(2,3,1),tone(4,4,2),tone(2,6,2),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,3),tone(2,3,1),tone(4,4,2),tone(2,6,2),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,3),tone(2,3,1),tone(4,4,3),tone(2,7,1),tone(5,8,1),tone(2,9,1),tone(4,10,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,3),tone(2,3,1),tone(4,4,3),tone(2,7,1),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;
Rytme = [tone(2,-1,1),tone(6,0,3),tone(2,3,1),tone(4,4,3),tone(2,7,1),tone(5,8,3),tone(2,11,1),tone(4,12,2)] ;
Rytme = [tone(2,7,1),tone(6,8,1),tone(2,9,1),tone(4,10,1),tone(2,11,1),tone(5,12,1),tone(2,13,1),tone(4,14,2)] ;
no

Disse resultater kan så omskrives til sædvanlig rytmenotation:

Alle 18 rytmer skrevet med almindelig rytmenotation

Rytmegenerator

Prolog-programmet havde den store fordel, at de opstillede regler ret ubesværet kunne omformes til et computerprogram. Desværre er repræsentationen med tallene ikke den mest bekvemme. Jeg har derfor udarbejdet programmet Rytmegenerator, der er et almindeligt computer-program, der anvender de opstillede regler til at generere rytmer på baggrund af en tekstrytme. Til forskel fra Prolog-programmet er Rytmegenerator et program med en almindelig grafisk brugergrænseflade. Man indtaster simpelthen en tekstrytme og klikker på symbolerne for teksttryk:

Billede fra Rytmegenerator - indtastning af stavelser og teksttryk

Herefter vælger man den musikalske norm – i dette tilfælde „simpel melodirytme“:

Angivelse af den musikalske norm (model)

Ved et klik på knappen „Opret Rytmer“ vil man så blive præsenteret for de 18 rytmer ovenfor i almindelig rytmenotation.

Programmet Rytmegenerator kan desuden anvendes i forbindelse med Prolog-programmet til at udforme „spørgsmål“ og fortolke resultater i den repræsentation, som Prolog-programmet anvender. Man kan således anvende Rytmegenerator til at angive en tekstrytme og en musikalsk norm. Man kan så fra „Prolog“-menuen vælge „Kopier mål til skuffen“:

Valg af 'Kopier mål til skuffen'

Der vil så blive kopieret følgende mål:

?- simpelMelodirytmeMedTekstrytmen( Rytme , [2,6,2,4,2,5,2,4] , [16,8,4,2,1] ).

Denne tekst kan så sættes ind i Prolog-programmet.

Omvendt kan man få Rytmegenerator til at vise resultater fra Prolog-programmet, der jo for eksempel kan se således ud:

Rytme = [tone(2,-2,2),tone(6,0,2),tone(2,2,2),tone(4,4,2),tone(2,6,2),tone(5,8,2),tone(2,10,2),tone(4,12,2)] ;

Man kopierer simpelthen alle de linier, man vil have vist, og vælger „Vis rytmer i skuffen“ (Macinosh) eller „Vis rytmer i udklipsholder“ (Windows) fra „Prolog“-menuen. Resultaterne vil så blive vist i almindelig rytmenotation. Man kan i øvrigt sagtens medtage linier, der ikke indeholder rytmer – Rytmegenerator vil kun vise linier, hvor der er en rytme.