|
|
1.1 root 1: .\" @(#)ss6 6.1 (Berkeley) 5/8/86
2: .\"
3: .SH
4: 6: Precedence
5: .PP
6: There is one common situation
7: where the rules given above for resolving conflicts are not sufficient;
8: this is in the parsing of arithmetic expressions.
9: Most of the commonly used constructions for arithmetic expressions can be naturally
10: described by the notion of
11: .I precedence
12: levels for operators, together with information about left
13: or right associativity.
14: It turns out that ambiguous grammars with appropriate disambiguating rules
15: can be used to create parsers that are faster and easier to
16: write than parsers constructed from unambiguous grammars.
17: The basic notion is to write grammar rules
18: of the form
19: .DS
20: expr : expr OP expr
21: .DE
22: and
23: .DS
24: expr : UNARY expr
25: .DE
26: for all binary and unary operators desired.
27: This creates a very ambiguous grammar, with many parsing conflicts.
28: As disambiguating rules, the user specifies the precedence, or binding
29: strength, of all the operators, and the associativity
30: of the binary operators.
31: This information is sufficient to allow Yacc to resolve the parsing conflicts
32: in accordance with these rules, and construct a parser that realizes the desired
33: precedences and associativities.
34: .PP
35: The precedences and associativities are attached to tokens in the declarations section.
36: This is done by a series of lines beginning with a Yacc keyword: %left, %right,
37: or %nonassoc, followed by a list of tokens.
38: All of the tokens on the same line are assumed to have the same precedence level
39: and associativity; the lines are listed in
40: order of increasing precedence or binding strength.
41: Thus,
42: .DS
43: %left \'+\' \'\-\'
44: %left \'*\' \'/\'
45: .DE
46: describes the precedence and associativity of the four arithmetic operators.
47: Plus and minus are left associative, and have lower precedence than
48: star and slash, which are also left associative.
49: The keyword %right is used to describe right associative operators,
50: and the keyword %nonassoc is used to describe operators, like
51: the operator .LT. in Fortran, that may not associate with themselves; thus,
52: .DS
53: A .LT. B .LT. C
54: .DE
55: is illegal in Fortran, and such an operator would be described with the keyword
56: %nonassoc in Yacc.
57: As an example of the behavior of these declarations, the description
58: .DS
59: %right \'=\'
60: %left \'+\' \'\-\'
61: %left \'*\' \'/\'
62:
63: %%
64:
65: expr : expr \'=\' expr
66: | expr \'+\' expr
67: | expr \'\-\' expr
68: | expr \'*\' expr
69: | expr \'/\' expr
70: | NAME
71: ;
72: .DE
73: might be used to structure the input
74: .DS
75: a = b = c*d \- e \- f*g
76: .DE
77: as follows:
78: .DS
79: a = ( b = ( ((c*d)\-e) \- (f*g) ) )
80: .DE
81: When this mechanism is used,
82: unary operators must, in general, be given a precedence.
83: Sometimes a unary operator and a binary operator
84: have the same symbolic representation, but different precedences.
85: An example is unary and binary \'\-\'; unary minus may be given the same
86: strength as multiplication, or even higher, while binary minus has a lower strength than
87: multiplication.
88: The keyword, %prec, changes the precedence level associated with a particular grammar rule.
89: %prec appears immediately after the body of the grammar rule, before the action or closing semicolon,
90: and is followed by a token name or literal.
91: It
92: causes the precedence of the grammar rule to become that of the following token name or literal.
93: For example, to make unary minus have the same precedence as multiplication the rules might resemble:
94: .DS
95: %left \'+\' \'\-\'
96: %left \'*\' \'/\'
97:
98: %%
99:
100: expr : expr \'+\' expr
101: | expr \'\-\' expr
102: | expr \'*\' expr
103: | expr \'/\' expr
104: | \'\-\' expr %prec \'*\'
105: | NAME
106: ;
107: .DE
108: .PP
109: A token declared
110: by %left, %right, and %nonassoc need not be, but may be, declared by %token as well.
111: .PP
112: The precedences and associativities are used by Yacc to
113: resolve parsing conflicts; they give rise to disambiguating rules.
114: Formally, the rules work as follows:
115: .IP 1.
116: The precedences and associativities are recorded for those tokens and literals
117: that have them.
118: .IP 2.
119: A precedence and associativity is associated with each grammar rule; it is the precedence
120: and associativity of the last token or literal in the body of the rule.
121: If the %prec construction is used, it overrides this default.
122: Some grammar rules may have no precedence and associativity associated with them.
123: .IP 3.
124: When there is a reduce/reduce conflict, or there is a shift/reduce conflict
125: and either the input symbol or the grammar rule has no precedence and associativity,
126: then the two disambiguating rules given at the beginning of the section are used,
127: and the conflicts are reported.
128: .IP 4.
129: If there is a shift/reduce conflict, and both the grammar rule and the input character
130: have precedence and associativity associated with them, then the conflict is resolved
131: in favor of the action (shift or reduce) associated with the higher precedence.
132: If the precedences are the same, then the associativity is used; left
133: associative implies reduce, right associative implies shift, and nonassociating
134: implies error.
135: .PP
136: Conflicts resolved by precedence are not counted in the number of shift/reduce and reduce/reduce
137: conflicts reported by Yacc.
138: This means that mistakes in the specification of precedences may
139: disguise errors in the input grammar; it is a good idea to be sparing
140: with precedences, and use them in an essentially ``cookbook'' fashion,
141: until some experience has been gained.
142: The
143: .I y.output
144: file
145: is very useful in deciding whether the parser is actually doing
146: what was intended.
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.