Pour une mission, nous avons dû mettre en œuvre quelque chose comme un analyseur sexp très basique, de sorte que pour l'entrée comme:Très simple analyseur sexp
"((a b) ((c d) e) f)"
Il retournerait:
[["a", "b"], [["c", "d"], "e"], "f"]
Depuis c'était partie d'une plus grande affectation, l'analyseur est seulement donné une entrée valide (parens correspondant & c). Je suis venu avec la solution suivante en Ruby:
def parse s, start, stop
tokens = s.scan(/#{Regexp.escape(start)}|#{Regexp.escape(stop)}|\w+/)
stack = [[]]
tokens.each do |tok|
case tok
when start
stack << []
when stop
stack[-2] << stack.pop
else
stack[-1] << tok
end
end
return stack[-1][-1]
end
Ce qui peut ne pas être la meilleure solution, mais il fait le travail. Maintenant, je suis intéressé par une solution Haskell idiomatique pour la fonctionnalité de base (ie je me fiche du lexing ou du choix des délimiteurs, en prenant déjà une entrée lexée serait bien), si possible en utilisant seulement "core" haskell, sans extensions ou libs comme parsec.
Notez que cela ne fait PAS partie de la mission, je suis simplement intéressé par la façon de faire Haskell.
La solution idiomatique consiste à utiliser une bibliothèque d'analyseurs (combinateur ou autre).Puisque vous excluez explicitement cette option, une solution idiomatique est impossible. La programmation concerne la réutilisation et non la réinvention. – jrockway
Bien sûr, si c'était un problème du monde réel, vous auriez absolument raison. Mais considérons tous les livres qui enseignent le haskell dans lequel, à des fins d'apprentissage, les fonctions de prélude sont réimplémentées. Ne seriez-vous pas d'accord qu'il existe des solutions plus idiomatiques que d'autres? Oui, la programmation concerne la réutilisation, mais l'apprentissage peut parfois être une réinvention. – danlei