def infixNotation( baseExpr, opList, lpar=Suppress('<STR_LIT:(>'), rpar=Suppress('<STR_LIT:)>') ):
<EOL>class _FB(FollowedBy):<EOL><INDENT>def parseImpl(self, instring, loc, doActions=True):<EOL><INDENT>self.expr.tryParse(instring, loc)<EOL>return loc, []<EOL><DEDENT><DEDENT>ret = Forward()<EOL>lastExpr = baseExpr | ( lpar + ret + rpar )<EOL>for i,operDef in enumerate(opList):<EOL><INDENT>opExpr,arity,rightLeftAssoc,pa = (operDef + (None,))[:<NUM_LIT:4>]<EOL>termName = "<STR_LIT>" % opExpr if arity < <NUM_LIT:3> else "<STR_LIT>" % opExpr<EOL>if arity == <NUM_LIT:3>:<EOL><INDENT>if opExpr is None or len(opExpr) != <NUM_LIT:2>:<EOL><INDENT>raise ValueError(<EOL>"<STR_LIT>")<EOL><DEDENT>opExpr1, opExpr2 = opExpr<EOL><DEDENT>thisExpr = Forward().setName(termName)<EOL>if rightLeftAssoc == opAssoc.LEFT:<EOL><INDENT>if arity == <NUM_LIT:1>:<EOL><INDENT>matchExpr = _FB(lastExpr + opExpr) + Group( lastExpr + OneOrMore( opExpr ) )<EOL><DEDENT>elif arity == <NUM_LIT:2>:<EOL><INDENT>if opExpr is not None:<EOL><INDENT>matchExpr = _FB(lastExpr + opExpr + lastExpr) + Group( lastExpr + OneOrMore( opExpr + lastExpr ) )<EOL><DEDENT>else:<EOL><INDENT>matchExpr = _FB(lastExpr+lastExpr) + Group( lastExpr + OneOrMore(lastExpr) )<EOL><DEDENT><DEDENT>elif arity == <NUM_LIT:3>:<EOL><INDENT>matchExpr = _FB(lastExpr + opExpr1 + lastExpr + opExpr2 + lastExpr) +Group( lastExpr + opExpr1 + lastExpr + opExpr2 + lastExpr )<EOL><DEDENT>else:<EOL><INDENT>raise ValueError("<STR_LIT>")<EOL><DEDENT><DEDENT>elif rightLeftAssoc == opAssoc.RIGHT:<EOL><INDENT>if arity == <NUM_LIT:1>:<EOL><INDENT>if not isinstance(opExpr, Optional):<EOL><INDENT>opExpr = Optional(opExpr)<EOL><DEDENT>matchExpr = _FB(opExpr.expr + thisExpr) + Group( opExpr + thisExpr )<EOL><DEDENT>elif arity == <NUM_LIT:2>:<EOL><INDENT>if opExpr is not None:<EOL><INDENT>matchExpr = _FB(lastExpr + opExpr + thisExpr) + Group( lastExpr + OneOrMore( opExpr + thisExpr ) )<EOL><DEDENT>else:<EOL><INDENT>matchExpr = _FB(lastExpr + thisExpr) + Group( lastExpr + OneOrMore( thisExpr ) )<EOL><DEDENT><DEDENT>elif arity == <NUM_LIT:3>:<EOL><INDENT>matchExpr = _FB(lastExpr + opExpr1 + thisExpr + opExpr2 + thisExpr) +Group( lastExpr + opExpr1 + thisExpr + opExpr2 + thisExpr )<EOL><DEDENT>else:<EOL><INDENT>raise ValueError("<STR_LIT>")<EOL><DEDENT><DEDENT>else:<EOL><INDENT>raise ValueError("<STR_LIT>")<EOL><DEDENT>if pa:<EOL><INDENT>if isinstance(pa, (tuple, list)):<EOL><INDENT>matchExpr.setParseAction(*pa)<EOL><DEDENT>else:<EOL><INDENT>matchExpr.setParseAction(pa)<EOL><DEDENT><DEDENT>thisExpr <<= ( matchExpr.setName(termName) | lastExpr )<EOL>lastExpr = thisExpr<EOL><DEDENT>ret <<= lastExpr<EOL>return ret<EOL>
Helper method for constructing grammars of expressions made up of
    operators working in a precedence hierarchy.  Operators may be unary
    or binary, left- or right-associative.  Parse actions can also be
    attached to operator expressions. The generated parser will also
    recognize the use of parentheses to override operator precedences
    (see example below).

    Note: if you define a deep operator list, you may see performance
    issues when using infixNotation. See
    :class:`ParserElement.enablePackrat` for a mechanism to potentially
    improve your parser performance.

    Parameters:
     - baseExpr - expression representing the most basic element for the
       nested
     - opList - list of tuples, one for each operator precedence level
       in the expression grammar; each tuple is of the form ``(opExpr,
       numTerms, rightLeftAssoc, parseAction)``, where:

       - opExpr is the pyparsing expression for the operator; may also
         be a string, which will be converted to a Literal; if numTerms
         is 3, opExpr is a tuple of two expressions, for the two
         operators separating the 3 terms
       - numTerms is the number of terms for this operator (must be 1,
         2, or 3)
       - rightLeftAssoc is the indicator whether the operator is right
         or left associative, using the pyparsing-defined constants
         ``opAssoc.RIGHT`` and ``opAssoc.LEFT``.
       - parseAction is the parse action to be associated with
         expressions matching this operator expression (the parse action
         tuple member may be omitted); if the parse action is passed
         a tuple or list of functions, this is equivalent to calling
         ``setParseAction(*fn)``
         (:class:`ParserElement.setParseAction`)
     - lpar - expression for matching left-parentheses
       (default= ``Suppress('(')``)
     - rpar - expression for matching right-parentheses
       (default= ``Suppress(')')``)

    Example::

        # simple example of four-function arithmetic with ints and
        # variable names
        integer = pyparsing_common.signed_integer
        varname = pyparsing_common.identifier

        arith_expr = infixNotation(integer | varname,
            [
            ('-', 1, opAssoc.RIGHT),
            (oneOf('* /'), 2, opAssoc.LEFT),
            (oneOf('+ -'), 2, opAssoc.LEFT),
            ])

        arith_expr.runTests('''
            5+3*6
            (5+3)*6
            -2--11
            ''', fullDump=False)

    prints::

        5+3*6
        [[5, '+', [3, '*', 6]]]

        (5+3)*6
        [[[5, '+', 3], '*', 6]]

        -2--11
        [[['-', 2], '-', ['-', 11]]]