我试图解决的问题是:我有一个浮点数容器(双向量向量):
std::vector<std::vector<double>> dv { {0.0, 0.0}, {1.0, 0.0}, {0.0, 1.0}, {1.0, 1.0} };
然后,假设我有一个新点(双向量):
std::vector<double> v1 {0.0001, 1.0};
我想检查一个点v1是否在容器dv中,基于一些公差。两个向量之间的距离被计算为欧几里得距离。
我已经查看了相关的问题和答案: 并尝试使用
std :: find_if()
,但没有成功,因为它仅接受一元谓词。目前,我想到了一个临时解决方案。首先,我创建了一个通用函数来查找两个向量之间的欧几里得距离:
template <typename InputIt1, typename InputIt2>
double EuclideanDistance(InputIt1 beg1, InputIt1 end1, InputIt2 beg2) {
double val = 0.0;
while (beg1 != end1) {
double dist = (*beg1++) - (*beg2++);
val += dist*dist;
}
return val > 0.0? sqrt(val) : 0.0;
}
第二步,我创建了
check_if
函数,根据公差(Epsilon)检查一个元素是否存在于容器中。template <typename Container, typename Element>
bool check_if(const Container& c, const Element& el,
const double Epsilon = 0.001) {
auto pos = c.begin();
for (; pos != c.end(); ++pos) {
if (EuclideanDistance(pos->begin(), pos->end(), el.begin()) < Epsilon) {
return true;
}
}
return false;
}
然后我可以在这样的上下文中使用我的代码:
// Check if container contains v1 using check_if()
if (check_if(dv, v1)) {
std::cout << "Using check_if() - Container contains v1\n";
}
所以我的问题如下:
- 是否有内部STL算法来实现相同的目标?如果没有,我该如何改进我的代码?例如,我不确定如何在
check_in()
中使用任何距离函数而不是EuclideanDistance()
? - 我想知道AshleysBrain建议(https://dev59.com/-3A75IYBdhLWcg3wJFcL#3451045)使用
std::set
而不是std::vector
,对于一个包含浮点数的容器是否会有任何区别?
std::pair<double>
或std::array<double,2>
中 - 对于固定大小的数据,std::vector
是过度杀伤,此外您需要验证它始终具有2个元素。 - SlavaEpsilon
的 lambda,并将该 lambda 传递给find_if
。 - Praetorianstd::find_if
试一次,因为我看不出任何它不能工作的原因。 - juanchopanzaEuclideanDistance
接受一个包含double
的容器的迭代器。如果OP使用了std::vector<Point>
,那么代码会更清晰,这样就可以写成EuclideanDistance(pt, expected_pt) < Epsilon
。 - Jarod42Point
,那么v1
将成为该类型的一个对象,您也不需要使用v1.begin()
。 - Slava