Account Options

  1. Sign in
The old Google Groups will be going away soon.
Switch to the new Google Groups.
Google Groups Home
« Groups Home
Parsec : Problems with operator precedence
There are currently too many topics in this group that display first. To make this topic appear first, remove this option from another topic.
There was an error processing your request. Please try again.
flag
  8 messages - Collapse all  -  Translate all to Translated (View all originals)
The group you are posting to is a Usenet group. Messages posted to this group will make your email address visible to anyone on the Internet.
Your reply message has not been sent.
Your post was successful
 
From:
To:
Cc:
Followup To:
Add Cc | Add Followup-to | Edit Subject
Subject:
Validation:
For verification purposes please type the characters you see in the picture below or the numbers you hear by clicking the accessibility icon. Listen and type the numbers you hear
 
Erik de Castro Lopo  
View profile  
 More options Dec 29 2008, 4:28 am
Newsgroups: fa.haskell
From: Erik de Castro Lopo <mle...@mega-nerd.com>
Date: Mon, 29 Dec 2008 09:28:28 UTC
Local: Mon, Dec 29 2008 4:28 am
Subject: [Haskell-cafe] Parsec : Problems with operator precedence
Hi all,

I'm using Text.ParserCombinators.Parsec.Expr to parse expressions for
a Javascript like language. This language has C-like logical operators
('&&' and '||') and bitwise operators ('&' and '|'). Furthermore, the
language definition states that bitwise operators have a higher precedence
than the logical ones.

I therefore have the following (trimmed):

    import qualified Text.ParserCombinators.Parsec.Expr as E

    opTable :: [[ E.Operator Char st Expression ]]
    opTable = [
        -- Operators listed from highest precedence to  lowest precedence.

        {- snip, snip -}

        [    binaryOp "&" BinOpBinAnd E.AssocLeft ],
        [    binaryOp "^"  BinOpBinXor E.AssocLeft ],
        [    binaryOp "|"  BinOpBinOr E.AssocLeft ],

        [    binaryOp "&&" BinOpLogAnd E.AssocLeft ],
        [    binaryOp "||" BinOpLogOr E.AssocLeft ]
        ]

    binaryOp :: String -> (SourcePos -> a -> a -> a) -> E.Assoc -> E.Operator Char st a
    binaryOp name con assoc =
        E.Infix (reservedOp name >>
            getPosition >>=
            return . con) assoc

but I still get the following parse error:

    unexpected "|"
    expecting end of "|" or term

on the line:

    if (name == null || value == null)

If I change the above from a logical to a bitwise OR, the parser
accepts it quite happily.

Any clues as to what I'm doing wrong here?

Cheers,
Erik
--
-----------------------------------------------------------------
Erik de Castro Lopo
-----------------------------------------------------------------
BSD:  A psychoactive drug, popular in the 80s, probably developed at UC
Berkeley or thereabouts.  Similar in many ways to the prescription-only
medication called "System V", but infinitely more useful. (Or, at least,
more fun.)  The full chemical name is "Berkeley Standard Distribution".
_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Daniel Fischer  
View profile  
 More options Dec 29 2008, 5:32 am
Newsgroups: fa.haskell
From: Daniel Fischer <daniel.is.fisc...@web.de>
Date: Mon, 29 Dec 2008 10:32:48 UTC
Local: Mon, Dec 29 2008 5:32 am
Subject: Re: [Haskell-cafe] Parsec : Problems with operator precedence
Am Montag, 29. Dezember 2008 10:27 schrieb Erik de Castro Lopo:

The problem is that "|" is a prefix of "||" and it gets the first bite. So
when the parser gets to "||" it first tries to parse a bitwise or. That
succeeds. Then the parser is looking for an operand, but it finds the second
- unexpected - "|". I don't remember how Parsec's expression parsers work,
maybe you can add a "try" some parser(s) to make it work.

> Any clues as to what I'm doing wrong here?

> Cheers,
> Erik

