import Control.Applicative
calcRPN fs s = do
[result
] <- foldM f
[] $ words s
where
f
= foldr (\f g xs s
-> f xs s
<|> g xs s
) push fs
push xs s
= (:xs
) <$> case reads s
of {[(x
, "")] -> Just x;
_ -> Nothing
}
infixMaybe op a (y:x:xs) b | a == b = Just $ x `op` y : xs
infixMaybe _ _ _ _ = Nothing
add = infixMaybe (+) "+"
sub = infixMaybe (-) "-"
mul = infixMaybe (*) "*"
fdiv = infixMaybe (/) "/"
extension
(x:xs
) "sum" = Just
$ [sum (x:xs
)]extension
(x:xs
) "exp" = Just
$ exp x : xs
extension _ _ = Nothing
main = do
print $ calcRPN
[add
, sub
, mul
, fdiv
] "3 19 + -2 /" print $ calcRPN
[add
, sub
, mul
, fdiv
] "1 2 3" print $ calcRPN
[add
, sub
, mul
, fdiv
, extension
] "5 4 - exp 3 -2 1 sum"
aW1wb3J0IENvbnRyb2wuTW9uYWQKaW1wb3J0IENvbnRyb2wuQXBwbGljYXRpdmUKCmNhbGNSUE4gZnMgcyA9IGRvCiAgW3Jlc3VsdF0gPC0gZm9sZE0gZiBbXSAkIHdvcmRzIHMKICByZXR1cm4gcmVzdWx0CiAgd2hlcmUKICAgIGYgPSBmb2xkciAoXGYgZyB4cyBzIC0+IGYgeHMgcyA8fD4gZyB4cyBzKSBwdXNoIGZzCiAgICBwdXNoIHhzIHMgPSAoOnhzKSA8JD4gY2FzZSByZWFkcyBzIG9mIHtbKHgsICIiKV0gLT4gSnVzdCB4OyBfIC0+IE5vdGhpbmd9CgoKaW5maXhNYXliZSBvcCBhICh5Ong6eHMpIGIgfCBhID09IGIgPSBKdXN0ICQgeCBgb3BgIHkgOiB4cwogICAgICAgICAgICAgICAgICAgICAgICAgICB8IG90aGVyd2lzZSA9IE5vdGhpbmcKaW5maXhNYXliZSBfIF8gXyBfID0gTm90aGluZwoKYWRkID0gaW5maXhNYXliZSAoKykgIisiCnN1YiA9IGluZml4TWF5YmUgKC0pICItIgptdWwgPSBpbmZpeE1heWJlICgqKSAiKiIKZmRpdiA9IGluZml4TWF5YmUgKC8pICIvIgoKZXh0ZW5zaW9uICh4OnhzKSAic3VtIiA9IEp1c3QgJCBbc3VtICh4OnhzKV0KZXh0ZW5zaW9uICh4OnhzKSAiZXhwIiA9IEp1c3QgJCBleHAgeCA6IHhzCmV4dGVuc2lvbiBfIF8gPSBOb3RoaW5nCgptYWluID0gZG8KICBwcmludCAkIGNhbGNSUE4gW2FkZCwgc3ViLCBtdWwsIGZkaXZdICIzIDE5ICsgLTIgLyIKICBwcmludCAkIGNhbGNSUE4gW2FkZCwgc3ViLCBtdWwsIGZkaXZdICIxIDIgMyIKICBwcmludCAkIGNhbGNSUE4gW2FkZCwgc3ViLCBtdWwsIGZkaXYsIGV4dGVuc2lvbl0gIjUgNCAtIGV4cCAzIC0yIDEgc3VtIg==