1083: False coin

TZOJ 1083: False coin

思路和1080: Counterfeit Dollar差不多,第一次看到这题就想到用枚举的方法枚举每一枚硬币去跑一遍记录,最后一定要注意一些细节。
首先假设硬币i为假币,并且当它为轻的硬币;则:
1、当记录为左边<右边时,因为它是轻的硬币,所以在左边去寻找这枚硬币,如果找到了那么跑下一条记录,否则枚举下一枚硬币。
2、当记录为左边>右边,同理得在右边寻找硬币…
3、当记录为左边=右边时,寻找左边和右边是否存在这枚硬币,如果存在则枚举下一枚硬币。
当其中一枚跑完所有记录时,用res[i]++记录第i枚硬币满足多少次。
同理当假币为重的情况和上面一样。
最后跑一边res[]数组,寻找是否只有一枚硬币满足条件输出这枚硬币,否则有超过1枚硬币满足记录或者都不满足记录则输出0;

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<math.h>
#include<algorithm>
#include<iostream>
//#define ll long long int
using namespace std;
int N,K;
int l[100][100];
int r[100][100];
int num[1000];
int res[1000];
char f[1000];
int cnt=0;
void istrue(int x,int t){        //t为1表示这枚硬币是重的,为0表示轻的
    int flag;
    for(int i=0;i<K;i++){        //遍历每个记录
        flag=0; //每次跑一条记录都要重新标记
        int *ll=l[i];            //获取左边的信息
        int *rr=r[i];			//获取右边的信息
        if(f[i]=='<'){
            if(t){                           //遍历该硬币是否满足条件
                for(int j=0;j<num[i];j++){
                    if(rr[j]==x){
                        flag=1;
                    }
                }
                if(flag==0)return;
            }else{
                for(int j=0;j<num[i];j++){
                    if(ll[j]==x){
                        flag=1;
                    }
                }
                if(flag==0)return;
            }
        }
        if(f[i]=='>'){
            if(t){
                for(int j=0;j<num[i];j++){
                    if(ll[j]==x){
                        flag=1;
                    }
                }
                if(flag==0)return;
            }else{
                for(int j=0;j<num[i];j++){
                    if(rr[j]==x){
                        flag=1;
                    }
                }
                if(flag==0)return;
            }
        }
        if(f[i]=='='){
            for(int j=0;j<num[i];j++){
                if(ll[j]==x){
                    
                    return;
                }
            }
            for(int j=0;j<num[i];j++){
                 if(rr[j]==x){
                    
                    return;
                }
            }
            flag=1;
        }
    }
    if(flag){   //跑完K条记录如果满足条件,将该硬币放入数组
        res[x]++;
        return;
    }
}
int main(int argc, char const *argv[])
{
    memset(res,0,sizeof(res));
    scanf("%d %d",&N,&K);
    int count;
    for(int i=0;i<K;i++){
        scanf("%d",&count);
        num[i]=count;
        for(int j=0;j<count;j++)scanf("%d",&l[i][j]);
        for(int k=0;k<count;k++)scanf("%d",&r[i][k]);
        getchar();
        scanf("%c",&f[i]);
    }
    for(int i=1;i<=N;i++){
        istrue(i,1);               //枚举每个硬币是轻
        istrue(i,0);			//不知道硬币是轻还是重所有都要枚举
    }
    int kk=0;
    for(int i=1;i<=100;i++){  //寻找满足条件的硬币个数
        if(res[i]!=0){
            cnt++;
            kk=i;
        }
    }
    if(N==2){    //当然2枚硬币一定输出0
        printf("0\n");
    }else if(cnt==1)printf("%d\n",kk);
    else printf("0\n");
    return 0;
}

这题解法不唯一我这方法肯定不是最好的

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值