题目
有6条配置命令,它们执行的结果分别是:
注意:he he不是命令。
为了简化输入,方便用户,以“最短唯一匹配原则”匹配:
1、若只输入一字串,则只匹配一个关键字的命令行。例如输入:r,根据该规则,匹配命令reset,执行结果为:reset what;输入:res,根据该规则,匹配命令reset,执行结果为:reset what;
2、若只输入一字串,但本条命令有两个关键字,则匹配失败。例如输入:reb,可以找到命令reboot backpalne,但是该命令有两个关键词,所有匹配失败,执行结果为:unkown command
3、若输入两字串,则先匹配第一关键字,如果有匹配但不唯一,继续匹配第二关键字,如果仍不唯一,匹配失败。例如输入:r b,找到匹配命令reset board,执行结果为:board fault。
4、若输入两字串,则先匹配第一关键字,如果有匹配但不唯一,继续匹配第二关键字,如果唯一,匹配成功。例如输入:b a,无法确定是命令board add还是backplane abort,匹配失败。
5、若输入两字串,第一关键字匹配成功,则匹配第二关键字,若无匹配,失败。例如输入:bo a,确定是命令board add,匹配成功。
6、若匹配失败,打印“unkonw command”
输入:
多行字符串,每行字符串一条命令
输出:
执行结果,每条命令输出一行
样例输入:
reset
reset board
board add
board delet
reboot backplane
backplane abort
样例输出:
reset what
board fault
where to add
no board at all
impossible
install first
—————————————————分割线————————————————
这一题看着有点迷糊,只是考察字符串匹配吗??题目提出的规则是“最短唯一匹配原则”,这个“最短”一开始认为是相同前缀时选择单词长度最短的出现,结果在测试用例中发现不是这么回事。题目要求的就是一个“唯一匹配原则”,即输入字符串保证与命令字符串唯一匹配,如果出现多个匹配或者0匹配均输出“unknown command”。
代码
#include
#include
#include
using namespace std;
#define WORDS_NUM 6
#define ANSWER_NUM 7
static string words[WORDS_NUM] = {"reset", "reset board", "board add", "board delet", "reboot backplane", "backplane abort"};
static string answer[ANSWER_NUM] = {"reset what", "board fault", "where to add", "no board at all", "impossible", "install first", "unkown command"};
//计算输入字符串有多少个单词
int theNumOfWord(string cmd) {
string::size_type pos = 0;
int count = 0;
//空串直接返回0
if (cmd.size() == 0) {
return 0;
}
while(1) {
count++;
pos = cmd.find_first_of(' ', pos);
if (pos == cmd.npos) {
break;
}
while (cmd[pos] == ' ') {
pos++;
}
}
return count;
}
/*
比较字符串,返回0表示匹配成功, 返回-1表示匹配失败
*/
int cmpareWords(string cmd, string words) {
int i, j;
int cmdSize = cmd.size(), wordsSize = words.size();
string::size_type pos = 0;
for (i = 0, j = 0; i < cmdSize && j < wordsSize;) {
if (cmd[i] == words[j]) {
i++;
j++;
}else{
/*
出现字符不相等分为两种情况:
1、cmd字符串为‘ ’,即cmd字符串前一个单词已经匹配操作完,此时应该接着判断下一个单词;
2、cmd字符串为其他任意字符。
*/
if (cmd[i] == ' ') {
while (cmd[i] == ' ') {
i++;
}
pos = words.find_first_of(' ', pos);
while (words[pos] == ' ') {
pos++;
}
j = pos;
}else{
return -1;
}
}
}
return 0;
}
void getCommand(string cmd, vector<int> &numOfWord) {
int i, count;
int n = theNumOfWord(cmd);
int len = numOfWord.size();
vector<int> likelyCmd;
for (i = 0, count = 0; i < len; i++) {
/*
遍历的是命令字符串单词个数数组,对于所有匹配的命令把其下标均记录到likelyCmd数组中
*/
if (n == numOfWord[i] && cmpareWords(cmd, words[i]) == 0) {
likelyCmd.push_back(i);
}
}
//只有唯一匹配才可以输出操作结果,其余均输出"unkown command"
if (likelyCmd.size() != 1) {
cout << answer[ANSWER_NUM - 1] << endl;
}else{
cout << answer[likelyCmd[0]] << endl;
}
return;
}
//初始化命令字符串单词个数数组
void init(vector<int> &numOfWord) {
int i, n;
for (i = 0; i < WORDS_NUM; i++) {
n = theNumOfWord(words[i]);
numOfWord.push_back(n);
}
return;
}
int main() {
string cmd;
vector<int> numOfWord;
init(numOfWord);
while (getline(cin, cmd)) {
getCommand(cmd, numOfWord);
}
return 0;
}
加油 !!!