[Haskell] Parsec question: attempted 'notMatching' combinator

Graham Klyne gk at ninebynine.org
Tue Feb 17 18:42:39 EST 2004


I've attempted to define a Parsec combinator thus:

[[
notMatching :: Show a => GenParser tok st a -> GenParser tok st ()
notMatching p = try ( do { a <- p ; unexpected (show a) } <|> return () )
]]

It's modelled on the Parsec-provided combinator 'notFollowedBy', but is 
less fussy about the type of parser allowed.  It is an attempt to do a 
look-ahead.  It compiles OK, but it doesn't work as I might expect, e.g. as in:

[[
relativeUri :: UriParser URI
relativeUri =
     do  { notMatching uscheme
         ; ua <- option "" ( do { try (string "//") ; uauthority } )
         ; up <- upath
         ; uq <- option "" ( do { string "?" ; uquery    } )
         ; uf <- option "" ( do { string "#" ; ufragment } )
         ; return $ URI
             { scheme    = ""
             , authority = ua
             , path      = up
             , query     = uq
             , fragment  = uf
             }
         }
]]

It has the effect of causing several otherwise valid parses to 
fail.  Notably, it is cases that do not match the 'uscheme' parser that 
fail when they should be matched overall.  I *suspect* that the 'try' logic 
is not interacting cleanly with the case that uscheme parser does not 
succeed, but I don't have any hard evidence.  Can anyone see anything 
obviously wrong with this?

(I have a work-around to the problem, but one that sometimes involves 
parsing an entire URI twice when trying to isolate relative URIs.  I could 
restructure the code in other ways, but that would defeat my goal of 
keeping the code very close to the work-in-progress URI specification.)

#g


------------
Graham Klyne
For email:
http://www.ninebynine.org/#Contact



More information about the Haskell mailing list