【PAT乙级】1003 我要通过! (20分)
1003 我要通过! (20分)
“答案正确”是自动判题系统给出的最令人欢喜的回复。本题属于 PAT 的“答案正确”大派送 —— 只要读入的字符串满足下列条件,系统就输出“答案正确”,否则输出“答案错误”。
得到“答案正确”的条件是:
- 字符串中必须仅有
P
、A
、T
这三种字符,不可以包含其它字符; - 任意形如
xPATx
的字符串都可以获得“答案正确”,其中x
或者是空字符串,或者是仅由字母A
组成的字符串; - 如果
aPbTc
是正确的,那么aPbATca
也是正确的,其中a
、b
、c
均或者是空字符串,或者是仅由字母A
组成的字符串。
现在就请你为 PAT 写一个自动裁判程序,判定哪些字符串是可以获得“答案正确”的。
输入格式:
每个测试输入包含 1 个测试用例。第 1 行给出一个正整数 n (≤10),是需要检测的字符串个数。接下来每个字符串占一行,字符串长度不超过 100,且不包含空格。
输出格式:
每个字符串的检测结果占一行,如果该字符串可以获得“答案正确”,则输出 YES
,否则输出 NO
。
输入样例:
1 | 10 |
输出样例:
1 | YES |
思路:
这道题说难也不是很难,说简单也不简单,主要是要理解如何判断一个字符串是否正确。接下来我们一条一条的看:
-
字符串中必须仅有
P
、A
、T
这三种字符,不可以包含其它字符;
由此可以得出,字符串的组成只有P
、A
、T
这三种字符,一旦出现其他的字符可以直接判断NO
。那么用什么结构来存储输入的字符串,以及更严格的要求,还得看接下来的两个条件。 -
任意形如
xPATx
的字符串都可以获得“答案正确”,其中x
或者是空字符串,或者是仅由字母A
组成的字符串;
这里x
其实就相当于未知数,也就是说PAT
这个字符串前后可以接受 加上两个相等的字符串(要么为空要么全是A
) ,形如这样的字符串都可以判断YES
那么问题来了, 如何在代码中判断这个PAT
前后加的两个字符串是否符合要求呢? 在这里,C++提供的 string 其实就可以满足了,遍历string容器,确定字符P
和字符T
的位置,就可以很方便的判断前后字符串是否符合要求。 -
如果
aPbTc
是正确的,那么aPbATca
也是正确的,其中a
、b
、c
均或者是空字符串,或者是仅由字母A
组成的字符串。
这里是最复杂的,我们慢慢分析。这里有一个大前提就是:如果aPbTc
是正确的。那以我们现在的要求,要想让aPbTc
是正确的,那么PT
中间的b
肯定是字符串A
,而且a
和c
要相等才行,那么就可以代入一下第二个要求的图片。①.
a
=c
=‘∅’(a和c是空串),b
=A
。再看 那么aPbATca
也是正确的 ,那这个字符串就变成了PAAT
,由题意知,这个也是对的。那如此嵌套循环下去,PAAAT
,PAAAAT
……等等也是正确的。因为只要是正确的字符串,就可以继续套入aPbATca
这个“公式”。用人话说就是:P
和T
之间至少有一个A
。②.
a
=c
=‘A’,b
=‘A’。代入公式得APAATAA
,现在字符串就有点奇怪了,好像看不出什么规律,那么我们接着往下看。
③.
a
=c
=“AA”,b
=‘A’。代入公式得AAPAATAAAA
,这下是不是有点思路了,这是不是 (P前面的A) × (PT中间的A) = (T后面的A)呢 ?不确定?那我们再随机验证一下。
④.
a
=‘A’c
=“AA”,b
=‘AA’。这次a
和c
不相等了,我们再代入一次公式,得到了APAAATAAA
,现在就确定了,就是 (P前面的A) × (PT中间的A) = (T后面的A) 。
其实同样的规律也可以用于第二个要求,因为中间只有一个
A
,那么不管两边有多少个A
,只要数量相等就可以,因为1乘任意数就等于任意数嘛。但是这里还有一个坑,三个要求全部看完之后,其实还有一些条件我们没有发现,接下来我们去看看输入样例和输出样例。 -
在样例中,xPATx、PT、Whatever、APAAATAA、APT、APATTAA都是错的,其中xPATx、Whatever都是因为包含有其他字符而错误。PT和APT是因为第三条的第一点,PT之间至少有一个A,所以PT错。APAAATAA这是因为A之间的关系不满足,所以也是错的。那么这个APATTAA是因为什么错呢,虽然说这个字符串A之间的关系也不满足(因为1 × 1 应该为 1 才对),但是还有一个致命的错误那就是 有两个T ,导致我们无法判断是哪个T的前后,包括P也是一样,所以这里应该还有一个条件是: 字母
P
和字母T
只能有一个 。 -
现在所有的条件都齐全了,那么在代码上由于要判断这个字符串所包含字符的种类、数量及位置,这里我想到用 map容器 来存储这个字符串的信息。
代码如下:
1 |
|