Jouez au Canon de Pachelbel

29

Sortez l'extrait suivant du Canon de Pachelbel en D sous forme audio:

Canon de Pachelbel en ré

Règles

  • N'importe quel format / encodage peut être utilisé, tant qu'un codec existait avant la création de ce défi
  • N'importe quel instrument (un véritable instrument, une synthèse MIDI, etc.) peut être utilisé
  • Le tempo doit être de 65 BPM (comme indiqué dans la partition) - si vous ne pouvez pas obtenir exactement 65 BPM, vous pouvez utiliser n'importe quel tempo dans la plage (incluse) 64,75 - 65,25
  • La partition est en pitch de concert
  • Un réglage de tempérament égal doit être utilisé (spécifiquement 12-ET avec A4 = 440 Hz)

Pour référence, voici un extrait de pile qui jouera l'extrait:

Mego
la source
Est-ce que cet extrait serait compétitif car il le télécharge d'ailleurs
Blue
4
@muddyfish Non, car l'extraction de la sortie d'une source externe est une faille standard.
Mego
La sortie d'un fichier midi au lieu d'audio serait-elle acceptable?
DJMcMayhem
@DJMcMayhem Oui, les fichiers MIDI sont acceptables.
Mego
Je suppose que l'accord final (uniquement) est requis en entier? Cela interdit effectivement les langages / API non polyphoniques
Level River St

Réponses:

9

JavaScript (ES7), 249 242 241 octets

with(new AudioContext)for(t=i=0;n=parseInt('l43l431db98643o86ogfdbdfdgfdzbdzgigikigfdbzbdv98db9864311480'[i++],36);)with(createOscillator())frequency.value=880*2**(-~-n%20/12),connect(destination),start(t),stop(i>56?t+q*8:t+=n>20?q=6/13:q/2)

Merci à @Neil et @PatrickRoberts pour quelques économies d'octets!

Explication

La notation est empaquetée dans la chaîne où chaque caractère est une seule note en tant que chiffre de base 36. Les valeurs des notes sont déterminées par la formule (19 - pitch) * time + 1pitchest le nombre de demi-tons inférieur à A5 et timecorrespond 1à un demi 20-quadrillage ou à un quartet. Le 0à la fin arrête la forboucle.

Le tempo est de 65,22 bpm Edit: exactement 65 bpm maintenant, pour 2 octets de plus .

Cette explication / démo utilise à la Math.powplace de **pour la compatibilité du navigateur. Il règle également le gain des oscillateurs pour .3que l'accord final ne fasse pas saigner vos oreilles (le gain par défaut est 1).

with(new AudioContext)            // use HTML5 audio
  for(                            // iterate through the note pitches and lengths
    t=i=0;                        // t = current time to place the note
    n=parseInt(                   // n = note pitch/length

      // Packed notation string
      'l43l431db98643o86ogfdbdfdgfdzbdzgigikigfdbzbdv98db9864311480'

    [i++],36);
  )
    with(createOscillator())      // create the note oscillator

      // Set the note frequency (using Math.pow for the demo).
      //frequency.value=880*2**(-~-n%20/12),
      frequency.value=880*Math.pow(2,-~-n%20/12),

      // Send the note's sound through the speakers (for the demo, we'll connect it to
      // a gain node so we can reduce the volume).
      //connect(destination),
      connect((g=createGain(),g.gain.value=.3,g.connect(destination),g)),

      start(t),                     // schedule the note to sound
      stop(                         // schedule the end of the note
        i>56?                       // if we are in the final chord
          t+                        //   do not increment the time
            q*8                     //   hard-code the length to a semibreve
        :t+=n>20?q=6/13:q/2         // else update the length based on the note value
      )

Vous pouvez appuyer sur le bouton ci-dessus pour le tester dans n'importe quel navigateur prenant en charge l'API HTML5 Web Audio .

