Mercurial > hg > silvet
comparison yeti/em_onecolumn.yeti @ 25:80f02ff5d37a
I think that previous normalisation was wrong!
author | Chris Cannam |
---|---|
date | Mon, 31 Mar 2014 15:41:15 +0100 |
parents | 0e8ee830b5ee |
children |
comparison
equal
deleted
inserted
replaced
24:0e8ee830b5ee | 25:80f02ff5d37a |
---|---|
14 (s = vec.sum v; | 14 (s = vec.sum v; |
15 if s > 0 then vec.divideBy s v | 15 if s > 0 then vec.divideBy s v |
16 else v | 16 else v |
17 fi); | 17 fi); |
18 | 18 |
19 normaliseSources s = | |
20 (denoms = fold do acc inst: vec.add [acc, (mat.getColumn inst s)] done | |
21 (vec.zeros (mat.height s)) [0..(mat.width s)-1]; | |
22 mat.fromColumns | |
23 (map do inst: vec.divide (mat.getColumn inst s) denoms done | |
24 [0..(mat.width s)-1])); | |
25 | |
19 initialise ranges templates notes = | 26 initialise ranges templates notes = |
20 (instruments = sort (keys ranges); | 27 (instruments = sort (keys ranges); |
21 { | 28 { |
22 pitches = // z in the original. 1 per note | 29 pitches = // z in the original. 1 per note |
23 normalise (vec.randoms notes), | 30 normalise (vec.randoms notes), |
24 sources = // u in the original. 1 per note-instrument | 31 sources = normaliseSources // u in the original. 1 per note-instrument |
25 mat.fromRows | 32 (mat.fromColumns |
26 (map do note: | 33 (map do instrument: |
27 normalise | 34 (vec.fromList |
28 (vec.fromList | 35 (map do note: |
29 (map do instrument: | 36 if inRange ranges instrument note then 1 else 0 fi |
30 if inRange ranges instrument note then 1 else 0 fi | 37 done [0..notes-1])) |
31 done instruments)) | 38 done instruments)), |
32 done [0..notes-1]), | |
33 instruments = array instruments, | 39 instruments = array instruments, |
34 instCount = length instruments, | 40 instCount = length instruments, |
35 noteCount = notes, | 41 noteCount = notes, |
36 templates = array | 42 templates = array |
37 (map do iname: | 43 (map do iname: |
67 { w, p, s } = distributionsFor data inst note; | 73 { w, p, s } = distributionsFor data inst note; |
68 vec.add [acc, vec.scaled (p * s) w]; | 74 vec.add [acc, vec.scaled (p * s) w]; |
69 done acc [data.ranges[inst].lowest .. | 75 done acc [data.ranges[inst].lowest .. |
70 data.ranges[inst].highest] | 76 data.ranges[inst].highest] |
71 done (vec.consts epsilon (vec.length column)) [0..data.instCount-1]; | 77 done (vec.consts epsilon (vec.length column)) [0..data.instCount-1]; |
72 vec.divide column estimate); | 78 { estimate, q = vec.divide column estimate }); |
73 | 79 |
74 performMaximisation data column q = | 80 performMaximisation data column q = |
75 (column = normalise column; | 81 (column = normalise column; |
76 | 82 |
77 pitches = vec.fromList | 83 pitches = vec.fromList |
86 else epsilon | 92 else epsilon |
87 fi | 93 fi |
88 done [0..data.noteCount-1]); | 94 done [0..data.noteCount-1]); |
89 pitches = vec.divideBy (vec.sum pitches) pitches; | 95 pitches = vec.divideBy (vec.sum pitches) pitches; |
90 | 96 |
91 sources = mat.fromRows | 97 sources = mat.fromColumns |
92 (map do note: vec.fromList | 98 (map do inst: vec.fromList |
93 (map do inst: | 99 (map do note: |
94 if not inRange data.ranges inst note then epsilon else | 100 (if not inRange data.ranges inst note then epsilon else |
95 { w, p, s } = distributionsFor data inst note; | 101 { w, p, s } = distributionsFor data inst note; |
96 fold do acc bin: | 102 fold do acc bin: |
97 acc + s * p * (vec.at w bin) * (vec.at q bin); | 103 acc + s * p * (vec.at w bin) * (vec.at q bin); |
98 done epsilon [0..vec.length column - 1] | 104 done epsilon [0..vec.length column - 1] |
99 fi; | 105 fi); |
100 done [0..data.instCount-1]) | 106 done [0..data.noteCount-1]) |
101 done [0..data.noteCount-1]); | 107 done [0..data.instCount-1]); |
102 | |
103 sourceDenoms = fold do acc inst: | |
104 vec.add [acc, (mat.getColumn inst sources)] | |
105 done (vec.zeros data.noteCount) [0..data.instCount-1]; | |
106 | 108 |
107 //!!! shouldn't this normalisation be the other way? (rows, not columns) | 109 sources = normaliseSources sources; |
108 /* sources = mat.fromColumns | |
109 (map do inst: | |
110 vec.divide (mat.getColumn inst sources) sourceDenoms; | |
111 done [0..data.instCount-1]); | |
112 */ | |
113 sources = mat.fromRows | |
114 (map do note: | |
115 vec.divide (mat.getRow note sources) sourceDenoms; | |
116 done [0..data.noteCount-1]); | |
117 | 110 |
118 data with { | 111 data with { |
119 pitches, | 112 pitches, |
120 sources, | 113 sources, |
121 }); | 114 }); |