我想要获得一个未排序的,可变长度的特征c++ vectorXf对象的weighted_median。似乎我可以使用boost的统计累加器库中的boost weighted_median函数来高效地完成这项工作。
本质上,我正在尝试做一些与here所做的非常相似的事情。我不确定boost的累加器是不是这个任务的正确框架(如果不是,请建议!),但我还没有找到另一个O(n)加权中值的货架实现。
在这一点上,我的问题是,是否有一种方法可以用更优雅的构造替换下面的"for(int i=0;i<100;i++)“循环?
另外,我见过this这样的问题,但不清楚如何将那里的答案转化为可操作的解决方案。
#include <Eigen/Dense>
#include <iostream>
#include <boost/accumulators/accumulators.hpp>
#include <boost/accumulators/statistics/stats.hpp>
#include <boost/accumulators/statistics/median.hpp>
#include <boost/accumulators/statistics/weighted_median.hpp>
using namespace boost::accumulators;
using namespace Eigen;
int main(){
accumulator_set<float, stats<tag::median > > acc1;
accumulator_set<float, stats<tag::median >,int> acc2;
VectorXi rw=VectorXi::Random(100);
VectorXf rn=VectorXf::Random(100);
rw=rw.cwiseAbs();
for(int i=0;i<100;i++){
acc1(rn(i));
acc2(rn(i),weight=rw(i));
}
std::cout << " Median: " << median(acc1) << std::endl;
std::cout << "Weighted Median: " << median(acc2) << std::endl;
return 0;
}发布于 2012-06-22 06:54:37
您要做的是使用boost累加器在某种容器中累加值。您将注意到,即使将std::vector<float>传递给累加器也不起作用。累加器根本就不是这样使用的。当然,您可以使用累加器来累加向量值或矩阵值,但这不是您在这里要做的。
您可以使用std::for_each来摆脱显式循环,仅此而已:
// median
using boost::bind;
using boost::ref;
std::for_each(rn.data(), rn.data()+rn.rows(), bind<void>( ref(acc1), _1 ) );在最新版本的Eigen3中,您链接到的question不再相关。这里给出的代码运行良好,并产生正确的结果。
https://stackoverflow.com/questions/11147761
复制相似问题