牛为什么过马路
尽管科学界已经深入探究了鸡为什么过马路这一问题,令人惊讶的是,关于牛过马路的的研究文献却很少发表。
农夫约翰很清楚这一问题的重要性,当一所当地的大学联系他,要求他协助进行一项关于奶牛为什么要过马路的科学研究时,他非常激动并热心的表示愿意帮忙。
作为研究的一部分,约翰被要求记录下他的每头奶牛穿过马路的次数。
他仔细记录了奶牛的位置数据,在一天时间里,他进行了 NN 次观察,每次观察都会记录一头牛的 ID (约翰共有 1010 头牛,ID 从 11 到 1010)以及牛在路的哪一边。
根据约翰记录的数据,请帮助他计算可以确定的奶牛穿过马路的次数。
当连续观察到一头奶牛在道路的两侧时,就可以确定它穿过了一次马路。
输入格式
第一行包含整数 NN。
接下来 NN 行,用来描述观察结果,首先包含一个整数表示观察奶牛的 ID,然后包含一个整数 00 或 11,00 表示它在马路一边,11 表示它在马路另一边。
输出格式
输出可以确认发生的穿过马路的次数。
数据范围
1≤N≤1001≤N≤100,
输入样例:样例解释
在此样例中,33 号奶牛穿过马路两次,先 1→01→0,然后 0→10→1。
44 号奶牛穿过马路一次 1→01→0。
22 号和 66 号奶牛没有穿过马路。
难度:简单 |
时/空限制:1s / 64MB |
总通过数:2294 |
总尝试数:3232 |
来源:USACO 2017 February Contest Bronze |
算法标签 |
一道大水题!
两种解法
1.先初始设为每头奶牛的位置是-1,也就是从未被标记过。
然后对于每一次操作:
1. 如果当前奶牛的位置是-1(没被标记过)或者是当前奶牛与给出的位置相同(没动),那么就把当前奶牛位置标记一下。
2. 如果不符合第一条,说明过了一次马路,那么就需要标记位置,并且累加答案。
代码实现也不怎么困难,很简洁
#include<bits/stdc++.h>
using namespace std;
int a[20],ans;
int main() {
int t;
scanf("%d",&t);
memset(a,-1,sizeof a);
while(t--){
int x,opt;
cin>>x>>opt;
if (a[x]==-1||a[x]==opt){
a[x]=opt;
}else{
a[x]=opt;
ans++;
}
}
printf("%d\n", ans);
}
2.思路
用一个哈希表unordered_map<int,pair<int,int> >
来存取当前牛的状态,键值为牛的ID号,
pair队的first存取0(马路一边),second存取1(马路另一边);
用k来记录牛出现的最后一次位置;
#include <iostream>
#include <cstring>
#include <unordered_map>
#include <algorithm>
using namespace std;
int main()
{
int ans = 0,a,b,n,k;
unordered_map<int,pair<int,int> > ma1;
cin>>n;
while(n--){
cin>>a>>b;
if(b == 1 && ma1[a].second == 0)
ma1[a].second++,k = 1;
else if(b == 0 && ma1[a].first == 0)
ma1[a].first++,k = 0;
if(ma1[a].first > 0 && ma1[a].second > 0 && k == 1){
ans++;
ma1[a].first = 0;
}
else if(ma1[a].first > 0 && ma1[a].second > 0 && k == 0){
ans++;
ma1[a].second = 0;
}
}
cout<<ans;
return 0;
}