user81655
la source
880*2**(-~-n%20/12)devrait vous faire économiser quelques octets.
Neil
@Neil Merci. Je soupçonne que je peux aussi m'en débarrasser -~-en modifiant le format de l'emballage de mes notes (le + 1dans la formule n'est là que parce que j'ai besoin 0d'arrêter la forboucle et j'étais trop paresseux pour y penser beaucoup avant de poster).
user81655
J'ai vu ça après avoir posté ma réponse, lol
Patrick Roberts
Vous pouvez enregistrer un autre octet en remplaçant c=new AudioContext;par with(new AudioContext)et en supprimant les deux occurrences de c.dans le programme.
Patrick Roberts
1
@ kamoroso94 Non. L'exposant peut être une fraction, donc si je l'utilise, <<il le convertit en entier.
user81655
8

Mathematica, 212 152 139 139 135 octets

{#~(s=##~SoundNote~41&)~1&/@LetterNumber@"uursuursuikmnprsrrnprrfgikigifgiggkiggfdfdbdfgikggkikkmnikmnprsu",{14,18,21}~s~16}~Sound~18.5

Sort un Soundobjet qui joue le Canon de Pachelbel en D lorsque le bouton Lecture est enfoncé. L'instrument est l'instrument MIDI n ° 41 "Violon".

L'audio

Cliquez moi!

Explication

LetterNumber@"uursuursuikmnprsrrnprrfgikigifgiggkiggfdfdbdfgikggkikkmnikmnprsu"

Recherchez les nombres de lettres de chaque caractère dans la chaîne ("a" -> 1, "b" -> 2, etc.), enveloppés d'un List. (Cette chaîne représente le Canon de Pachelbel en ré)

#~(s=##~SoundNote~41&)~1&/@...

Réglez ssur la SoundNotefonction dont l'instrument est le # 41. Réglez la durée sur 1 et mappez cette fonction à chaque élément du List(créant ainsi SoundNotedes objets primitifs).

{14,18,21}~s~16

Faites la dernière triade. (La durée 16est là pour rendre la dernière note 16 fois plus longue - une note entière est seize fois une seizième.)

... ~Sound~18.5

Fabriquez un Soundobjet, en 18.5secondes (car le tempo est de 65 bpm [5 mesures de 4/4 avec un tempo de 65 bpm = environ 18,5 secondes]).

Version 126 octets, non concurrente

Sound[{(s=SoundNote)/@LetterNumber@"uursuursuikmnprsrrnprrfgikigifgiggkiggfdfdbdfgikggkikkmnikmnprsu",{14,18,21}~s~16},240/13]

Pas de concurrence car la sortie contient deux doubles croches au lieu d'une huitième et la séparation est assez perceptible.

JungHwan Min
la source
14
Vraiment, Mathematica n'a pas intégré pour Canon de Pachelbel?
Stewie Griffin
1
@StewieGriffin Seul le tout probablement, et le coût de l'écrêtage serait trop élevé.
Mego
@StewieGriffin Étonnamment, ce n'est pas le cas.
JungHwan Min
6

Bubblegum , 203 octets

00000000: e002 2800 c35d 0026 9509 6f34 76f2 ffad  ..(..].&..o4v...
00000010: 4150 0893 a735 bd02 a1eb 1237 18fe 5498  AP...5.....7..T.
00000020: 120a 83e1 6662 8a5e 9709 fe8a 3430 0f48  ....fb.^....40.H
00000030: 5008 54af d19a b44f 2be9 fb3b bf9d 206d  P.T....O+..;.. m
00000040: abbf 12f0 2151 6dae 4712 8c18 4d8e f5cd  ....!Qm.G...M...
00000050: eb85 404c 17cd bd5c 2775 38bd eb50 ab88  ..@L...\'u8..P..
00000060: e015 fb7e 4b1e 5ddb 515b 144c fc5e c1be  ...~K.].Q[.L.^..
00000070: 3d5d 20cd e950 4a1d 256e b56e d364 188b  =] ..PJ.%n.n.d..
00000080: 6fa1 afcc 2100 0235 ada0 2f23 411d 95dd  o...!..5../#A...
00000090: 6665 3b45 041d cbe2 8e3b 2456 fb8d 4e4c  fe;E.....;$V..NL
000000a0: 1a7f b814 a6cf 850e 9b6c 9285 3a6f 1ec3  .........l..:o..
000000b0: 02ed 505c 996b eb4d 209c 2776 a8aa 8380  ..P\.k.M .'v....
000000c0: 42cc b779 218e e75e 8000 00              B..y!..^...

