假币问题 问题描述 利有 12 枚银币。其中有 11 枚真币和 1 枚假币。假币看起来和真币没有区别,但是重量不同。但赛利不知道假币比真币轻还是重。于是他向朋友借了一架天平。朋友希望赛利称三次 就能找出假币并且确定假币是轻是重。例如:如果赛利用天平称两枚硬币,发现天平平衡,说明两枚都是真的。如果赛利用一枚真币与另一枚银币比较,发现它比真币轻或重,说明它是假币。经过精心安排每次的称量,赛利保证在称三次后确定假币。
Input:
输入有三行,每行表示一次称量的结果。赛利事先将银币标号为 A-L。每次称量的结果用三个以空格隔开的字符串表示: 天平左边放置的硬币 天平右边放置的硬币 平衡状态。 其中平衡状态用,up, down, 或 even表示, 分别为右端高、右端低和平衡。天平左右的硬币数总是相等的。
Output:
输出哪一个标号的银币是假币,并说明它比真币轻还是重(heavy or light)。 Sample Input 1 ABCD EFGH even ABCI EFJK up ABIJ EFGH even Sample Output K is the counterfeit coin and it is light
思路 核心(枚举)
首先,每一个标号的银币都可能是假币,所以需要对每个银币都进行分析,其次题目没说假币是更重还是更轻,所以又要再分俩种情况。
具体实现则是,读入三次称重结果,对每一枚银币,分更重和更轻俩种情况讨论,看哪种符合读入的结果。
比如这次的输入,ABCD EFGH even,说明假币不可能在这8枚银币里,但程序仍会对A-H进行分析,再分析I,先假设I更轻,第二个就不满足了,因为up表示右边高,I排除,再分析J,同样 先假设J更轻,第三个就不满足了,最后剩一个K,先假设更轻,刚好满足第二个条件。
所以程序需要实现的就是这三个过程,遍历A-L,假币更重比较一次,假币更轻比较一次。
用到了strchr(const char str[], int c),如果在字符串 str 中找到字符 c,则函数返回指向该字符的指针,如果未找到该字符则返回 NULL。假币在天平上肯定出现不平衡,所以找出事先假设好的假币在哪边,再判断。
代码 #define _NO_SECURE_NO_WARNINGS #include <stdio.h> #include <string.h> char left[3 ][7 ];char right[3 ][7 ];char result[3 ][7 ];bool isCounterfeitCoin (char iCoin, bool isLight) ;int main () { int t; scanf ("%d" , &t); while (t--) { for (int i = 0 ; i < 3 ; i++) scanf ("%s %s %s" , &left[i], &right[i], &result[i]); for (char iCoin = 'A' ; iCoin <= 'L' ; iCoin++) if (isCounterfeitCoin(iCoin, true )) { printf ("%c is the counterfeit coin and it is light.\n" , iCoin); break ; } else if (isCounterfeitCoin(iCoin, false )) { printf ("%c is the counterfeit coin and it is heavy.\n" , iCoin); break ; } } return 0 ; } bool isCounterfeitCoin (char iCoin, bool isLight) { for (int i = 0 ; i < 3 ; ++i) { char * pleft; char * pright; if (isLight) { pleft = left[i]; pright = right[i]; } else { pleft = right[i]; pright = left[i]; } switch (result[i][0 ]) { case 'u' : if (strchr (pright, iCoin) == NULL ) return false ; break ; case 'e' : if (strchr (pleft, iCoin) || strchr (pright, iCoin)) return false ; break ; case 'd' : if (strchr (pleft, iCoin) == NULL ) return false ; break ; } } return true ; }
跳绳为题 (参考自:) 题目描述 朋友玩跳绳比赛,要计算在一分钟内跳了多少下.假设每秒钟跳一下,如果中途失败了,则要 花三秒钟后才能开始重跳.一般小朋友跳绳一分钟要跳坏好几次.现在给出小朋友每次跳坏时 已经跳的总数,求小朋友在一分钟内跳了多少下.(请注意分析示例数据.)
Input:
第一行为 n 个小朋友 其余各行,每行第一个整数是跳坏的次数 m,其余 m 个整数是跳坏时累计跳了多少下.
Output:
输出相应小朋友头一分钟内跳了多少下.
Sample Input
603 12 23 451 17 4 10 20 30 40 5 10 20 30 40 58 6 10 20 30 40 47 60
Sample Output
60 51 57 48 48 47 Hint
提示,在跳绳比赛时,你可能已经超时了,但自己还在计数,但裁判已经停止计时并得到成绩. 这里相当与自己计数.因此,并非跳坏的时候都是在前一分钟以内.请注意分析示例数据
思路 代码 #include <stdio.h> int main () { int n, m, x, i, ok, time, s; scanf ("%d" , &n); while (n--) { time = ok = s = 0 ; scanf ("%d" , &m); for (i = 0 ; i < m; ++i) { scanf ("%d" , &x); time = x + 3 * i; if (ok == 0 ) { if (time >= 57 ) { ok = 1 ; time = (time > 60 ) ? 60 : time; s = time - 3 * i; } else if (time < 57 && i == m - 1 ) { s = 60 - 3 * (i + 1 ); } } } printf ("%d\n" , (m == 0 ) ? 60 : s); } return 0 ; }