11. 排兵布阵

Description

总所周知,韩信是一位神勇的军事家。某日夜幕,敌方突然来袭,韩信作为塞外将帅吹响紧急的号角。各个帐内的士兵听见号角立即集合,站成一排,排成连续的一队。但是士兵太多了,如果让他们集合耗费太多精力就没有办法打好接下来的胜仗,因此韩信希望选择一个最优的方案使得所有士兵从帐内移动到将要站队的位置的曼哈顿距离和最小

解题思路:

题要求所有人站到一列,而x与y可以独立考虑。先考虑简单的y坐标,不妨设在y点时走的步数最少,则Sy=|Y0-y|+|Y1-y|+|Y2-y+ ……+|Yn-1-y|根据绝对值的性质我们得y取在Y0~Yn-1这些数的中位数时Sy最小

再看x坐标,不妨设第一个人站在x时总步数最少,则剩下人根据Xi的大小依次往后站,不可能存在Xi<Xj但i站在j后面的情况,否则交换得到更优解。

因此先对x排序,

计算Sx=|X0-x|+|X1- (x+1) |+|X2-(x+2)|+ …… +|Xn-1-(x+(n-1))|
经过变形Sx=|X0-x|+|(X1-1)-x|+|(X2-2)-x|+ …… …… +|(Xn-1-(n-1))-x|

故同理对Xi-i进行排序,取中位数的最小值。

再进行遍历将所需步数加上

代码:

#include<iostream>
#include<algorithm>
using namespace std;
int x[100010];
int y[100010];
int main(){
	int n;
	cin>>n;
	for(int i=0;i<n;i++){
		cin>>x[i];
		cin>>y[i];
	}
	sort(x,x+n);
	for(int i=0;i<n;i++)x[i]-=i;
	sort(x,x+n);
	sort(y,y+n);
	long long ans=0;
	for(int i=0;i<n;i++){
		ans+=abs(x[i]-x[n/2]);
		ans+=abs(y[i]-y[n/2]);
	}
	cout<<ans<<endl;
	
} 

  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值