题目:
设有n个互不相同的元素x1,x2,…xk,每个元素xi带有一个权值wi,且∑ni=1wi=1。若元素xk满足∑xi<xkwi≤12且∑xi>xkwi≤12,则称元素xk为x1,x2,…,xn的带权中位数。请编写一个算法,能够在最坏情况下用O(n)时间找出n个元素的带权中位数。
例如:
10
719 449 446 981 431 993 919 389 549 453
0.01757775 0.02028202 0.16863048 0.07320842 0.16283562 0.16167665 0.14970060 0.04095036 0.12806645 0.07707166
答案:
549
本题我们采用递归的方式进行求解,相关代码如下所示:
#include<iostream>
#include<vector>
using namespace std;
void Find(vector<int>num, vector<double>w,int index);
int main() {
int Num;
cout << "请输入一个整数:" << endl;
cin >> Num;
vector<int>num;
cout << "请输入" << Num << "个数:" << endl;
for (int i = 0; i < Num; i++) {
int temp;
cin >> temp;
num.push_back(temp);
}
cout << "请输入" << Num << "个数的对应权重:" << endl;
vector<double>w;
for (int i = 0; i < Num; i++) {
double temp;
cin >> temp;
w.push_back(temp);
}
Find(num, w,0);//递归调用函数查找中位数
return 0;
}
void Find(vector<int>num, vector<double>w,int index) {
if (index == num.size()) {
return;//index到达底部,但是仍然没有寻找到相关结果
}
double w1 = 0;//大于的权重和
for (int i = 0; i < num.size(); i++) {
if (num[i] > num[index]) {
w1+= w[i];
}
}
double w2 = 0;//小于的权重的和
for (int i = 0; i < num.size(); i++) {
if (num[i] < num[index]) {
w2+= w[i];
}
}
if (w1 <=0.5 && w2 <=0.5) {
cout <<"中位数为:"<< num[index] << endl;
}
else {
Find(num, w, index + 1);//继续递归寻找符合条件的值
}
}
运行结果如图:
xjtuer算法儿拿走不谢!