1110 距離之和最小 v3
基準時間限制:1 秒 空間限制:131072 kb 分值: 40
難度:4級演算法題
x軸上有n個點,每個點除了包括乙個位置資料x[i],還包括乙個權值w[i]。點p到點p[i]的帶權距離 = 實際距離 * p[i]的權值。求x軸上一點使它到這n個點的帶權距離之和最小,輸出這個最小的帶權距離之和。
input
第1行:點的數量n。(2 <= n <= 10000)output第2 - n + 1行:每行2個數,中間用空格分隔,分別是點的位置及權值。(-10^5 <= x[i] <= 10^5,1 <= w[i] <= 10^5)
輸出最小的帶權距離之和。input示例
5output示例-1 1
-3 1
0 17 1
9 1
20思路:列方程 || 拆分
一,列方程:將所有點按下標排序,對於最小值ans所取的點一定在所有相鄰的兩點之間,可從右到左遍歷所有相鄰兩點,對於點 d[i]的下標d[i].x和權值d[i].w,開始 ans所取的點在最右點,對於 方程ans=ax+b, a=所有點的權值和, b=所有點的權值*下標和, 那麼遍歷到 d[i]和d[i+1]點之間最左端 l=d[i].x ,最右端 r=d[i+1].x ,則 a-=2*d[i+1].w; b-=2*d[i+1].w*d[i+1].x; 那麼對於 ans=ax+b, 首先由題目可以肯定 ans>0,那麼只要對 a分情況討論即可
a>0, 則 x=l 時 ans最小 為 a*l+b;
a<0, 則 x=r 時 ans最小 為 a*r+b;
二,拆分: 對於下標為x,權值為w的點可以將其 拆分成 w個 下標為x,權值為1的點,這樣就可利用中位數來求得最小值
code 1 :
//列方程組
#include#includeusing namespace std;
typedef long long ll;
struct node
sort(d,d+n);
ll ans=1e15;
int l,r;
for(int i=n-2;i>=0;--i)
else ans=min(ans,a*r+b);
} cout
//拆分
#include#includeusing namespace std;
typedef long long ll;
struct node{
int x;
ll w;
bool operator
return x>n;
for(int i=0;i>d[i].x>>d[i].w;
sort(d,d+n);
ll ans=0,t;
int l=0,r=n-1;
while(l
51 Nod 1110距離之和最小V3
1 秒131,072 kb 40 分 4 級題 x軸上有n個點,每個點除了包括乙個位置資料x i 還包括乙個權值w i 點p到點p i 的帶權距離 實際距離 p i 的權值。求x軸上一點使它到這n個點的帶權距離之和最小,輸出這個最小的帶權距離之和。收起第1行 點的數量n。2 n 10000 第2 n...
51Nod 1110 距離之和最小 V3 三分
分類 三分 51nod 1110 距離之和最小 v3 x軸上有n個點,每個點除了包括乙個位置資料x i 還包括乙個權值w i 點p到點p i 的帶權距離 實際距離 p i 的權值。求x軸上一點使它到這n個點的帶權距離之和最小,輸出這個最小的帶權距離之和。input 第1行 點的數量n。2 n 100...
51nod 1096 距離之和最小
1096 距離之和最小 基準時間限制 1 秒 空間限制 131072 kb 分值 20 難度 3級演算法題 x軸上有n個點,求x軸上一點使它到這n個點的距離之和最小,輸出這個最小的距離之和。input 第1行 點的數量n。2 n 10000 第2 n 1行 點的位置。10 9 p i 10 9 ou...