Mercurial > hg > svcore
comparison base/ColumnOp.h @ 1193:927d329252bf spectrogram-minor-refactor
Convert ColumnNormalization to an enum class, and separate out normalize-visible
author | Chris Cannam |
---|---|
date | Thu, 14 Jul 2016 16:12:05 +0100 |
parents | f6998e304b36 |
children | c118d2022ffa |
comparison
equal
deleted
inserted
replaced
1192:9884efa1f88a | 1193:927d329252bf |
---|---|
19 #include "BaseTypes.h" | 19 #include "BaseTypes.h" |
20 | 20 |
21 #include <cmath> | 21 #include <cmath> |
22 | 22 |
23 /** | 23 /** |
24 * Display normalization types for columns in e.g. grid plots. | |
25 * | |
26 * Max1 means to normalize to max value = 1.0. | |
27 * Sum1 means to normalize to sum of values = 1.0. | |
28 * | |
29 * Hybrid means normalize to max = 1.0 and then multiply by | |
30 * log10 of the max value, to retain some difference between | |
31 * levels of neighbouring columns. | |
32 * | |
33 * Area normalization is handled separately. | |
34 */ | |
35 enum class ColumnNormalization { | |
36 None, | |
37 Max1, | |
38 Sum1, | |
39 Hybrid | |
40 }; | |
41 | |
42 /** | |
24 * Class containing static functions for simple operations on data | 43 * Class containing static functions for simple operations on data |
25 * columns, for use by display layers. | 44 * columns, for use by display layers. |
26 */ | 45 */ |
27 class ColumnOp | 46 class ColumnOp |
28 { | 47 { |
31 * Column type. | 50 * Column type. |
32 */ | 51 */ |
33 typedef std::vector<float> Column; | 52 typedef std::vector<float> Column; |
34 | 53 |
35 /** | 54 /** |
36 * Normalization types. | |
37 * | |
38 * NormalizeColumns means to normalize to max value = 1. | |
39 * NormalizeHybrid means normalize to max = 1 and then multiply by | |
40 * log10 of the max value, to retain some difference between | |
41 * levels of neighbouring columns. | |
42 * | |
43 * NormalizeVisibleArea is ignored here and is included only so as | |
44 * to match the set of normalization options historically provided | |
45 * in the SV spectrogram layer. | |
46 */ | |
47 enum Normalization { | |
48 NoNormalization, | |
49 NormalizeColumns, | |
50 NormalizeVisibleArea, | |
51 NormalizeHybrid | |
52 }; | |
53 | |
54 /** | |
55 * Scale an FFT output by half the FFT size. | 55 * Scale an FFT output by half the FFT size. |
56 */ | 56 */ |
57 static Column fftScale(const Column &in, int fftSize) { | 57 static Column fftScale(const Column &in, int fftSize) { |
58 | 58 |
59 Column out; | 59 Column out; |
97 | 97 |
98 /** | 98 /** |
99 * Return a column normalized from the input column according to | 99 * Return a column normalized from the input column according to |
100 * the given normalization scheme. | 100 * the given normalization scheme. |
101 */ | 101 */ |
102 static Column normalize(const Column &in, Normalization n) { | 102 static Column normalize(const Column &in, ColumnNormalization n) { |
103 | 103 |
104 if (n == NoNormalization || n == NormalizeVisibleArea) { | 104 if (n == ColumnNormalization::None) { |
105 return in; | 105 return in; |
106 } | 106 } |
107 | 107 |
108 float max = *max_element(in.begin(), in.end()); | 108 float scale = 1.f; |
109 | 109 |
110 if (n == NormalizeColumns && max == 0.f) { | 110 if (n == ColumnNormalization::Sum1) { |
111 return in; | 111 |
112 } | 112 float sum = 0.f; |
113 | 113 |
114 if (n == NormalizeHybrid && max <= 0.f) { | 114 for (auto v: in) { |
115 return in; | 115 sum += v; |
116 } | 116 } |
117 | |
118 if (sum != 0.f) { | |
119 scale = 1.f / sum; | |
120 } | |
121 } else { | |
122 | |
123 float max = *max_element(in.begin(), in.end()); | |
124 | |
125 if (n == ColumnNormalization::Max1) { | |
126 if (max != 0.f) { | |
127 scale = 1.f / max; | |
128 } | |
129 } else if (n == ColumnNormalization::Hybrid) { | |
130 if (max > 0.f) { | |
131 scale = log10f(max + 1.f) / max; | |
132 } | |
133 } | |
134 } | |
117 | 135 |
118 std::vector<float> out; | 136 std::vector<float> out; |
119 out.reserve(in.size()); | 137 out.reserve(in.size()); |
120 | 138 |
121 float scale; | |
122 if (n == NormalizeHybrid) { | |
123 scale = log10f(max + 1.f) / max; | |
124 } else { | |
125 scale = 1.f / max; | |
126 } | |
127 | |
128 for (auto v: in) { | 139 for (auto v: in) { |
129 out.push_back(v * scale); | 140 out.push_back(v * scale); |
130 } | 141 } |
142 | |
131 return out; | 143 return out; |
132 } | 144 } |
133 | 145 |
134 /** | 146 /** |
135 * Scale the given column using the given gain multiplier. | 147 * Scale the given column using the given gain multiplier. |