-
Notifications
You must be signed in to change notification settings - Fork 1
/
Copy pathTactileValueArray.cpp
180 lines (162 loc) · 4.77 KB
/
TactileValueArray.cpp
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
/* ============================================================
*
* Copyright (C) 2015 by Robert Haschke <rhaschke at techfak dot uni-bielefeld dot de>
*
* This file may be licensed under the terms of the
* GNU Lesser General Public License Version 3 (the "LGPL"),
* or (at your option) any later version.
*
* Software distributed under the License is distributed
* on an ``AS IS'' basis, WITHOUT WARRANTY OF ANY KIND, either
* express or implied. See the LGPL for the specific language
* governing rights and limitations.
*
* You should have received a copy of the LGPL along with this
* program. If not, go to http://www.gnu.org/licenses/lgpl.html
* or write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*
* The development of this software was supported by:
* CITEC, "Cognitive Interaction Technology" Excellence Cluster
* Bielefeld University
*
* ============================================================ */
#include "TactileValueArray.h"
#include <numeric>
namespace tactile {
TactileValueArray::TactileValueArray(size_t n, float min, float max)
{
init(n, min, max);
}
void TactileValueArray::init(size_t n, float min, float max)
{
vSensors.resize(n);
reset(min, max);
}
void TactileValueArray::reset(float min, float max)
{
for (auto &sensor : vSensors)
sensor.init(min, max);
}
TactileValueArray::AccMode TactileValueArray::getMode(const std::string &sName)
{
if (sName == "Sum") return Sum;
if (sName == "SumPositive") return SumPositive;
if (sName == "SumNegative") return SumNegative;
if (sName == "CountPositive") return CountPositive;
if (sName == "CountNegative") return CountNegative;
if (sName == "Min") return Min;
if (sName == "Max") return Max;
return SumPositive; // default fallback
}
std::string TactileValueArray::getModeName(AccMode m)
{
switch (m) {
case Sum: return "Sum";
case SumPositive: return "SumPositive";
case SumNegative: return "SumNegative";
case CountPositive: return "CountPositive";
case CountNegative: return "CountNegative";
case Min: return "Min";
case Max: return "Max";
default: return "";
}
}
TactileValueArray::vector_data TactileValueArray::getValues(TactileValue::Mode mode) const
{
vector_data vReturn(vSensors.size());
getValues(mode, vReturn);
return vReturn;
}
typedef float (*AccumulatorFunction)(const float, const float);
static float Add(float result, float c)
{
return result + c;
}
static float posAdd(float result, float c)
{
if (c > 0)
return result + c;
else
return result;
}
static float negAdd(float result, float c)
{
if (c < 0)
return result + c;
else
return result;
}
static float posCnt(float result, float c)
{
if (c > 0)
return result + 1;
else
return result;
}
static float negCnt(float result, float c)
{
if (c < 0)
return result + 1;
else
return result;
}
static float minFun(float result, float c)
{
return std::min(result, c);
}
static float maxFun(float result, float c)
{
return std::max(result, c);
}
static float INITIAL[] = { 0, 0, 0, 0, 0, FLT_MAX, -FLT_MAX };
static AccumulatorFunction ACCUMULATORS[] = { Add, posAdd, negAdd, posCnt, negCnt, minFun, maxFun };
float TactileValueArray::accumulate(const vector_data &data, AccMode mode, bool bMean)
{
float result = std::accumulate(data.begin(), data.end(), INITIAL[mode], ACCUMULATORS[mode]);
if (bMean && !data.empty()) result /= data.size();
return result;
}
float TactileValueArray::accumulate(TactileValue::Mode mode, AccMode acc_mode, bool bMean)
{
return accumulate([mode](const TactileValue &self) { return self.value(mode); }, acc_mode,
bMean);
}
float TactileValueArray::accumulate(const AccessorFunction &accessor, AccMode mode,
bool bMean) const
{
float result = INITIAL[mode];
AccumulatorFunction acc = ACCUMULATORS[mode];
for (const auto &sensor : vSensors)
result = acc(result, accessor(sensor));
if (bMean && !vSensors.empty()) result /= vSensors.size();
return result;
}
void TactileValueArray::setMeanLambda(float fLambda)
{
for (auto &sensor : vSensors)
sensor.setMeanLambda(fLambda);
}
void TactileValueArray::setRangeLambda(float fLambda)
{
for (auto &sensor : vSensors)
sensor.setRangeLambda(fLambda);
}
void TactileValueArray::setReleaseDecay(float fDecay)
{
for (auto &sensor : vSensors)
sensor.setReleaseDecay(fDecay);
}
float TactileValueArray::getMeanLambda() const
{
return accumulate([](const TactileValue &self) { return self.getMeanLambda(); }, Sum, true);
}
float TactileValueArray::getRangeLambda() const
{
return accumulate([](const TactileValue &self) { return self.getRangeLambda(); }, Sum, true);
}
float TactileValueArray::getReleaseDecay() const
{
return accumulate([](const TactileValue &self) { return self.getReleaseDecay(); }, Sum, true);
}
} // namespace tactile