summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDavid Beazley <dave@dabeaz.com>2019-11-24 17:59:03 -0600
committerGitHub <noreply@github.com>2019-11-24 17:59:03 -0600
commitf6d78006324079bfe824422b9a21dc91811ecfa2 (patch)
tree7f85b26028fca2c29e382496783c916e948a7b7a
parentf45aa4e7aadfedbb48142cd8bab18c7cf6622d2e (diff)
parentaa2d0bda9c4fb742eaf460f91c19125480499385 (diff)
downloadply-f6d78006324079bfe824422b9a21dc91811ecfa2.tar.gz
Merge pull request #158 from hugovk/patch-1
README: Remove code formatting to make links clickable, add Python formatting to code
-rw-r--r--README.md227
1 files changed, 116 insertions, 111 deletions
diff --git a/README.md b/README.md
index e200232..edde724 100644
--- a/README.md
+++ b/README.md
@@ -75,14 +75,18 @@ within the 'ply' directory which may also be used as a Python package.
To use PLY, simply copy the 'ply' directory to your project and import
lex and yacc from the associated 'ply' package. For example:
- from .ply import lex
- from .ply import yacc
+```python
+from .ply import lex
+from .ply import yacc
+```
Alternatively, you can copy just the files lex.py and yacc.py
individually and use them as modules however you see fit. For example:
- import lex
- import yacc
+```python
+import lex
+import yacc
+```
PLY has no third-party dependencies.
@@ -105,7 +109,7 @@ Resources
=========
More information about PLY can be obtained on the PLY webpage at:
- http://www.dabeaz.com/ply
+* http://www.dabeaz.com/ply
For a detailed overview of parsing theory, consult the excellent
book "Compilers : Principles, Techniques, and Tools" by Aho, Sethi, and
@@ -114,11 +118,11 @@ may also be useful.
The GitHub page for PLY can be found at:
- https://github.com/dabeaz/ply
+* https://github.com/dabeaz/ply
An old and inactive discussion group for PLY is found at:
- http://groups.google.com/group/ply-hack
+* http://groups.google.com/group/ply-hack
Acknowledgments
===============
@@ -145,110 +149,111 @@ Example
Here is a simple example showing a PLY implementation of a calculator
with variables.
- # -----------------------------------------------------------------------------
- # calc.py
- #
- # A simple calculator with variables.
- # -----------------------------------------------------------------------------
-
- tokens = (
- 'NAME','NUMBER',
- 'PLUS','MINUS','TIMES','DIVIDE','EQUALS',
- 'LPAREN','RPAREN',
- )
-
- # Tokens
-
- t_PLUS = r'\+'
- t_MINUS = r'-'
- t_TIMES = r'\*'
- t_DIVIDE = r'/'
- t_EQUALS = r'='
- t_LPAREN = r'\('
- t_RPAREN = r'\)'
- t_NAME = r'[a-zA-Z_][a-zA-Z0-9_]*'
-
- def t_NUMBER(t):
- r'\d+'
- t.value = int(t.value)
- return t
-
- # Ignored characters
- t_ignore = " \t"
-
- def t_newline(t):
- r'\n+'
- t.lexer.lineno += t.value.count("\n")
-
- def t_error(t):
- print("Illegal character '%s'" % t.value[0])
- t.lexer.skip(1)
-
- # Build the lexer
- import ply.lex as lex
- lex.lex()
-
- # Precedence rules for the arithmetic operators
- precedence = (
- ('left','PLUS','MINUS'),
- ('left','TIMES','DIVIDE'),
- ('right','UMINUS'),
- )
-
- # dictionary of names (for storing variables)
- names = { }
-
- def p_statement_assign(p):
- 'statement : NAME EQUALS expression'
- names[p[1]] = p[3]
-
- def p_statement_expr(p):
- 'statement : expression'
- print(p[1])
-
- def p_expression_binop(p):
- '''expression : expression PLUS expression
- | expression MINUS expression
- | expression TIMES expression
- | expression DIVIDE expression'''
- if p[2] == '+' : p[0] = p[1] + p[3]
- elif p[2] == '-': p[0] = p[1] - p[3]
- elif p[2] == '*': p[0] = p[1] * p[3]
- elif p[2] == '/': p[0] = p[1] / p[3]
-
- def p_expression_uminus(p):
- 'expression : MINUS expression %prec UMINUS'
- p[0] = -p[2]
-
- def p_expression_group(p):
- 'expression : LPAREN expression RPAREN'
- p[0] = p[2]
-
- def p_expression_number(p):
- 'expression : NUMBER'
- p[0] = p[1]
-
- def p_expression_name(p):
- 'expression : NAME'
- try:
- p[0] = names[p[1]]
- except LookupError:
- print("Undefined name '%s'" % p[1])
- p[0] = 0
-
- def p_error(p):
- print("Syntax error at '%s'" % p.value)
-
- import ply.yacc as yacc
- yacc.yacc()
-
- while True:
- try:
- s = raw_input('calc > ') # use input() on Python 3
- except EOFError:
- break
- yacc.parse(s)
-
+```python
+# -----------------------------------------------------------------------------
+# calc.py
+#
+# A simple calculator with variables.
+# -----------------------------------------------------------------------------
+
+tokens = (
+ 'NAME','NUMBER',
+ 'PLUS','MINUS','TIMES','DIVIDE','EQUALS',
+ 'LPAREN','RPAREN',
+ )
+
+# Tokens
+
+t_PLUS = r'\+'
+t_MINUS = r'-'
+t_TIMES = r'\*'
+t_DIVIDE = r'/'
+t_EQUALS = r'='
+t_LPAREN = r'\('
+t_RPAREN = r'\)'
+t_NAME = r'[a-zA-Z_][a-zA-Z0-9_]*'
+
+def t_NUMBER(t):
+ r'\d+'
+ t.value = int(t.value)
+ return t
+
+# Ignored characters
+t_ignore = " \t"
+
+def t_newline(t):
+ r'\n+'
+ t.lexer.lineno += t.value.count("\n")
+
+def t_error(t):
+ print("Illegal character '%s'" % t.value[0])
+ t.lexer.skip(1)
+
+# Build the lexer
+import ply.lex as lex
+lex.lex()
+
+# Precedence rules for the arithmetic operators
+precedence = (
+ ('left','PLUS','MINUS'),
+ ('left','TIMES','DIVIDE'),
+ ('right','UMINUS'),
+ )
+
+# dictionary of names (for storing variables)
+names = { }
+
+def p_statement_assign(p):
+ 'statement : NAME EQUALS expression'
+ names[p[1]] = p[3]
+
+def p_statement_expr(p):
+ 'statement : expression'
+ print(p[1])
+
+def p_expression_binop(p):
+ '''expression : expression PLUS expression
+ | expression MINUS expression
+ | expression TIMES expression
+ | expression DIVIDE expression'''
+ if p[2] == '+' : p[0] = p[1] + p[3]
+ elif p[2] == '-': p[0] = p[1] - p[3]
+ elif p[2] == '*': p[0] = p[1] * p[3]
+ elif p[2] == '/': p[0] = p[1] / p[3]
+
+def p_expression_uminus(p):
+ 'expression : MINUS expression %prec UMINUS'
+ p[0] = -p[2]
+
+def p_expression_group(p):
+ 'expression : LPAREN expression RPAREN'
+ p[0] = p[2]
+
+def p_expression_number(p):
+ 'expression : NUMBER'
+ p[0] = p[1]
+
+def p_expression_name(p):
+ 'expression : NAME'
+ try:
+ p[0] = names[p[1]]
+ except LookupError:
+ print("Undefined name '%s'" % p[1])
+ p[0] = 0
+
+def p_error(p):
+ print("Syntax error at '%s'" % p.value)
+
+import ply.yacc as yacc
+yacc.yacc()
+
+while True:
+ try:
+ s = raw_input('calc > ') # use input() on Python 3
+ except EOFError:
+ break
+ yacc.parse(s)
+```
Bug Reports and Patches
=======================