-
Notifications
You must be signed in to change notification settings - Fork 0
/
automaton.js
131 lines (123 loc) · 3.01 KB
/
automaton.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
/**
* AUTOMATON
* Sebastián Gómez Dussán
* sgomezd@uniempresarial.edu.co
*/
const STATE_INICIO = "STATE_INICIO";
const STATE_EXTRAS = "STATE_EXTRAS";
const Automaton = {
processString: (str, graph) => {
let stateName = STATE_INICIO;
let state = graph[STATE_INICIO];
//Memoria de estados pasados para búsquedas sin orden
let charPath = [];
const processChar = (char) => {
const foundLink = state.links.find((link) => {
const linkParts = link.split(":");
const matches = linkParts[0].split("");
return matches.indexOf(char) !== -1;
});
//Si el caracter encontrado ya estuvo en un estado anterior, ignoramos el link
if (foundLink && !charPath.includes(char)) {
const linkParts = foundLink.split(":");
const nextStateName = linkParts[1];
const nextState = graph[nextStateName];
console.log(
`Encontrado link para ${char} en estado ${stateName} hacia estado ${nextStateName}`
);
stateName = nextStateName;
charPath = [...charPath, char];
return nextState;
}
console.log(`No se encontró link para '${char}'! Ignorando caracter...`);
return state;
};
let isFinal = false;
str.split("").forEach((char, index, array) => {
isLast = index === array.length - 1;
state = processChar(char);
if (isLast) {
isFinal = state.isFinal;
}
});
return isFinal;
},
};
const word = process.argv[2] || "EXIT";
console.log(`Procesar '${word}'`);
const graph = {
STATE_INICIO: {
links: ["E:E1", "X:X1", "I:I1", "T:T1"],
isFinal: false,
},
E1: {
links: ["E:E1", "X:X2", "T:T2", "I:I2"],
isFinal: false,
},
X1: {
links: ["X:X1", "E:E2", "T:T2", "I:I2"],
isFinal: false,
},
I1: {
links: ["I:I1", "X:X2", "T:T2", "E:E2"],
isFinal: false,
},
T1: {
links: ["T:T1", "X:X2", "E:E2", "I:I2"],
isFinal: false,
},
E2: {
links: ["E:E2", "X:X3", "T:T3", "I:I3"],
isFinal: false,
},
X2: {
links: ["X:X2", "E:E3", "T:T3", "I:I3"],
isFinal: false,
},
I2: {
links: ["I:I2", "X:X3", "T:T3", "E:E3"],
isFinal: false,
},
T2: {
links: ["T:T2", "X:X3", "E:E3", "I:I3"],
isFinal: false,
},
E3: {
links: ["E:E3", "X:X4", "T:T4", "I:I4"],
isFinal: false,
},
X3: {
links: ["X:X3", "E:E4", "T:T4", "I:I4"],
isFinal: false,
},
I3: {
links: ["I:I3", "X:X4", "T:T4", "E:E4"],
isFinal: false,
},
T3: {
links: ["T:T3", "X:X4", "E:E4", "I:I4"],
isFinal: false,
},
E4: {
links: ["E:E4", "ITX:" + STATE_EXTRAS],
isFinal: true,
},
X4: {
links: ["X:X4", "ITE:" + STATE_EXTRAS],
isFinal: true,
},
I4: {
links: ["I:I4", "ETX:" + STATE_EXTRAS],
isFinal: true,
},
T4: {
links: ["T:T4", "IEX:" + STATE_EXTRAS],
isFinal: true,
},
STATE_EXTRAS: {
links: ["EXIT:" + STATE_EXTRAS],
isFinal: true,
},
};
const result = Automaton.processString(word, graph);
console.log(result ? "COINCIDE" : "NO COINCIDE");