_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe

 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Erik de Castro Lopo  
View profile  
 More options Dec 29 2008, 6:11 am
Newsgroups: fa.haskell
From: Erik de Castro Lopo <mle...@mega-nerd.com>
Date: Mon, 29 Dec 2008 11:11:05 UTC
Local: Mon, Dec 29 2008 6:11 am
Subject: Re: [Haskell-cafe] Parsec : Problems with operator precedence

Daniel Fischer wrote:
> The problem is that "|" is a prefix of "||" and it gets the first bite. So
> when the parser gets to "||" it first tries to parse a bitwise or. That
> succeeds. Then the parser is looking for an operand, but it finds the second
> - unexpected - "|". I don't remember how Parsec's expression parsers work,
> maybe you can add a "try" some parser(s) to make it work.

I've did try a 'try' but that didn't help.

Erik
--
-----------------------------------------------------------------
Erik de Castro Lopo
-----------------------------------------------------------------
"Whenever the C++ language designers had two competing ideas as to
how they should solve some problem, they said, "OK, we'll do them
both". So the language is too baroque for my taste." -- Donald E Knuth
_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Lorenz Pretterhofer  
View profile  
 More options Dec 29 2008, 6:11 am
Newsgroups: fa.haskell
From: Lorenz Pretterhofer <krys...@internode.on.net>
Date: Mon, 29 Dec 2008 11:11:24 UTC
Local: Mon, Dec 29 2008 6:11 am
Subject: Re: [Haskell-cafe] Parsec : Problems with operator precedence
I haven't really used the expr parser combinator recently, but it does
sound like the parser with higher precedence is failing after reading
characters when processing the earlier "|" operator.

You could try using (try (reservedOp name)) in the definition of
binaryOp, which should prevent the operator from causing the error to
propagate out of the expression parser. Then the more general "||"
parser should be able to get to it.

Otherwise it will probably be necessary to use a follow set approach and
test of any further operator characters in the parser for the operator.
 From the error message it sounds that's already being done though.

Hope this helps.

-- Lorenz

_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe

 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Discussion subject changed to "Parsec : Problems with operator precedence (solution)" by Erik de Castro Lopo
Erik de Castro Lopo  
View profile  
 More options Dec 29 2008, 12:08 pm
Newsgroups: fa.haskell
From: Erik de Castro Lopo <mle...@mega-nerd.com>
Date: Mon, 29 Dec 2008 17:08:01 UTC
Local: Mon, Dec 29 2008 12:08 pm
Subject: Re: [Haskell-cafe] Parsec : Problems with operator precedence (solution)
Erik de Castro Lopo wrote:

>     binaryOp :: String -> (SourcePos -> a -> a -> a) -> E.Assoc -> E.Operator Char st a
>     binaryOp name con assoc =
>         E.Infix (reservedOp name >>
>             getPosition >>=
>             return . con) assoc

Replacing reservedOp above with:

    reservedOpNf :: String -> CharParser st ()
    reservedOpNf name = try (reservedOp name >> notFollowedBy (oneOf "|&="))

fixed the problem.

Cheers,
Erik
--
-----------------------------------------------------------------
Erik de Castro Lopo
-----------------------------------------------------------------
"If dolphins are so smart, why do they live in igloos?" -Eric Cartman
_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Erik de Castro Lopo  
View profile  
 More options Dec 29 2008, 10:51 pm
Newsgroups: fa.haskell
From: Erik de Castro Lopo <mle...@mega-nerd.com>
Date: Tue, 30 Dec 2008 03:51:21 UTC
Local: Mon, Dec 29 2008 10:51 pm
Subject: Re: [Haskell-cafe] Parsec : Problems with operator precedence (solution)
Erik de Castro Lopo wrote:

> Replacing reservedOp above with:

>     reservedOpNf :: String -> CharParser st ()
>     reservedOpNf name = try (reservedOp name >> notFollowedBy (oneOf opChars))

> fixed the problem.

