chiark / gitweb /
Import upstream version 5.3.
[mup] / mup / docs / uguide / ifclause.html
1 <HTML>
2 <HEAD><TITLE>
3 Generalized conditionals
4 </TITLE></HEAD>
5 <BODY>
6 <P>
7 &nbsp;&nbsp;&nbsp;<A HREF="macros.html">&lt;-- previous page</A>
8
9 &nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<A HREF="index.html">Table of Contents</A>&nbsp;&nbsp;&nbsp;&nbsp;<A HREF="include.html">next page --&gt;</A>
10 </P>
11           
12 <H3>
13 Generalized conditionals
14 </H3>
15 <P>
16 Mup also supports more general &quot;if&quot; clauses. If you happen to be
17 familiar with the preprocessors for the C and C++ programming
18 languages, Mup &quot;if&quot; clauses are very similar.
19 If you're not, that's okay, since things are explained below.
20 Also, some of the operations are really very rarely needed, so if
21 you find some of them confusing, you just can skip past this section;
22 you'll likely never have a need for the complicated operations anyway.
23 </P>
24 <P>
25 The general form is
26 <BR><PRE>
27 <B>if</B> <I>condition</I> <B>then</B> <I>Mup statements</I> <B>else</B> <I>Mup statements</I> <B>endif</B>
28 </PRE><BR>
29 As with the &quot;ifdef,&quot; the &quot;else&quot; and second set of Mup statements is optional.
30 </P>
31 <P>
32 One form of &quot;if&quot; is really just a variation of ifdef. It uses the
33 keyword &quot;defined&quot; followed by a macro name. So
34 <BR><PRE>
35   ifdef DUET
36 </PRE><BR>
37 could also be written
38 <BR><PRE>
39   if defined DUET then
40 </PRE><BR>
41 You may put a set of parentheses around the macro name for clarity
42 if you wish:
43 <BR><PRE>
44   if defined(DUET) then
45 </PRE><BR>
46 </P>
47 <P>
48 The ! is used to mean &quot;not,&quot; so
49 <BR><PRE>
50   ifndef TRIO
51 </PRE><BR>
52 could also be written as
53 <BR><PRE>
54   if ! defined(TRIO) then
55 </PRE><BR>
56 </P>
57 <P>
58 So far, this just looks longer, so what's the advantage?
59 The difference is that ifdef and ifndef can only be used to check if a single
60 macro is defined or not, whereas the &quot;if&quot; condition is much more general,
61 and therefore much more powerful.
62 Decisions can be based on the values of macros, not just whether they are
63 defined or not, and can also be based on more than one macro at a time,
64 Here is an example of a condition based on several macros at once:
65 <BR><PRE>
66  if defined(FULL_SCORE) &amp;&amp; defined(TRANSPOSE_UP) &amp;&amp; ! defined(MIDI) then
67 </PRE><BR>
68 would be true only if both FULL_SCORE and TRANSPOSE_UP were defined,
69 but MIDI was not defined. The &amp;&amp; means &quot;and.&quot;
70 There is also || which means &quot;or,&quot; so
71 <BR><PRE>
72  if defined(CELLO) || defined(STRINGBASS)
73 </PRE><BR>
74 would be true as long as at least one of the macros was defined.
75 </P>
76 <P>
77 The condition can also include numbers and macros used as numeric values
78 in arithmetic and comparisons.  For example,
79 <BR><PRE>
80   define STAFFS 3 @
81   define S 5 @
82   if STAFFS &gt; 5 then
83      // ... this would not be executed, since 3 is not greater than 5
84   endif
85   if 2 &lt;= STAFFS then
86      // ... This would be executed, since 2 is less than or equal to 3
87   endif
88   if STAFFS + 1 == S - 1 then
89      // ... This would be executed, since 3+1 equals 5-1
90   endif
91 </PRE><BR>
92 Note that the symbol to test for &quot;equals&quot; is two equals signs, not just
93 one. This is to be consistent with what is used in the C and C++ languages.
94 The operators for comparisons are:
95 <TABLE BORDER=4>
96 <TR>
97 <TD>&lt;</TD>   <TD>less than</TD>
98 </TR>
99 <TR>
100 <TD>&gt;</TD>   <TD>greater than</TD>
101 </TR>
102 <TR>
103 <TD>&lt;=</TD>  <TD>less than or equal</TD>
104 </TR>
105 <TR>
106 <TD>&gt;=</TD>  <TD>greater than or equal</TD>
107 </TR>
108 <TR>
109 <TD>==</TD>     <TD>equal</TD>
110 </TR>
111 <TR>
112 <TD>!=</TD>     <TD>not equal</TD>
113 </TR>
114 </TABLE>
115
116 </P>
117 <P>
118 Note that the values in the conditions can only be either literal numbers
119 or macros whose values evaluate to a number. They cannot be things like
120 <A HREF="param.html">Mup parameters.</A>
121 A macro which is not defined is treated as having a value of zero.
122 Macro values are substituted for macro names just as elsewhere in Mup,
123 so if you use a macro whose resulting value does not evaulate to a number,
124 you may get an error or other unexpected result.
125 </P>
126 <P>
127 If you are familiar with &quot;octal&quot; and &quot;hexadecimal&quot; numbers, they can be
128 used, following the C language convention of a leading zero for octal
129 or a leading 0x for hexadecimal. (If you're not familiar with these
130 numbers or conventions, don't worry about it; it's never really necessary
131 to use them. Just make sure you don't accidentally start a number other
132 than a zero with a zero).
133 </P>
134 <P>
135 Values are limited to 32-bit signed numbers. (If you don't know
136 what that means, all you need to know is that you
137 can only use numbers between -2147483648 and 2147483647.
138 </P>
139 <P>
140 Before we introduce the remaining operators, it would be good to discuss
141 two concepts, called precedence and associativity. These determine the
142 order in which operations are done. Consider the following expression:
143 <BR><PRE>
144    5 + 3 * 8
145 </PRE><BR>
146 What is its value? If we just went left to right, we would add 5 and 3,
147 getting 8, then multiple by 8, for a final value of 64. However,
148 multiplication is generally considered to have higher &quot;precedence&quot;
149 than addition, meaning that multiplications should be done before additions.
150 In other words, the expression should actually be treated as
151 <BR><PRE>
152    5 + (3 * 8)
153 </PRE><BR>
154 so we would first multiply 3 by 8, getting 24, and then add 5 and 24,
155 obtaining a final answer of 29.
156 </P>
157 <P>
158 If you really intended the 64 meaning, that could be shown by parentheses,
159 indicating you want the addition to be done first:
160 <BR><PRE>
161    (5 + 3) * 8
162 </PRE><BR>
163 </P>
164 <P>
165 Associativity determines whether operators of equal precedence are done
166 left to right or right to left. Parentheses and
167 all of the operators that have two
168 operands associate left to right, while all the others
169 associate right to left. For example, since addition and subtraction
170 associate left to right, the expression
171 <BR><PRE>
172   10 - 6 - 1
173 </PRE><BR>
174 would be evaluated by first subtracting 6 from 10 to get 4,
175 then subtracting 1, yielding 3.
176 If they associated right to left, first 1 would be subtracted from 6
177 to get 5, which would then be subtracted from 10, yielding 5.
178 So using different associativity can lead to different answers!
179 </P>
180 <P>
181 Since the &quot;not&quot; operator and unary minus associate right to left,
182 in the expression
183 <BR><PRE>
184   ! - (5)
185 </PRE><BR>
186 the unary minus would be applied first to get -5, then the &quot;not&quot; would be
187 applied. But what does &quot;not -5&quot; mean? The &quot;not&quot; operator will treat its
188 operand as a boolean value, with a value of zero meaning false, and
189 any non-zero value being true. Since -5 is not zero, it represents &quot;true,&quot;
190 and &quot;not true&quot; would be &quot;false,&quot; or zero.  By the way,
191 any operator that yields a boolean result
192 (not, logical and, logical or, less than, greater than,
193 less than or equal, greater than or equal, equal, or not equal) will
194 always yield 1 for true, even though any non-zero value could mean true.
195 </P>
196 <P>
197 The operators are listed below. Those on the same line have the same
198 precedence, with those on each line having higher precedence than the
199 lines below.
200 <TABLE BORDER=4>
201 <TR>
202 <TD><B>operators</B></TD>       <TD><B>operations</B></TD>      <TD><B>associativity</B></TD>
203 </TR>
204 <TR>
205 <TD><TT>( )</TT></TD>   <TD>grouping</TD>       <TD>left to right</TD>
206 </TR>
207 <TR>
208 <TD><TT>! ~ - +</TT></TD>       <TD>not, one's complement, unary minus, unary plus</TD> <TD>right to left</TD>
209 </TR>
210 <TR>
211 <TD><TT>* / %</TT></TD> <TD>multiply, divide, modulo</TD>       <TD>left to right</TD>
212 </TR>
213 <TR>
214 <TD><TT>+ -</TT></TD>   <TD>add, subtract</TD>  <TD>left to right</TD>
215 </TR>
216 <TR>
217 <TD><TT>&lt;&lt; &gt;&gt;</TT></TD>     <TD>left shift, right shift</TD>        <TD>left to right</TD>
218 </TR>
219 <TR>
220 <TD><TT>&lt; &lt;= &gt; &gt;=</TT></TD> <TD>less than, less or equal, greater than, greater or equal</TD>       <TD>left to right</TD>
221 </TR>
222 <TR>
223 <TD><TT>== !=</TT></TD> <TD>equal, not equal</TD>       <TD>left to right</TD>
224 </TR>
225 <TR>
226 <TD><TT>&amp;</TT></TD> <TD>bitwise AND</TD>    <TD>left to right</TD>
227 </TR>
228 <TR>
229 <TD><TT>^</TT></TD>     <TD>bitwise XOR</TD>    <TD>left to right</TD>
230 </TR>
231 <TR>
232 <TD><TT>|</TT></TD>     <TD>bitwise OR</TD>     <TD>left to right</TD>
233 </TR>
234 <TR>
235 <TD><TT>&amp;&amp;</TT></TD>    <TD>logical AND</TD>    <TD>left to right</TD>
236 </TR>
237 <TR>
238 <TD><TT>||</TT></TD>    <TD>logical OR</TD>     <TD>left to right</TD>
239 </TR>
240 <TR>
241 <TD><TT>? :</TT></TD>   <TD>interrogation</TD>  <TD>right to left</TD>
242 </TR>
243 </TABLE>
244
245 </P>
246 <HR><P>
247 &nbsp;&nbsp;&nbsp;<A HREF="macros.html">&lt;-- previous page</A>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<A HREF="index.html">Table of Contents</A>&nbsp;&nbsp;&nbsp;&nbsp;<A HREF="include.html">next page --&gt;</A>
248 </P>
249 </BODY></HTML>