Bison Flex уменьшает / уменьшает конфликты при свисании еще с помощью среднего действия
В настоящее время я перемещаю свой забавный проект на bison/flex в качестве парсера, и у меня возникли проблемы с решением конфликта уменьшения / уменьшения:
// https://github.com/X39/yaoosl/blob/master/code-gen/yaoosl.y#L761-L766
ifthen: YST_IF YST_ROUNDO expression code_ifstart YST_ROUNDC codebody code_ifendnoelse
| YST_IF YST_ROUNDO expression code_ifstart YST_ROUNDC ifthen_clsd YST_ELSE code_ifelse ifthen code_ifendelse
;
ifthen_clsd: codebody
| YST_IF YST_ROUNDO expression code_ifstart YST_ROUNDC ifthen_clsd code_ifelse YST_ELSE ifthen_clsd code_ifendelse
;
Примечание: вещи с префиксом code_ - это промежуточные действия
Может ли кто-нибудь объяснить мне, как правильно решить эту проблему и почему решение "перейти" либо неверно, либо не сработало? Спасибо, X39
1 ответ
Решение
Поскольку эти два правила идентичны до code_ifelse
(и предполагая, что code_ifelse - пустое правило, например действие в правиле), он не может определить, нужно ли сокращать code_ifelse
до или после YST_ELSE. Вы можете исправить это, приведя два правила в соответствие с порядкомcode_ifelse
а также YST_ELSE
.
Некоторые практические правила грамматики:
- Не используйте символьные имена для одиночных символьных токенов, например
'('
а также')'
- он просто запутывает вещи и затрудняет чтение и понимание грамматики. - Не используйте действия внутри правила без крайней необходимости - лучше создать правило с одним токеном с действием конечного правила, которое делает то, что вам нужно.