Essayez-le en ligne!

Il s'agit d'un hexdump (inversé avec xxd -r) du code source. Le fichier MIDI qu'il produit est le suivant (également un hexdump):

00000000: 4d54 6864 0000 0006 0001 0002 01e0 4d54  MThd..........MT
00000010: 726b 0000 0019 00ff 5902 0200 00ff 5804  rk......Y.....X.
00000020: 0402 1808 00ff 5103 0e15 c500 ff2f 004d  ......Q....../.M
00000030: 5472 6b00 0001 f200 c000 00ff 0405 5069  Trk...........Pi
00000040: 616e 6f00 9051 5f81 5880 5100 1890 4e5f  ano..Q_.X.Q...N_
00000050: 6c80 4e00 0c90 4f5f 6c80 4f00 0c90 515f  l.N...O_l.O...Q_
00000060: 8158 8051 0018 904e 5f6c 804e 000c 904f  .X.Q...N_l.N...O
00000070: 5f6c 804f 000c 9051 5f6c 8051 000c 9045  _l.O...Q_l.Q...E
00000080: 5f6c 8045 000c 9047 5f6c 8047 000c 9049  _l.E...G_l.G...I
00000090: 5f6c 8049 000c 904a 5f6c 804a 000c 904c  _l.I...J_l.J...L
000000a0: 5f6c 804c 000c 904e 5f6c 804e 000c 904f  _l.L...N_l.N...O
000000b0: 5f6c 804f 000c 904e 5f81 5880 4e00 1890  _l.O...N_.X.N...
000000c0: 4a5f 6c80 4a00 0c90 4c5f 6c80 4c00 0c90  J_l.J...L_l.L...
000000d0: 4e5f 8158 804e 0018 9042 5f6c 8042 000c  N_.X.N...B_l.B..
000000e0: 9043 5f6c 8043 000c 9045 5f6c 8045 000c  .C_l.C...E_l.E..
000000f0: 9047 5f6c 8047 000c 9045 5f6c 8045 000c  .G_l.G...E_l.E..
00000100: 9043 5f6c 8043 000c 9045 5f6c 8045 000c  .C_l.C...E_l.E..
00000110: 9042 5f6c 8042 000c 9043 5f6c 8043 000c  .B_l.B...C_l.C..
00000120: 9045 5f6c 8045 000c 9043 5f81 5880 4300  .E_l.E...C_.X.C.
00000130: 1890 475f 6c80 4700 0c90 455f 6c80 4500  ..G_l.G...E_l.E.
00000140: 0c90 435f 8158 8043 0018 9042 5f6c 8042  ..C_.X.C...B_l.B
00000150: 000c 9040 5f6c 8040 000c 9042 5f6c 8042  ...@[email protected]_l.B
00000160: 000c 9040 5f6c 8040 000c 903e 5f6c 803e  ...@_l.@...>_l.>
00000170: 000c 9040 5f6c 8040 000c 9042 5f6c 8042  ...@[email protected]_l.B
00000180: 000c 9043 5f6c 8043 000c 9045 5f6c 8045  ...C_l.C...E_l.E
00000190: 000c 9047 5f6c 8047 000c 9043 5f81 5880  ...G_l.G...C_.X.
000001a0: 4300 1890 475f 6c80 4700 0c90 455f 6c80  C...G_l.G...E_l.
000001b0: 4500 0c90 475f 8158 8047 0018 9049 5f6c  E...G_.X.G...I_l
000001c0: 8049 000c 904a 5f6c 804a 000c 9045 5f6c  .I...J_l.J...E_l
000001d0: 8045 000c 9047 5f6c 8047 000c 9049 5f6c  .E...G_l.G...I_l
000001e0: 8049 000c 904a 5f6c 804a 000c 904c 5f6c  .I...J_l.J...L_l
000001f0: 804c 000c 904e 5f6c 804e 000c 904f 5f6c  .L...N_l.N...O_l
00000200: 804f 000c 9051 5f6c 8051 000c 904a 5f00  .O...Q_l.Q...J_.
00000210: 904e 5f00 9051 5f8e 4c80 4a00 0080 4e00  .N_..Q_.L.J...N.
00000220: 0080 5100 8360 ff2f 00                   ..Q..`./.
Mego
la source
6

BBC BASIC, 141 caractères ASCII (65.217BPM)

*TEMPO1
F.i=2TO71j=i>65SOUND1-j*(479+i/2),-9,ASCM." \\VX\\VX\DHLNRVXVVNRVV>@DHD@D>@D@@HD@@>:>:6:>@DH@@HDHHLNLDHLNRVXNNVV\\",i)*2,23-j*161N.

Révisé pour tenir compte de la limite de tempo. Met à jour l'explication plus tard.

BBC BASIC, 123 caractères ASCII (non compétitif en 60BPM)

Téléchargez l'interprète sur http://www.bbcbasic.co.uk/bbcwin/download.html

Joue la chanson directement lors de l'exécution.

F.i=1TO67j=i>64SOUND1-j*(447+i),-9,ASCM."\\VX\\VX\DHLNRVXVVNRVV>@DHD@D>@D@@HD@@>:>:6:>@DH@@HDHHLNLDHLNRVXNV\",i)*2,5-j*75N.

Non golfé

  FOR i = 1 TO 67
    j = i > 64: REM j=0 for the first four bars composed of 16th notes, j=-1 for the final chord (whole note)
    SOUND 1 - j * (447 + i), -9, ASC(MID$("\\VX\\VX\DHLNRVXVVNRVV>@DHD@D>@D@@HD@@>:>:6:>@DH@@HDHHLNLDHLNRVXNV\", i)) * 2, 5 - j * 75
  NEXT i

Explication

jest un drapeau indiquant si nous sommes dans les 4 premières mesures ou l'accord final. TRUE est -1en BBC BASIC.

L' SOUNDinstruction prend 4 paramètres:

CANAL: pour les 4 premières mesures, il s'agit du canal 1. Pour les 3 notes de l'accord dans la 5e mesure, les numéros de canal sont 201, 202 et 203 hexadécimaux (513 514 et 515 décimal). Cela signifie jouer sur les canaux 1,2 et 3, les 2 initiales signifiant jouer simultanément avec 2 notes sur d'autres canaux (c'est-à-dire jouer un accord de 3 notes).

VOLUME: Donné comme une valeur négative car les valeurs positives représentent d'autres effets (enveloppes sonores.). Fixé à -9 (ira jusqu'à -15, ce qui est le plus fort.)

PITCH: Pour cet air, varie de D4 = 108 à A5 = 184. Chaque pas entier est 1/4 d'un demi-ton. Les valeurs sont stockées sous forme de codes ASCII dans la plage 54 à 92 et doublées pour régénérer la valeur correcte. Les 1/8 de notes sont stockées sous forme de doubles de 1/16 de note. L'accord final est stocké sur 3 hauteurs distinctes et la longueur de la note varie en note entière comme ci-dessous.

DURÉE: en 1/20 de seconde. La durée de la 1 / 16ème note est de 5/20 de seconde, donc 60 1/4 notes par minute (la résolution est insuffisante pour rendre le tempo plus précis.) La note entière est de 5 - (- 75) = 80 unités (4 secondes ) longue.

Level River St
la source
Cela ne devrait-il pas être qualifié de non concurrentiel?
JungHwan Min
@JungHwanMin Pour répondre au texte original de votre commentaire: le BPM est à moins de 10% de 65. Il n'y a pas de limite sur la précision de la question. L'appel de l'OP.
Level River St
60 bpm est distinctement audible de 65 bpm. Je permettrai que cela ne soit pas en concurrence car c'est une restriction imposée par la langue.
Mego
@Mego Au départ, je pensais que BBC Basic comptait en centièmes de seconde par défaut, je ne savais pas que c'était aussi grossier que les vingtièmes de seconde. J'ai ajusté mon code au 100ème, alors maintenant je peux faire 65.215BPM, est-ce OK? Cela a pris un peu de violon supplémentaire car la note entière dépasse 256/100, j'ai donc dû la jouer en deux demi-notes. 50e de seconde serait un code plus court mais 62,5BPM n'est pas vraiment une amélioration.
Level River St
Soit dit en passant, il y avait quelques erreurs de transcription mineures dans le message d'origine. Vous devrez peut-être modifier un peu votre code. (Le code actuel a la mauvaise version)
JungHwan Min
4

Befunge, 242 octets

Le morceau est écrit sur stdout au format d'un fichier MIDI. Vous devrez rediriger cette sortie vers un fichier .mid afin de lire l'extrait.

<v:"MThd"0006000101"MTrk"001+"~e"0*3"UQ"30*5"-\"9
v>9#:-#,_0"QONLJIGEJIGEGCGECB@>@B@BCEGCECBECEGECBNLJNONLJIGEQONQONQ"0\:
_v#:\%+77+1,"@",\,*8*82,+3*4!*-3::\,"@",:,*:*62,1
v>"QNJQNJ"0\:
_v#:\+1,"@",\,-**82/3\*:*62:,+!\**97!-3::\
@>,\"/U"3*,,,

Essayez-le en ligne! , bien que je ne pense pas qu'il soit actuellement possible d'enregistrer la sortie de telle manière qu'elle conserve l'intégrité binaire des données.

Explication

La première ligne est essentielle juste un en-tête MIDI codé en dur, qui est sorti au début de la ligne deux. Le reste de la ligne deux code la séquence de notes en tant que leurs valeurs MIDI, qui sont commodément ASCII. La troisième ligne écrit les commandes MIDI pour jouer ces notes, la durée étant automatiquement calculée (chaque note est un demi-crochet sauf si i% 14 == 0). L'accord final est traité comme un cas spécial sur les lignes quatre et cinq (car cela nécessite d'appuyer simultanément sur plusieurs touches), et la sixième ligne écrit le marqueur MIDI final de fin de piste.

James Holderness
la source
4

C, 248 228 210 198 193 191 191 octets

#define y(x)cos(.346*t*exp(x/17.))
d=1846,t;main(c){for(;t++<d*80;putchar(c=((t<d*64?y(("TTQRTTQRTHJLMOQRQQMOQQEFHJHFHEFHFFJHFFECECACEFHJFFJHJJLMHJLMOQRT"[t/d]-72)):y(12)+y(9)+y(5))+3)*42));}

Cela produit une séquence d'échantillons non signés 8 bits destinés à être lus à 8 000 échantillons par seconde. Si vous avez une ancienne configuration UNIX / Linux, vous pouvez rediriger la sortie vers /dev/audio. Sur certaines distributions Linux plus récentes, vous devrez peut-être diriger la sortie vers le lecteur de ligne de commande ALSAaplay

plafond
la source
génial. Excellente solution!
Abel Tom
1

SmileBASIC, 115 octets

BGMPLAY"@305T65L16[A8F+G]2A{r}F#8>F#GABAGAF#GAG8BAG8F#EF#EDEF#GABG8BAB8<C#D{r}AA1:1[R1]4F#1:2[R1]4D1{r=>AB<C#DEF#G}

L'utilisation d'un bel instrument valait 4 octets supplémentaires :)

12Me21
la source
Qu'est-ce que l'instrument 305?
Pavel
SmileBASIC possède tous les instruments MIDI généraux, mais possède également un tas d'instruments «secrets» non documentés. Voici un exemple d'une version beaucoup plus compliquée du Canon de Pachelbel joué à l'aide de cet instrument: dropbox.com/s/wfhr90tdkkji6qy/305.mp3?dl=0
12Me21
0

JavaScript (ES6) utilisant WAV.js , 325 octets

w=new WAV();w.addProgression(btoa9‘¹9‘¹8€¹‘9‘¹‘y‘9‘y¸€x¸x€8¸€8¸888¸€x¸€8€xù€xù‘y9`.replace(/[CF]./g,'$&#').split(/(?=[A-G])/g).map((f=t=>n=>({note:n,time:t}))(15/65)));['D5','F5#','A5'].map(n=>w.addNote(f(48/13)(n),.3,[],1,1));new Audio(URL.createObjectURL(w.toBlob())).play()
<script src="https://cdn.rawgit.com/patrickroberts/3b065ab94ce5094baacf45ed23e2a16e/raw/9c367e292fbee8341e1019d0d5953a2234449882/wav.babel.js"></script>

Patrick Roberts
la source