分析文本时保持状态

Keep a state when parsing text

本文关键字:状态 文本      更新时间:2023-10-16

我正在尝试制作一个程序,每当它从一个状态转到另一个状态时,都会查找语法它需要指示该状态。我得到了不该得到的不同输出。

using namespace cppfsm;
#include <vector>
#include <iostream>
using std::cin;
using std::cout;
using std::endl;
using std::vector;
int cppfsm::updateState(int& state, char c) {
    const int state1 = 1;
    const int state2 = 2;
    switch (state) {
    case state1:
        if (c == '/')
            cout << "1" << endl;
            // do stuff; update state
        else if (c == '"')
            cout << "1" << endl;
            // do something else; update state
    case state2:
        if (c == '/')
            cout << "1" << endl;
            // do stuff; update state
        else if (c == '"')
            cout << "1" << endl;
            // do something else; update state
    }
    return 0;
}
void testFSM(string s) {
    vector<int> stlist; // list of states.
    int cstate = start;
    for (unsigned long i = 0; i < s.length(); i++) {
        stlist.push_back(updateState(cstate,s[i]));
    }
    // push the last state:
    stlist.push_back(cstate);
    cout << s << endl;
    for (unsigned long i = 0; i < stlist.size(); i++) {
        cout << stlist[i];
    }
    cout << endl;
}
int main() {
    // the finite state machine:
    string input;
    while(getline(cin,input)) {
        cout << " ";
        testFSM(input);
    }
    return 0;
}

输出应该是这样的。数字是从1到另一个时的状态

$ echo "int x; // holds stuff" | ./fsm 
int x; // holds stuff
0111010042222222222222
$ echo 'cout << "some string";' | ./fsm 
cout << "some string";
01111000033333333333300
$ echo 'cout << ""escape" chars are fun";' | ./fsm 
cout << ""escape" chars are fun";
011110000353333333533333333333333300

但是我的输出结果都是0000……s。我该如何解决这个问题?

如果您想知道为什么stlist都是0,请查看updateState:的返回语句

     return 0;
}

将其与用于填充stlist:的代码进行比较

stlist.push_back(updateState(cstate,s[i]));

据我所知,所有0都是该代码的正确行为。显然,这不是预期的或合乎逻辑的行为,所以我建议更改updateState:

int cppfsm::updateState(int& state, char c) {
    // ...
    return state;
}

现在,当您运行代码stlist时,应该包含预期的每个状态更改。

看起来您总是用相同的值调用updateState,start。该值未在开关中处理,因此函数返回零。这意味着你只需要在stlist向量上加零。

尝试处理开关中的启动状态,updateState函数的返回值应分配给cstate变量。

您的代码从不检查您的启动状态:

switch (state) {
    case state1: /* ... */
    case state2: /* ... */
    case start : /* ... */
}