题目链接:Link
Problem
Solution
首先我们可以发现:当安排好一个对应的移动方案后,每个士兵的移动的最短距离必然是一个曼哈顿距离。
设从左到右依次对应的士兵分别位于 $ (x_1,y_1),(x_2,y_2),...,(x_n,y_n) $ ,则答案为 $ \sum_{i=1}^n { \left| y-y_i \right| } + \sum_{i=1}^n { \left| x+i-1-x_i \right| } $
于是我们可以发现,y轴上的答案和x轴上的答案可以分开统计。不难得出如下贪心策略:将\(x_i\)从小到大排序。然后x轴上的答案就可以转换成$ \sum_{i=1}^n { \left| x-(x_i+1-i) \right| } $。
然后这个问题就被转换成了2个货仓选址问题。
Code
#include
#include
using std::sort;
typedef long long LL;
const int maxn=10005;
int n,x[maxn],y[maxn];
inline LL abs(const LL &x) { return x>0?x:-x; }
int main()
{
#ifdef local
freopen("pro.in","r",stdin);
#endif
scanf("%d",&n);
for(int i=1;i<=n;i++) scanf("%d %d",&x[i],&y[i]);
sort(x+1,x+n+1);
for(int i=1;i<=n;i++) x[i]+=1-i;
sort(x+1,x+n+1); sort(y+1,y+n+1);
LL res=0,tx=x[(n+1)/2],ty=y[(n+1)/2];
for(int i=1;i<=n;i++) res+=abs(x[i]-tx)+abs(y[i]-ty);
printf("%lld\n",res);
return 0;
}