泛型模板函数始终返回整数值

generic-template function always returning integer values

本文关键字:返回 整数 函数 泛型      更新时间:2023-10-16

我正在编写下面的线性插值函数,该函数是通用的,但当前结果不是。

该函数在两个给定边界点之间查找所需数量的等距点线性。所需数量和边界都作为参数给出。作为返回,返回线性插值的向量。

我担心返回类型的问题,它总是显示为整数,即使它应该有一些尾数,例如:

vec = interpolatePoints(5, 1, 4);
for (auto val : vec) std::cout << val << std::endl; // prints 4, 3, 2, 1

但它应该打印:4.2、3.4、2.6、1.8

我应该怎么做才能使它泛型并具有正确的返回值?

法典:

template <class T>
std::vector<T> interpolatePoints(T lower_limit, T high_limit, const unsigned int quantity) {
auto step = ((high_limit - lower_limit)/(double)(quantity+1));
std::vector<T> interpolated_points;
for(unsigned int i = 1; i <= quantity; i++) {
interpolated_points.push_back((std::min(lower_limit, high_limit) + (step*i)));
}
return interpolated_points;
}

经过一些简化后,该函数可能如下所示:

template<typename T, typename N, typename R = std::common_type_t<double, T>>
std::vector<R> interpolate(T lo_limit, T hi_limit, N n) {
const auto lo = static_cast<R>(lo_limit);
const auto hi = static_cast<R>(hi_limit);
const auto step = (hi - lo) / (n + 1);
std::vector<R> pts(n);
const auto gen = [=, i = N{0}]() mutable { return lo + step * ++i; };
std::generate(pts.begin(), pts.end(), gen);
return pts;
}

返回std::vector中的元素类型为std::common_type_t<double, T>。对于int,它是double,对于long double,它是long doubledouble看起来像一个合理的默认类型。

你只需要传递正确的类型:

auto vec = interpolatePoints(5., 1., 4); // T deduced as double

演示

在 C++20 中,您可以使用std::lerp来拥有:

template <class T>
std::vector<T> interpolatePoints(T lower_limit, T high_limit, const unsigned int quantity) {
auto step = 1 / (quantity + 1.);
std::vector<T> interpolated_points;
for(unsigned int i = 1; i <= quantity; i++) {
interpolated_points.push_back(std::lerp(lower_limit, high_limit, step * i));
}
return interpolated_points;
}

演示