2019 GUDT RC 2 Problem B(题解)
作者:互联网
原题
题目大意
这道题大概是讲有n头牛,第i只牛距离谷仓xi米,x是互不相同的,然后农夫要训练这些牛的传球技能.农夫开始时会发球给牛,牛接到球后会把球传给离它最近的牛,如果它左右两边的牛与它的距离相同,它会把球传给左边的那只.要求给出农夫至少需要发几个球,才能保证每只牛都能碰到球.就样例来说,牛位置排序后是1 3 4 7 11,农夫刚开始只需要把一个球传给1,一个球传给11就可以让每只牛都碰到球了.ps:样例的两个球最后都会在3和4之间不断传来传去.
题目分析
这道题最关键的搞懂这些牛传球的性质,仔细想想会发现球传到了一头牛时,其实这头牛传球的方向是固定的,那么只需要记录每头牛传球的方向,在扫一下就可以找到答案了.首先先把牛的位置按从小到大排序,然后创一个数组来记录每头牛的传球方向(第一头牛肯定会往右传,最后一头牛肯定往左传),设一个ans变量来记录得用多少个球,再扫一遍这个数组,扫的过程中根据情况给ans++,最后输出ans即可.(具体什么情况ans++我会在代码中注释)
代码
1 #include <cstdio> 2 #include <cmath> 3 #include <iostream> 4 #include <cstring> 5 #include <algorithm> 6 #include <vector> 7 #include <string> 8 #include <utility> 9 #include <queue> 10 #include <stack> 11 const int INF=0x3f3f3f3f; 12 using namespace std; 13 14 int poi[101]; //记录位置 15 int d[101]; //记录方向,其中1代表向右,0代表向左 16 int n; 17 18 int main() 19 { 20 cin>>n; 21 for(int i=0;i<n;i++) 22 cin>>poi[i]; 23 sort(poi,poi+n); 24 for(int i=0;i<n-1;i++) //记录方向,由于最后一头牛肯定向左所以,i到n-2就可以结束 25 { 26 if(!i) d[i]=1; //第一头牛肯定向右 27 else 28 { 29 if(poi[i+1]-poi[i]<poi[i]-poi[i-1]) d[i]=1; //比较距离决定向左还是向右 30 } 31 } 32 int ans=0; 33 int i=0; 34 while(i<n-1) //下面会涉及到i+1,所以要另i<n-1 35 { 36 if(d[i+1]==d[i]) i++; //如果该牛方向与下头牛方向一致,则球可以继续传. 37 else if(d[i+1]&&!d[i]) ans++,i++; //如果该牛往左传,而下头牛往右传,则球传到i头牛这里将被中断,下面需要一个新球. 38 //如果该牛往右传且下头牛往左传,情况会比较复杂,需要检测i-1头牛的方向 39 //情况1:如果是往右,那么该球必定会在i+1处中断,也就是说i+2开始需要一个新球; 40 //情况2:如果是往左,则球不会中断,可以继续i++ 41 else 42 { 43 if(i-1>=0&&d[i-1]==d[i]) ans++,i+=2; //这里要注意i-1>=0,i-1<0的属于上述情况2 44 else i++; 45 } 46 47 } 48 if(i==n-1) ans++; //这里不能漏,否则会导致最后一次没有记录,会让ans-1. 49 50 cout<<ans<<endl; 51 return 0; 52 }
标签:传球,头牛,int,题解,poi,ans,Problem,include,GUDT 来源: https://www.cnblogs.com/VBEL/p/10403016.html