annotate yeti/silvet_onecolumn.yeti @ 27:9ec18d453889

Split single-column and matrix versions
author Chris Cannam
date Mon, 31 Mar 2014 17:06:24 +0100
parents yeti/silvet.yeti@fbc4011c7693
children cd9fd74931bb
rev   line source
Chris@12 1
Chris@27 2 program silvet_onecolumn;
Chris@12 3
Chris@12 4 { prepareTimeFrequency } = load timefreq;
Chris@13 5 { loadTemplates, extractRanges } = load templates;
Chris@14 6
Chris@19 7 em1 = load em_onecolumn;
Chris@12 8
Chris@12 9 mat = load may.matrix;
Chris@12 10 vec = load may.vector;
Chris@14 11 plot = load may.plot;
Chris@12 12
Chris@12 13 templates = loadTemplates ();
Chris@12 14
Chris@13 15 ranges = extractRanges templates;
Chris@13 16
Chris@13 17 eprintln "\nWe have \(length (keys templates)) instruments:";
Chris@13 18 for (sort (keys templates)) do k:
Chris@14 19 eprintln " * \(k) \(mat.size templates[k]) range \(ranges[k].lowest) -> \(ranges[k].highest)";
Chris@13 20 done;
Chris@12 21 eprintln "";
Chris@12 22
Chris@12 23 columns = prepareTimeFrequency "test.wav";
Chris@12 24
Chris@12 25 height = if empty? columns then 0 else vec.length (head columns) fi;
Chris@12 26
Chris@19 27 em1data = em1.initialise ranges templates 88;
Chris@19 28
Chris@23 29 col = head (drop 50 columns); // (drop ((length columns) / 2) columns);
Chris@19 30
Chris@20 31 \() (plot.plot [ Caption "Source frequency distribution", Vector col ]);
Chris@19 32
Chris@22 33 \() (plot.plot [ Caption "Source distribution beforehand", Grid em1data.sources]);
Chris@20 34
Chris@25 35 normalise v =
Chris@25 36 (s = vec.sum v;
Chris@25 37 if s > 0 then vec.divideBy s v
Chris@25 38 else v
Chris@25 39 fi);
Chris@25 40
Chris@20 41 oneIteration em1data col n =
Chris@25 42 ({ estimate, q } = em1.performExpectation em1data col;
Chris@19 43 newdata = em1.performMaximisation em1data col q;
Chris@21 44 if (n % 6 == 0) then
Chris@20 45 \() (plot.plot [ Caption "Pitch distribution before and after M-step update for iteration \(n)", Vector (em1data.pitches), Vector (newdata.pitches) ]);
Chris@22 46 \() (plot.plot [ Caption "Source distribution after M-step update for iteration \(n)", Grid newdata.sources ]);
Chris@25 47 \() (plot.plot [ Caption "Q function for E-step iteration \(n)", Vector q ]);
Chris@25 48 \() (plot.plot [ Caption "Estimate from E-step iteration \(n) against original source distribution, and difference between them", Vector estimate, Vector (normalise col), Vector (vec.subtract estimate (normalise col)) ]);
Chris@20 49 fi;
Chris@19 50 newdata);
Chris@19 51
Chris@21 52 iterations = 12;
Chris@19 53
Chris@20 54 var d = em1data;
Chris@20 55
Chris@20 56 for [1..iterations] do i:
Chris@20 57 d := oneIteration d col i;
Chris@20 58 done;
Chris@14 59
Chris@21 60 var sounding = [];
Chris@21 61
Chris@22 62 println "pitch distribution: \(vec.list d.pitches)";
Chris@21 63
Chris@21 64 for [d.lowest .. d.highest] do p:
Chris@21 65 if (vec.at d.pitches p) > 0.05 then
Chris@21 66 sounding := sounding ++ [p];
Chris@21 67 fi;
Chris@21 68 done;
Chris@21 69
Chris@21 70 println "Sounding: \(sounding)";
Chris@21 71
Chris@21 72 toNote p = (array ["A","A#","B","C","C#","D","D#","E","F","F#","G","G#"])[p % 12];
Chris@21 73
Chris@21 74 println "Notes: \(map toNote sounding)";
Chris@21 75
Chris@21 76 var instruments = [];
Chris@21 77 for sounding do p:
Chris@22 78 var best = 0;
Chris@21 79 var bestp = 0;
Chris@22 80 for [0..d.instCount-1] do i:
Chris@22 81 if mat.at d.sources p i > bestp then
Chris@22 82 bestp := mat.at d.sources p i;
Chris@21 83 best := i;
Chris@21 84 fi;
Chris@21 85 done;
Chris@21 86 if bestp > 0 then
Chris@21 87 instruments := instruments ++ [best];
Chris@21 88 else
Chris@22 89 instruments := instruments ++ [-1];
Chris@21 90 fi;
Chris@21 91 done;
Chris@21 92
Chris@22 93 println "Instruments: \(map do i: (d.instruments[i]) done instruments)";
Chris@21 94
Chris@24 95 if not (empty? sounding) then
Chris@24 96 p = head sounding;
Chris@24 97 i = head instruments;
Chris@24 98 w = mat.getColumn p d.templates[i];
Chris@24 99 \() (plot.plot [ Vector w, Vector (normalise col), Caption "Template for instrument \(d.instruments[i]), pitch \(p), against normalised source distribution" ]);
Chris@24 100 fi;
Chris@21 101
Chris@14 102 ();
Chris@14 103
Chris@14 104