有穷自动机--单词与空格

输入一个字符串,输入的只有两种字符,一种是字母,一种是空格。现在求一共有几个单词。注意,有可能有多个空格连在一起,开头和结尾都有可能有空格。

有穷自动机的意思是,有多种状态同时进行

那么这是一道简单的有穷自动机,运行时分两种情况:

①是空格

②是字母

(其实当前状态就是上一个字符的状态

那么在遍历数组的时候拿一个变量记录下来当前是什么状态,可以用000代表当前是空格状态,111代表是字母状态

当如果当前状态是111,而现在却遇到空格,那么就计数器加一,同时要将状态改为000,如果当前状态是000,现在的字符却是字母,就只将状态改为111

不过要注意

在跳出循环的时候如果状态是111,要将计数器加一,否则如果最后是字母就会少统计一个单词!

(所以可以在最后人为加几个空格)

 1 #include <cstdio>
 2 
 3 int main () {
 4 
 5     char a[1001];
 6     int state, ans = 0;
 7 
 8     gets(a);
 9 
10     if(a[0] == ' ') state = 0;//设置初始值
11     else state = 1;
12 
13     for(int i = 1; a[i]; i ++ ) {//要从一开始遍历,因为零已经遍历过了
14         if(a[i] == ' ') {//是空格
15             if(state == 1) {//当前状态(前一个)是字母,说明找到一个单词了
16                 ans ++ ;//答案加一
17                 state = 0;//千万别忘了改状态
18             }
19         }
20         else {//是字母
21             if(state == 0) {//当前状态(前一个)是空格
22                 state = 1;//将状态改为1
23             }
24         }
25     }
26 
27     if(state == 1)//最后还要判断一下千万不要忘记
28         ans ++ ;
29     printf("%d", ans);
30 
31     return 0;
32 }

判断条件:前一个是字母(state=1)后一个是空格.最后一个如果是字母,则加一.

P1308 洛谷

  1 #include <cstdio>
  2 
  3 int main () {
  4 
  5     char a[1001];
  6     int state, ans = 0;
  7 
  8     gets(a);
  9 
 10     if(a[0] == ' ') state = 0;//设置初始值
 11     else state = 1;
 12 
 13     for(int i = 1; a[i]; i ++ ) {//要从一开始遍历,因为零已经遍历过了
 14         if(a[i] == ' ') {//是空格
 15             if(state == 1) {//当前状态(前一个)是字母,说明找到一个单词了
 16                 ans ++ ;//答案加一
 17                 state = 0;//千万别忘了改状态
 18             }
 19         }
 20         else {//是字母
 21             if(state == 0) {//当前状态(前一个)是空格
 22                 state = 1;//将状态改为1
 23             }
 24         }
 25     }
 26 
 27     if(state == 1)//最后还要判断一下千万不要忘记
 28         ans ++ ;
 29     printf("%d", ans);
 30 
 31     return 0;
 32 }
 33 
 34 那么,这就是简单的自动机代码,现在看看本题用自动机如何做
 35 
 36 其实一样,就是注意字母状态分时要查找单词状态和不是要查找单词状态,而且单词第nnn个字母的状态就用nnn来表示
 37 
 38 以下是code:
 39 
 40 #include <cstdio>
 41 #include <cctype>
 42 #include <cstring>
 43 
 44 const int SPACE = 0;//三种状态,这是空格状态
 45 const int LETTER = -1;//字母状态,但这表示不是要查找的单词的字母的状态
 46 const int WORD = 1;//而这种状态是要查找的单词的状态
 47 //当然了,如果状态时大于1的数,说明是要查找的单词的中间部分的状态,上文讲过了
 48 
 49 inline void strlower (char *a) {//不解释,上面的代码有了
 50     for(int i = 0; a[i]; i ++ ) {
 51         if(isupper(a[i])) a[i] = tolower(a[i]);
 52     }
 53 }
 54 
 55 int main () {
 56 
 57     char a[1000001], word[20];
 58     int ans = 0;
 59     int ans2 = -1;
 60     int state = 0;//表状态,假设是空格,因为空格上来就判断是不是三种状态
 61     int i;
 62 
 63     gets(word);
 64     gets(a);
 65     strlower(a);
 66     strlower(word);
 67     int len = strlen( word );
 68 
 69     for(i = 0; a[i]; i ++ ) {//遍历数组
 70         switch ( state ) {
 71             case SPACE : //如果当前状态(上一个)是空格
 72                 if(a[i] == word[0]) state = WORD;//变成单词第一个字母状态
 73                 else if(a[i] == ' ') state = SPACE;//其实这句话可以省略,因为反正都是空格状态,改它是一样的
 74                 else state = LETTER;//剩下的肯定是其他字母状态了
 75                 break;
 76             case LETTER : //是其他字母状态
 77                 if(a[i] == ' ') state = SPACE;//空格状态
 78                 break;
 79             default: //是要查找的单词状态
 80                 if ( state < len  ) {//还不是最后一个字母
 81                     if(a[i] == ' ') state = SPACE;
 82                     else if(a[i] == word[state]) state ++ ;//变成下一个字母状态
 83                     else state = LETTER;//其他字母状态
 84                 }
 85                 else if (state == len )//是最后一个字母
 86                 {   
 87                     if(a[i] == ' ') {//如果下一个是空格,找到了!
 88                         state = SPACE;//状态不要忘记改变
 89                             if(ans2 == -1)//第一次找到,记录下来位置
 90                                 ans2 = i - len;//因为i是单词的尾,所以要减长度
 91                         ans ++ ;//个数加一
 92                     }
 93                     else state = LETTER;//可惜,最后跟着其他字母,不是单词
 94                 }
 95         }
 96 
 97     }
 98 
 99     if(state == len) {
100         ans ++ ;
101         if(ans2 == -1)
102             ans2 = i - 1 - len;
103     }
104     if(ans2 == -1) printf("-1");
105     else printf("%d %d", ans, ans2);
106 
107     return 0;
108 }

(转载自AH是女孩子 的题解)

猜你喜欢

转载自www.cnblogs.com/zhmlzhml/p/12322379.html