首先,蚂蚁A可能坠落,也可能不坠落。
其中,不坠落的情况有两种,即A两边的蚂蚁,右边的蚂蚁向右边走,左边的蚂蚁向左边走,则这一类的蚂蚁都不会与A相撞;另一种情况就是存在右边的蚂蚁向左边走,左边的蚂蚁向右边走,但是,这两种蚂蚁的数量是相等的,这样也不会坠落。
而A坠落的情况,归根结底就是两种,即向右边坠落,或者向左边坠落。这里我们可以先做一下预处理,首先将蚂蚁根据其位置进行排序,对于左边的蚂蚁向左边走,右边的蚂蚁向右边走这种情况,我们可以忽略,然后左边的蚂蚁向右边走归为left数组中,右边的蚂蚁向左边走归为right数组中,left的蚂蚁有n,right的蚂蚁有m,则
当n>m时,A向右边坠落,且可以简化认为A是与left中第n-m个蚂蚁(left数组从后往前数)相撞,然后开始向右边移动,并最终移动到100坠落,因此时间为100减去left中第n-m个蚂蚁的位置。
当n<m时,A向左边坠落,且可以简化认为A是与right中第m-n个蚂蚁相撞,然后开始向左边移动,并最终移动到0坠落,因此时间为right中第m-n个蚂蚁的位置。
由此得到如下代码:
#include <iostream>
#include <cstdio>
#include <vector>
#include <algorithm>
using namespace std;
const int MAXN = 100 + 10;
struct Ant {
int position;
int direction;
};
bool Compare(Ant x, Ant y) {
return x.position < y.position;
}
Ant ants[MAXN];
int main() {
int n ;
while(scanf("%d",&n) != EOF) {
vector<int> left;
vector<int> right;
int position;
for (int i = 0; i < n; ++i) {
scanf("%d%d", &ants[i].position, &ants[i].direction);
if (ants[i].direction == 0) { //确定A的位置
position = ants[i].position;
}
}
sort(ants, ants + n, Compare);
for (int i = 0; i < n; ++i) { //只找出那些会与A相撞的
if (ants[i].position < position && ants[i].direction == 1) {
left.push_back(ants[i].position);
}
if (ants[i].position > position && ants[i].direction == -1) {
right.push_back(ants[i].position);
}
}
if (left.size() == right.size()) {
//左右数量相等,则不会坠落
printf("Cannot fall!\n");
} else if (left.size() < right.size()) {
//右边数量大于左边,则会向左边坠落,时间为两边数量消完之后
//的右边第一个的位置与0之间的距离
printf("%d\n", right[left.size()]);
} else {
//左边数量大于右边,则会向右边坠落,时间为两边数量消完之后
//的左边最后一个的位置与100之间的距离,因为左边的元素是从左往右
//排列,但是相消的时候,左边元素是从后往前消去
printf("%d\n", 100 - left[left.size() - right.size() - 1]);
}
}
return 0 ;
}