Just for the sake of completeness and the google archive, the above
fixed the main problem but left another problem in parsing something
like:

   if (whatever == -1)

which  resulted in a error at uninary minus sign.

The problem was that the reservedOp combinator as used above chews
up any trailing whitespace so that the notFollowedBy was triggered
by the minus.

The solution was to use the string combinator instead of reservedOp,
then use the notFollowedBy and finally chew up trailing whitespace
as follows:

    reservedOpNf :: String -> CharParser st ()
    reservedOpNf name =
        try (string name >> notFollowedBy (oneOf "|&=") >> whiteSpace)

Erik
--
-----------------------------------------------------------------
Erik de Castro Lopo
-----------------------------------------------------------------
Is God willing to prevent evil, but not able?
Then he is not omnipotent.
Is he able, but not willing?
Then he is malevolent.
Is he both able and willing?
Then whence cometh evil?
Is he neither able nor willing?
Then why call him God?
-- Epicurus, Greek philosopher, BC 341-270
_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Benedikt Huber  
View profile  
 More options Jan 2 2009, 8:21 pm
Newsgroups: fa.haskell
From: Benedikt Huber <benj...@gmx.net>
Date: Sat, 03 Jan 2009 01:21:31 UTC
Local: Fri, Jan 2 2009 8:21 pm
Subject: [Haskell-cafe] Re: Parsec : Problems with operator precedence (solution)
Erik de Castro Lopo schrieb:
> Erik de Castro Lopo wrote:

>>     binaryOp :: String -> (SourcePos -> a -> a -> a) -> E.Assoc -> E.Operator Char st a
>>     binaryOp name con assoc =
>>         E.Infix (reservedOp name >>
>>             getPosition >>=
>>             return . con) assoc

> Replacing reservedOp above with:

>     reservedOpNf :: String -> CharParser st ()
>     reservedOpNf name = try (reservedOp name >> notFollowedBy (oneOf "|&="))

> fixed the problem.

Hi Erik,
There is an easy, better solution, modifying the lexer:

 > lexer = makeTokenParser $ emptyDef
 >           { L.reservedOpNames = words "&& || & | ^" }
 > reservedOp = P.reservedOp lexer
 > identifier = P.identifier lexer
 > ...

I'd try to avoid 'try', if possible.

benedikt
_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
Erik de Castro Lopo  
View profile  
 More options Jan 2 2009, 10:14 pm
Newsgroups: fa.haskell
From: Erik de Castro Lopo <mle...@mega-nerd.com>
Date: Sat, 03 Jan 2009 03:14:57 UTC
Local: Fri, Jan 2 2009 10:14 pm
Subject: Re: [Haskell-cafe] Re: Parsec : Problems with operator precedence (solution)

Benedikt Huber wrote:
> There is an easy, better solution, modifying the lexer:

>  > lexer = makeTokenParser $ emptyDef
>  >           { L.reservedOpNames = words "&& || & | ^" }
>  > reservedOp = P.reservedOp lexer
>  > identifier = P.identifier lexer
>  > ...

> I'd try to avoid 'try', if possible.

Hi Benedikt,

I did try that (reservedOpNames as a list of operators as strings)
but that interferred rather badly with another part of the parser
which handles raw inline XML like this (yes, utterly horrid):

     var xdata = <xml>sucks</xml> ;

Because I had the XML parsing working when I hit the operator precedence
problem I worked towards a solution that didn't break the XML rather
than do the right thing to fix the operator precedence and then have to
fix the XML part.

Erik
--
-----------------------------------------------------------------
Erik de Castro Lopo
-----------------------------------------------------------------
"how am I expected to quit smoking if I have to deal with NT
every day" -- Ben Raia
_______________________________________________
Haskell-Cafe mailing list
Haskell-C...@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


 
You must Sign in before you can post messages.
To post a message you must first join this group.
Please update your nickname on the subscription settings page before posting.
You do not have the permission required to post.
End of messages
« Back to Discussions « Newer topic     Older topic »