feat: pd_signal: resample, linspace
This commit is contained in:
@@ -17,7 +17,7 @@ TEST(SignalTest, interp_t1) {
|
|||||||
// 5.99494949495 = (5.5-5.01)/0.99*(7-5.01)+5.01
|
// 5.99494949495 = (5.5-5.01)/0.99*(7-5.01)+5.01
|
||||||
|
|
||||||
std::vector<double> y;
|
std::vector<double> y;
|
||||||
interp(x, xp, fp, y);
|
interp(y, x, xp, fp);
|
||||||
|
|
||||||
// assert y == y_e, nb. upto 5 digits
|
// assert y == y_e, nb. upto 5 digits
|
||||||
double abs_err = 1e-5;
|
double abs_err = 1e-5;
|
||||||
@@ -25,3 +25,13 @@ TEST(SignalTest, interp_t1) {
|
|||||||
ASSERT_NEAR(y_e[i], y[i], abs_err + 1e-9 * i);
|
ASSERT_NEAR(y_e[i], y[i], abs_err + 1e-9 * i);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TEST(SignalTest, ranges) {
|
||||||
|
const double abs_error = 1e-5;
|
||||||
|
std::vector<double> i;
|
||||||
|
size_t N = 3;
|
||||||
|
linspace(i, 0, (int) (N-1), (int) N, false);
|
||||||
|
ASSERT_NEAR(0.0, i[0], abs_error);
|
||||||
|
ASSERT_NEAR(1.0, i[1], abs_error);
|
||||||
|
ASSERT_NEAR(2.0, i[2], abs_error);
|
||||||
|
}
|
||||||
|
|||||||
@@ -8,11 +8,20 @@
|
|||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
namespace pd_signal {
|
namespace pd_signal {
|
||||||
|
/** `num` evenly spaced numbers over interval [start,stop] */
|
||||||
|
void linspace(std::vector<double>& data, double start, double stop, int num);
|
||||||
|
/** `num` evenly spaced numbers over interval [start,stop] with endpoint=true or [start,stop) with endpoint=false */
|
||||||
|
void linspace(std::vector<double>& data, double start, double stop, int num, bool endpoint);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Evaluate at points x the function given by the samples fp[xp[n]].
|
* Evaluate at points x the function given by the samples fp[xp[n]].
|
||||||
* Returned in y.
|
* Returned in y.
|
||||||
*/
|
*/
|
||||||
void interp(std::vector<double>& x, std::vector<double>& xp, std::vector<double>& fp, std::vector<double>& y);
|
void interp(std::vector<double>& y, std::vector<double>& x, std::vector<double>& xp, std::vector<double>& fp);
|
||||||
|
|
||||||
|
/** resample to BEAT_LEN */
|
||||||
|
void resample(std::vector<double> &out, std::vector<double> x, int beat_len);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif //PASADASUPERPROJECT_SIGNAL_H
|
#endif //PASADASUPERPROJECT_SIGNAL_H
|
||||||
@@ -23,8 +23,28 @@ static int binarySearch(std::vector<double>& data, double x) {
|
|||||||
return -(insertion_point) - 1; // no element found directly
|
return -(insertion_point) - 1; // no element found directly
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void linspace(std::vector<double>& data, double start, double stop, int num) {
|
||||||
|
linspace(data, start, stop, num, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
// `num` evenly spaced numbers over interval [start,stop] with endpoint=true or [start,stop) with endpoint=false
|
||||||
|
void linspace(std::vector<double>& data, double start, double stop, int num, bool endpoint) {
|
||||||
|
if(num < 0) throw std::invalid_argument("num must be >= 0");
|
||||||
|
|
||||||
|
int end = endpoint ? num : (num-1);
|
||||||
|
double step = (stop - start) / (double) end;
|
||||||
|
|
||||||
|
double d = start;
|
||||||
|
data.resize(num);
|
||||||
|
|
||||||
|
for(int i = 0; i < num; i++) {
|
||||||
|
data[i] = d;
|
||||||
|
d += step;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
// Evaluate at points x the function given by the samples fp[xp[n]].
|
// Evaluate at points x the function given by the samples fp[xp[n]].
|
||||||
void interp(std::vector<double>& x, std::vector<double>& xp, std::vector<double>& fp, std::vector<double>& y) {
|
void interp(std::vector<double>& y, std::vector<double>& x, std::vector<double>& xp, std::vector<double>& fp) {
|
||||||
if (xp.size() != fp.size()) throw std::invalid_argument("xp.size() != fp.size()");
|
if (xp.size() != fp.size()) throw std::invalid_argument("xp.size() != fp.size()");
|
||||||
size_t N = xp.size();
|
size_t N = xp.size();
|
||||||
size_t M = x.size();
|
size_t M = x.size();
|
||||||
@@ -65,4 +85,13 @@ void interp(std::vector<double>& x, std::vector<double>& xp, std::vector<double>
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// resample to BEAT_LEN
|
||||||
|
void resample(std::vector<double> &out, std::vector<double> x, int beat_len) {
|
||||||
|
std::vector<double> t;
|
||||||
|
std::vector<double> i;
|
||||||
|
linspace(t, 0, (double) x.size(), beat_len, false);
|
||||||
|
linspace(i, 0, (int) (x.size()-1), (int) x.size(), false);
|
||||||
|
interp(out, t, i, x);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user