[r9259]: docs / branches / 4.1.3 / trunk / rexxref / intro.xml  Maximize  Restore  History

Download this file

2958 lines (2847 with data), 134.8 kB

   1
   2
   3
   4
   5
   6
   7
   8
   9
  10
  11
  12
  13
  14
  15
  16
  17
  18
  19
  20
  21
  22
  23
  24
  25
  26
  27
  28
  29
  30
  31
  32
  33
  34
  35
  36
  37
  38
  39
  40
  41
  42
  43
  44
  45
  46
  47
  48
  49
  50
  51
  52
  53
  54
  55
  56
  57
  58
  59
  60
  61
  62
  63
  64
  65
  66
  67
  68
  69
  70
  71
  72
  73
  74
  75
  76
  77
  78
  79
  80
  81
  82
  83
  84
  85
  86
  87
  88
  89
  90
  91
  92
  93
  94
  95
  96
  97
  98
  99
 100
 101
 102
 103
 104
 105
 106
 107
 108
 109
 110
 111
 112
 113
 114
 115
 116
 117
 118
 119
 120
 121
 122
 123
 124
 125
 126
 127
 128
 129
 130
 131
 132
 133
 134
 135
 136
 137
 138
 139
 140
 141
 142
 143
 144
 145
 146
 147
 148
 149
 150
 151
 152
 153
 154
 155
 156
 157
 158
 159
 160
 161
 162
 163
 164
 165
 166
 167
 168
 169
 170
 171
 172
 173
 174
 175
 176
 177
 178
 179
 180
 181
 182
 183
 184
 185
 186
 187
 188
 189
 190
 191
 192
 193
 194
 195
 196
 197
 198
 199
 200
 201
 202
 203
 204
 205
 206
 207
 208
 209
 210
 211
 212
 213
 214
 215
 216
 217
 218
 219
 220
 221
 222
 223
 224
 225
 226
 227
 228
 229
 230
 231
 232
 233
 234
 235
 236
 237
 238
 239
 240
 241
 242
 243
 244
 245
 246
 247
 248
 249
 250
 251
 252
 253
 254
 255
 256
 257
 258
 259
 260
 261
 262
 263
 264
 265
 266
 267
 268
 269
 270
 271
 272
 273
 274
 275
 276
 277
 278
 279
 280
 281
 282
 283
 284
 285
 286
 287
 288
 289
 290
 291
 292
 293
 294
 295
 296
 297
 298
 299
 300
 301
 302
 303
 304
 305
 306
 307
 308
 309
 310
 311
 312
 313
 314
 315
 316
 317
 318
 319
 320
 321
 322
 323
 324
 325
 326
 327
 328
 329
 330
 331
 332
 333
 334
 335
 336
 337
 338
 339
 340
 341
 342
 343
 344
 345
 346
 347
 348
 349
 350
 351
 352
 353
 354
 355
 356
 357
 358
 359
 360
 361
 362
 363
 364
 365
 366
 367
 368
 369
 370
 371
 372
 373
 374
 375
 376
 377
 378
 379
 380
 381
 382
 383
 384
 385
 386
 387
 388
 389
 390
 391
 392
 393
 394
 395
 396
 397
 398
 399
 400
 401
 402
 403
 404
 405
 406
 407
 408
 409
 410
 411
 412
 413
 414
 415
 416
 417
 418
 419
 420
 421
 422
 423
 424
 425
 426
 427
 428
 429
 430
 431
 432
 433
 434
 435
 436
 437
 438
 439
 440
 441
 442
 443
 444
 445
 446
 447
 448
 449
 450
 451
 452
 453
 454
 455
 456
 457
 458
 459
 460
 461
 462
 463
 464
 465
 466
 467
 468
 469
 470
 471
 472
 473
 474
 475
 476
 477
 478
 479
 480
 481
 482
 483
 484
 485
 486
 487
 488
 489
 490
 491
 492
 493
 494
 495
 496
 497
 498
 499
 500
 501
 502
 503
 504
 505
 506
 507
 508
 509
 510
 511
 512
 513
 514
 515
 516
 517
 518
 519
 520
 521
 522
 523
 524
 525
 526
 527
 528
 529
 530
 531
 532
 533
 534
 535
 536
 537
 538
 539
 540
 541
 542
 543
 544
 545
 546
 547
 548
 549
 550
 551
 552
 553
 554
 555
 556
 557
 558
 559
 560
 561
 562
 563
 564
 565
 566
 567
 568
 569
 570
 571
 572
 573
 574
 575
 576
 577
 578
 579
 580
 581
 582
 583
 584
 585
 586
 587
 588
 589
 590
 591
 592
 593
 594
 595
 596
 597
 598
 599
 600
 601
 602
 603
 604
 605
 606
 607
 608
 609
 610
 611
 612
 613
 614
 615
 616
 617
 618
 619
 620
 621
 622
 623
 624
 625
 626
 627
 628
 629
 630
 631
 632
 633
 634
 635
 636
 637
 638
 639
 640
 641
 642
 643
 644
 645
 646
 647
 648
 649
 650
 651
 652
 653
 654
 655
 656
 657
 658
 659
 660
 661
 662
 663
 664
 665
 666
 667
 668
 669
 670
 671
 672
 673
 674
 675
 676
 677
 678
 679
 680
 681
 682
 683
 684
 685
 686
 687
 688
 689
 690
 691
 692
 693
 694
 695
 696
 697
 698
 699
 700
 701
 702
 703
 704
 705
 706
 707
 708
 709
 710
 711
 712
 713
 714
 715
 716
 717
 718
 719
 720
 721
 722
 723
 724
 725
 726
 727
 728
 729
 730
 731
 732
 733
 734
 735
 736
 737
 738
 739
 740
 741
 742
 743
 744
 745
 746
 747
 748
 749
 750
 751
 752
 753
 754
 755
 756
 757
 758
 759
 760
 761
 762
 763
 764
 765
 766
 767
 768
 769
 770
 771
 772
 773
 774
 775
 776
 777
 778
 779
 780
 781
 782
 783
 784
 785
 786
 787
 788
 789
 790
 791
 792
 793
 794
 795
 796
 797
 798
 799
 800
 801
 802
 803
 804
 805
 806
 807
 808
 809
 810
 811
 812
 813
 814
 815
 816
 817
 818
 819
 820
 821
 822
 823
 824
 825
 826
 827
 828
 829
 830
 831
 832
 833
 834
 835
 836
 837
 838
 839
 840
 841
 842
 843
 844
 845
 846
 847
 848
 849
 850
 851
 852
 853
 854
 855
 856
 857
 858
 859
 860
 861
 862
 863
 864
 865
 866
 867
 868
 869
 870
 871
 872
 873
 874
 875
 876
 877
 878
 879
 880
 881
 882
 883
 884
 885
 886
 887
 888
 889
 890
 891
 892
 893
 894
 895
 896
 897
 898
 899
 900
 901
 902
 903
 904
 905
 906
 907
 908
 909
 910
 911
 912
 913
 914
 915
 916
 917
 918
 919
 920
 921
 922
 923
 924
 925
 926
 927
 928
 929
 930
 931
 932
 933
 934
 935
 936
 937
 938
 939
 940
 941
 942
 943
 944
 945
 946
 947
 948
 949
 950
 951
 952
 953
 954
 955
 956
 957
 958
 959
 960
 961
 962
 963
 964
 965
 966
 967
 968
 969
 970
 971
 972
 973
 974
 975
 976
 977
 978
 979
 980
 981
 982
 983
 984
 985
 986
 987
 988
 989
 990
 991
 992
 993
 994
 995
 996
 997
 998
 999
1000
1001
1002
1003
1004
1005
1006
1007
1008
1009
1010
1011
1012
1013
1014
1015
1016
1017
1018
1019
1020
1021
1022
1023
1024
1025
1026
1027
1028
1029
1030
1031
1032
1033
1034
1035
1036
1037
1038
1039
1040
1041
1042
1043
1044
1045
1046
1047
1048
1049
1050
1051
1052
1053
1054
1055
1056
1057
1058
1059
1060
1061
1062
1063
1064
1065
1066
1067
1068
1069
1070
1071
1072
1073
1074
1075
1076
1077
1078
1079
1080
1081
1082
1083
1084
1085
1086
1087
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149
1150
1151
1152
1153
1154
1155
1156
1157
1158
1159
1160
1161
1162
1163
1164
1165
1166
1167
1168
1169
1170
1171
1172
1173
1174
1175
1176
1177
1178
1179
1180
1181
1182
1183
1184
1185
1186
1187
1188
1189
1190
1191
1192
1193
1194
1195
1196
1197
1198
1199
1200
1201
1202
1203
1204
1205
1206
1207
1208
1209
1210
1211
1212
1213
1214
1215
1216
1217
1218
1219
1220
1221
1222
1223
1224
1225
1226
1227
1228
1229
1230
1231
1232
1233
1234
1235
1236
1237
1238
1239
1240
1241
1242
1243
1244
1245
1246
1247
1248
1249
1250
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262
1263
1264
1265
1266
1267
1268
1269
1270
1271
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282
1283
1284
1285
1286
1287
1288
1289
1290
1291
1292
1293
1294
1295
1296
1297
1298
1299
1300
1301
1302
1303
1304
1305
1306
1307
1308
1309
1310
1311
1312
1313
1314
1315
1316
1317
1318
1319
1320
1321
1322
1323
1324
1325
1326
1327
1328
1329
1330
1331
1332
1333
1334
1335
1336
1337
1338
1339
1340
1341
1342
1343
1344
1345
1346
1347
1348
1349
1350
1351
1352
1353
1354
1355
1356
1357
1358
1359
1360
1361
1362
1363
1364
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
1378
1379
1380
1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392
1393
1394
1395
1396
1397
1398
1399
1400
1401
1402
1403
1404
1405
1406
1407
1408
1409
1410
1411
1412
1413
1414
1415
1416
1417
1418
1419
1420
1421
1422
1423
1424
1425
1426
1427
1428
1429
1430
1431
1432
1433
1434
1435
1436
1437
1438
1439
1440
1441
1442
1443
1444
1445
1446
1447
1448
1449
1450
1451
1452
1453
1454
1455
1456
1457
1458
1459
1460
1461
1462
1463
1464
1465
1466
1467
1468
1469
1470
1471
1472
1473
1474
1475
1476
1477
1478
1479
1480
1481
1482
1483
1484
1485
1486
1487
1488
1489
1490
1491
1492
1493
1494
1495
1496
1497
1498
1499
1500
1501
1502
1503
1504
1505
1506
1507
1508
1509
1510
1511
1512
1513
1514
1515
1516
1517
1518
1519
1520
1521
1522
1523
1524
1525
1526
1527
1528
1529
1530
1531
1532
1533
1534
1535
1536
1537
1538
1539
1540
1541
1542
1543
1544
1545
1546
1547
1548
1549
1550
1551
1552
1553
1554
1555
1556
1557
1558
1559
1560
1561
1562
1563
1564
1565
1566
1567
1568
1569
1570
1571
1572
1573
1574
1575
1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589
1590
1591
1592
1593
1594
1595
1596
1597
1598
1599
1600
1601
1602
1603
1604
1605
1606
1607
1608
1609
1610
1611
1612
1613
1614
1615
1616
1617
1618
1619
1620
1621
1622
1623
1624
1625
1626
1627
1628
1629
1630
1631
1632
1633
1634
1635
1636
1637
1638
1639
1640
1641
1642
1643
1644
1645
1646
1647
1648
1649
1650
1651
1652
1653
1654
1655
1656
1657
1658
1659
1660
1661
1662
1663
1664
1665
1666
1667
1668
1669
1670
1671
1672
1673
1674
1675
1676
1677
1678
1679
1680
1681
1682
1683
1684
1685
1686
1687
1688
1689
1690
1691
1692
1693
1694
1695
1696
1697
1698
1699
1700
1701
1702
1703
1704
1705
1706
1707
1708
1709
1710
1711
1712
1713
1714
1715
1716
1717
1718
1719
1720
1721
1722
1723
1724
1725
1726
1727
1728
1729
1730
1731
1732
1733
1734
1735
1736
1737
1738
1739
1740
1741
1742
1743
1744
1745
1746
1747
1748
1749
1750
1751
1752
1753
1754
1755
1756
1757
1758
1759
1760
1761
1762
1763
1764
1765
1766
1767
1768
1769
1770
1771
1772
1773
1774
1775
1776
1777
1778
1779
1780
1781
1782
1783
1784
1785
1786
1787
1788
1789
1790
1791
1792
1793
1794
1795
1796
1797
1798
1799
1800
1801
1802
1803
1804
1805
1806
1807
1808
1809
1810
1811
1812
1813
1814
1815
1816
1817
1818
1819
1820
1821
1822
1823
1824
1825
1826
1827
1828
1829
1830
1831
1832
1833
1834
1835
1836
1837
1838
1839
1840
1841
1842
1843
1844
1845
1846
1847
1848
1849
1850
1851
1852
1853
1854
1855
1856
1857
1858
1859
1860
1861
1862
1863
1864
1865
1866
1867
1868
1869
1870
1871
1872
1873
1874
1875
1876
1877
1878
1879
1880
1881
1882
1883
1884
1885
1886
1887
1888
1889
1890
1891
1892
1893
1894
1895
1896
1897
1898
1899
1900
1901
1902
1903
1904
1905
1906
1907
1908
1909
1910
1911
1912
1913
1914
1915
1916
1917
1918
1919
1920
1921
1922
1923
1924
1925
1926
1927
1928
1929
1930
1931
1932
1933
1934
1935
1936
1937
1938
1939
1940
1941
1942
1943
1944
1945
1946
1947
1948
1949
1950
1951
1952
1953
1954
1955
1956
1957
1958
1959
1960
1961
1962
1963
1964
1965
1966
1967
1968
1969
1970
1971
1972
1973
1974
1975
1976
1977
1978
1979
1980
1981
1982
1983
1984
1985
1986
1987
1988
1989
1990
1991
1992
1993
1994
1995
1996
1997
1998
1999
2000
2001
2002
2003
2004
2005
2006
2007
2008
2009
2010
2011
2012
2013
2014
2015
2016
2017
2018
2019
2020
2021
2022
2023
2024
2025
2026
2027
2028
2029
2030
2031
2032
2033
2034
2035
2036
2037
2038
2039
2040
2041
2042
2043
2044
2045
2046
2047
2048
2049
2050
2051
2052
2053
2054
2055
2056
2057
2058
2059
2060
2061
2062
2063
2064
2065
2066
2067
2068
2069
2070
2071
2072
2073
2074
2075
2076
2077
2078
2079
2080
2081
2082
2083
2084
2085
2086
2087
2088
2089
2090
2091
2092
2093
2094
2095
2096
2097
2098
2099
2100
2101
2102
2103
2104
2105
2106
2107
2108
2109
2110
2111
2112
2113
2114
2115
2116
2117
2118
2119
2120
2121
2122
2123
2124
2125
2126
2127
2128
2129
2130
2131
2132
2133
2134
2135
2136
2137
2138
2139
2140
2141
2142
2143
2144
2145
2146
2147
2148
2149
2150
2151
2152
2153
2154
2155
2156
2157
2158
2159
2160
2161
2162
2163
2164
2165
2166
2167
2168
2169
2170
2171
2172
2173
2174
2175
2176
2177
2178
2179
2180
2181
2182
2183
2184
2185
2186
2187
2188
2189
2190
2191
2192
2193
2194
2195
2196
2197
2198
2199
2200
2201
2202
2203
2204
2205
2206
2207
2208
2209
2210
2211
2212
2213
2214
2215
2216
2217
2218
2219
2220
2221
2222
2223
2224
2225
2226
2227
2228
2229
2230
2231
2232
2233
2234
2235
2236
2237
2238
2239
2240
2241
2242
2243
2244
2245
2246
2247
2248
2249
2250
2251
2252
2253
2254
2255
2256
2257
2258
2259
2260
2261
2262
2263
2264
2265
2266
2267
2268
2269
2270
2271
2272
2273
2274
2275
2276
2277
2278
2279
2280
2281
2282
2283
2284
2285
2286
2287
2288
2289
2290
2291
2292
2293
2294
2295
2296
2297
2298
2299
2300
2301
2302
2303
2304
2305
2306
2307
2308
2309
2310
2311
2312
2313
2314
2315
2316
2317
2318
2319
2320
2321
2322
2323
2324
2325
2326
2327
2328
2329
2330
2331
2332
2333
2334
2335
2336
2337
2338
2339
2340
2341
2342
2343
2344
2345
2346
2347
2348
2349
2350
2351
2352
2353
2354
2355
2356
2357
2358
2359
2360
2361
2362
2363
2364
2365
2366
2367
2368
2369
2370
2371
2372
2373
2374
2375
2376
2377
2378
2379
2380
2381
2382
2383
2384
2385
2386
2387
2388
2389
2390
2391
2392
2393
2394
2395
2396
2397
2398
2399
2400
2401
2402
2403
2404
2405
2406
2407
2408
2409
2410
2411
2412
2413
2414
2415
2416
2417
2418
2419
2420
2421
2422
2423
2424
2425
2426
2427
2428
2429
2430
2431
2432
2433
2434
2435
2436
2437
2438
2439
2440
2441
2442
2443
2444
2445
2446
2447
2448
2449
2450
2451
2452
2453
2454
2455
2456
2457
2458
2459
2460
2461
2462
2463
2464
2465
2466
2467
2468
2469
2470
2471
2472
2473
2474
2475
2476
2477
2478
2479
2480
2481
2482
2483
2484
2485
2486
2487
2488
2489
2490
2491
2492
2493
2494
2495
2496
2497
2498
2499
2500
2501
2502
2503
2504
2505
2506
2507
2508
2509
2510
2511
2512
2513
2514
2515
2516
2517
2518
2519
2520
2521
2522
2523
2524
2525
2526
2527
2528
2529
2530
2531
2532
2533
2534
2535
2536
2537
2538
2539
2540
2541
2542
2543
2544
2545
2546
2547
2548
2549
2550
2551
2552
2553
2554
2555
2556
2557
2558
2559
2560
2561
2562
2563
2564
2565
2566
2567
2568
2569
2570
2571
2572
2573
2574
2575
2576
2577
2578
2579
2580
2581
2582
2583
2584
2585
2586
2587
2588
2589
2590
2591
2592
2593
2594
2595
2596
2597
2598
2599
2600
2601
2602
2603
2604
2605
2606
2607
2608
2609
2610
2611
2612
2613
2614
2615
2616
2617
2618
2619
2620
2621
2622
2623
2624
2625
2626
2627
2628
2629
2630
2631
2632
2633
2634
2635
2636
2637
2638
2639
2640
2641
2642
2643
2644
2645
2646
2647
2648
2649
2650
2651
2652
2653
2654
2655
2656
2657
2658
2659
2660
2661
2662
2663
2664
2665
2666
2667
2668
2669
2670
2671
2672
2673
2674
2675
2676
2677
2678
2679
2680
2681
2682
2683
2684
2685
2686
2687
2688
2689
2690
2691
2692
2693
2694
2695
2696
2697
2698
2699
2700
2701
2702
2703
2704
2705
2706
2707
2708
2709
2710
2711
2712
2713
2714
2715
2716
2717
2718
2719
2720
2721
2722
2723
2724
2725
2726
2727
2728
2729
2730
2731
2732
2733
2734
2735
2736
2737
2738
2739
2740
2741
2742
2743
2744
2745
2746
2747
2748
2749
2750
2751
2752
2753
2754
2755
2756
2757
2758
2759
2760
2761
2762
2763
2764
2765
2766
2767
2768
2769
2770
2771
2772
2773
2774
2775
2776
2777
2778
2779
2780
2781
2782
2783
2784
2785
2786
2787
2788
2789
2790
2791
2792
2793
2794
2795
2796
2797
2798
2799
2800
2801
2802
2803
2804
2805
2806
2807
2808
2809
2810
2811
2812
2813
2814
2815
2816
2817
2818
2819
2820
2821
2822
2823
2824
2825
2826
2827
2828
2829
2830
2831
2832
2833
2834
2835
2836
2837
2838
2839
2840
2841
2842
2843
2844
2845
2846
2847
2848
2849
2850
2851
2852
2853
2854
2855
2856
2857
2858
2859
2860
2861
2862
2863
2864
2865
2866
2867
2868
2869
2870
2871
2872
2873
2874
2875
2876
2877
2878
2879
2880
2881
2882
2883
2884
2885
2886
2887
2888
2889
2890
2891
2892
2893
2894
2895
2896
2897
2898
2899
2900
2901
2902
2903
2904
2905
2906
2907
2908
2909
2910
2911
2912
2913
2914
2915
2916
2917
2918
2919
2920
2921
2922
2923
2924
2925
2926
2927
2928
2929
2930
2931
2932
2933
2934
2935
2936
2937
2938
2939
2940
2941
2942
2943
2944
2945
2946
2947
2948
2949
2950
2951
2952
2953
2954
2955
2956
2957
<!--####################################c#####################################
#
# Description: Open Object Rexx: Reference SGML file.
#
# Copyright (c) 2005-2009, Rexx Language Association. All rights reserved.
# Portions Copyright (c) 2004, IBM Corporation. All rights reserved.
#
# This program and the accompanying materials are made available under
# the terms of the Common Public License v1.0 which accompanies this
# distribution. A copy is also available at the following address:
# http://www.oorexx.org/license.html
#
# Redistribution and use in source and binary forms, with or
# without modification, are permitted provided that the following
# conditions are met:
#
# Redistributions of source code must retain the above copyright
# notice, this list of conditions and the following disclaimer.
# Redistributions in binary form must reproduce the above copyright
# notice, this list of conditions and the following disclaimer in
# the documentation and/or other materials provided with the distribution.
#
# Neither the name of Rexx Language Association nor the names
# of its contributors may be used to endorse or promote products
# derived from this software without specific prior written permission.
#
# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
# "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
# LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
# FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
# OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
# SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED
# TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA,
# OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
# OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
# NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
# SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
#
# Author(s):
# W. David Ashley <dashley@us.ibm.com>
#
#########################################################################
-->
<chapter id="intro"><title>Open Object Rexx General Concepts</title>
<indexterm><primary>general concepts</primary></indexterm>
<para>The Rexx language is particularly suitable for:
<itemizedlist>
<listitem><para>Application scripting</para></listitem>
<listitem><para>Command procedures</para></listitem>
<listitem><para>Application front ends</para></listitem>
<listitem><para>User-defined macros (such as editor subcommands)</para>
</listitem>
<listitem><para>Prototyping</para></listitem>
<listitem><para>Personal computing</para></listitem>
</itemizedlist></para>
<para> As an object-oriented language, Rexx provides data
encapsulation,
polymorphism, an object class hierarchy, class-based inheritance of methods,
and concurrency. It includes a number of useful base classes and allows you
create new object classes of your own.</para>
<para>
Open Object Rexx is compatible with earlier Rexx versions, both non-object based Rexx and IBM's Object
Rexx. It has the usual structured-programming instructions, for example IF, SELECT,
DO WHILE, and LEAVE, and a number of useful built-in functions.</para>
<para>The language imposes few restrictions
<indexterm><primary>programming restrictions</primary></indexterm>
<indexterm><primary>restrictions</primary>
<secondary>in programming</secondary></indexterm>
on the program format. There can be more than one clause on a line, or a single
clause can occupy more than one line. Any indentation scheme is allowed. You can,
therefore, code programs in a format that emphasizes their structure,
making them easier to read.</para>
<para>There is no limit to the size of variable values, as long as
all values fit into the storage available. There are no restrictions on
the types of data that variables can contain.</para>
<indexterm><primary>execution</primary>
<secondary>by language processor</secondary></indexterm>
<indexterm><primary>language</primary>
<secondary>processor execution</secondary></indexterm>
<para>
A language processor (interpreter) runs Rexx programs. That is, the program runs line by line and word
by word, without first being translated to machine language (compiled.) One of the advantages of this
is that you can fix the error and rerun the program faster than when using a compiler.
</para>
<para>
<emphasis role="bold">Note:</emphasis> Open Object Rexx also supplies the
<computeroutput>rexxc</computeroutput> program that can be used to <emphasis
role="italic">tokenize</emphasis> Rexx programs. Tokenizing a program is not the same as compiling a
program to machine language. See <emphasis role="italic">Appendix A. Distributing Programs without
Source</emphasis> of the <emphasis role="italic">Open Object Rexx Programming
Guide</emphasis> for details on <computeroutput>rexxc</computeroutput> and tokenizing.
</para>
<section id="object"><title>What Is Object-Oriented Programming?</title>
<indexterm><primary>object-oriented programming</primary></indexterm>
<para> Object-oriented
programming is a way to write computer programs by focusing not on the
instructions
and operations a program uses to manipulate data, but on the data itself.
First, the program simulates, or models, objects in the physical world as
closely as possible. Then the objects interact with each other to produce
the desired result.</para>
<para>Real-world objects, such as a company's employees, money in a bank
account, or a report, are stored as data so the computer can act upon it.
For example, when you print a report, print is the action
and report is the object acted upon. Essentially, the objects are the
"nouns", while the actions are the "verbs".
</para>
</section>
<section id="module"><title>Modularizing Data</title>
<indexterm><primary>data</primary>
<secondary>modularization</secondary></indexterm>
<indexterm><primary>modularizing data</primary></indexterm>
<para> In conventional, structured programming, actions like print
are often isolated from the data by placing them in subroutines or modules.
A module typically contains an operation for implementing one simple action.
You might have a PRINT module, a SEND module, an ERASE module. The data these
modules operate on must be constructed by the programmer and passed to the
modules to perform an action.
</para>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="Modules" scale="65">
</imageobject>
</mediaobject>
<para>But with object-oriented programming, it is the data that is modularized.
And each data module includes its own operations for performing actions directly
related to its data. The programmer that uses the objects need only be aware of the
operations an object performs and not how the data is organized internally.
</para>
<figure><title>Modular Data&mdash;a Report Object</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="ReportObject" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>In the case of report, the report object would contain its own built-in
PRINT, SEND, ERASE, and FILE operations.</para>
<para>Object-oriented programming lets you model real-world objects&mdash;even
very complex ones&mdash;precisely and elegantly. As a result, object manipulation
becomes easier and computer instructions become simpler and can be modified
later with minimal effort.</para>
<para>Object-oriented programming <emphasis>hides</emphasis> any information
that is not important for acting on an object, thereby concealing the object's
complexities. Complex tasks can then be initiated simply, at a very high level.
</para>
</section>
<section id="objects"><title>Modeling Objects</title>
<para>In object-oriented programming, objects are modeled to real-world objects.
A real-world object has actions related to it and characteristics of its own.
</para>
<para>Take a ball, for example. A ball can be acted on&mdash;rolled, tossed,
thrown, bounced, caught. But it also has its own physical characteristics&mdash;size,
shape, composition, weight, color, speed, position. An accurate data model
of a real ball would define not only the physical characteristics but
<emphasis>all</emphasis> related actions and characteristics in one package:
</para>
<figure><title>A Ball Object</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="BallObject" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>In object-oriented programming,
objects are the basic building blocks&mdash;the fundamental units of data.</para>
<indexterm><primary>object</primary>
<secondary>definition</secondary></indexterm>
<indexterm><primary>object</primary>
<secondary>kinds of</secondary></indexterm>
<para>There are many kinds of objects; for example, character
strings, collections, and input and output streams. An object&mdash;such as
a character string&mdash;always consists of two parts: the possible actions
or operations related to it, and its characteristics or variables. A variable
has a <emphasis>name</emphasis>, and an associated data value
that can change over time.
The variables represent the internal state of the object, and can be directly
accessed only by the code that implements the object's actions.
</para>
<figure><title>Ball Object with Variable Names and Values</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="BallObjectData" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>To access an object's data, you must always specify an
action. For example, suppose the object is the number
<computeroutput>5</computeroutput>. Its actions
might include addition, subtraction, multiplication, and division. Each of
these actions is an interface to the object's data. The data is said to
be <emphasis>encapsulated</emphasis>
<indexterm><primary>encapsulation of data</primary></indexterm>
<indexterm><primary>data</primary>
<secondary>encapsulation</secondary></indexterm>
because the only way to access it
is through one of these surrounding actions. The encapsulated internal
characteristics of an object are its
<indexterm><primary>variables</primary>
<secondary>in objects</secondary></indexterm>
<emphasis>variables</emphasis>. The variables are associated
with an object and exist for the lifetime of that object:</para>
<figure><title>Encapsulated 5 Object</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="EncapsulatedObject" scale="70">
</imageobject>
</mediaobject>
</figure>
</section>
<section id="interac"><title>How Objects Interact</title>
<indexterm><primary>messages</primary></indexterm>
<para>The actions defined by an object
are its only interface to other objects. Actions form a kind of &quot;wall&quot;
that encapsulates the object, and shields its internal information from outside
objects. This shielding is called
<indexterm><primary>information hiding</primary></indexterm>
<emphasis role="italic">information hiding.</emphasis> Information
hiding protects an object's data from corruption by outside objects, and
also protects outside objects from relying on another object's private
data, which can change without warning.</para>
<para>One object can act upon another (or
cause it to act) only by calling that object's actions, namely by sending
<emphasis>messages</emphasis>. Objects respond to these messages by performing
an action, returning data, or both. A message to an object must specify:
<itemizedlist>
<listitem><para>A receiving object</para></listitem>
<listitem>
<para>The &quot;message send&quot; symbol, ~,
which is called the <emphasis>twiddle</emphasis>
<indexterm><primary>~ (tilde or twiddle)</primary></indexterm>
<indexterm><primary>tilde (~)</primary></indexterm>
<indexterm><primary>twiddle (~)</primary></indexterm>
<indexterm><primary>message-send operator (~)</primary></indexterm>
</para></listitem>
<listitem><para>The action and, optionally in parentheses, any parameters
required by the action</para></listitem>
</itemizedlist></para>
<para>So the message format looks like this: </para>
<programlisting>
object~action(parameters)
</programlisting>
<para>Assume that the object is the string
<computeroutput>!iH.</computeroutput> Sending it a message
to use its REVERSE action: </para>
<programlisting>
"!iH"~reverse
</programlisting>
<para>returns the string object <computeroutput>Hi!.</computeroutput></para>
</section>
<section id="methods"><title>Methods</title>
<indexterm><primary>method</primary>
<secondary>definition</secondary></indexterm>
<para>Sending a message to
an object results in performing some action; that is, it executes
some underlying code. The action-generating code is called a
<emphasis>method</emphasis>. When you send a message to an object,
the message is the name of the target method.
Method names are character strings like REVERSE. In the
preceding example, sending the <computeroutput>reverse</computeroutput> message
to the <computeroutput>!iH</computeroutput> object causes it to run the
REVERSE method. Most objects are capable
of more than one action, and so have a number of available methods.</para>
<para>The classes Rexx provides include their own predefined methods. The Message
class, for example, has the COMPLETED, INIT, NOTIFY, RESULT, SEND, and START
methods. When you create your own classes, you can write new methods for them
in Rexx code. Much of the object programming in Rexx is writing the code for
the methods you create.</para>
</section>
<section id="xpolym"><title>Polymorphism</title>
<indexterm><primary>variables</primary>
<secondary>aquiring</secondary></indexterm>
<indexterm><primary>polymorphism</primary></indexterm>
<para>Rexx lets you send the same message to objects that are different:</para>
<programlisting>
"!iH"~reverse /* Reverses the characters "!iH" to form "Hi!" */
pen~reverse /* Reverses the direction of a plotter pen */
ball~reverse /* Reverses the direction of a moving ball */
</programlisting>
<para>As long as each object has its own REVERSE method, REVERSE runs
even if the programming implementation is different for each object. This
ability to hide different functions behind a common interface is called
<emphasis>polymorphism</emphasis>. As a result of information
hiding, each object in the previous example knows only its own version of
REVERSE. And even though the objects are different, each reverses itself as
dictated by its own code.</para>
<para>Although the <computeroutput>!iH</computeroutput> object's
REVERSE code is different from
the plotter pen's, the method name can be the same because Rexx keeps
track of the methods each object owns. The ability to reuse the same method
name so that one message can initiate more than one function is another feature
of polymorphism. You do not need to have several message names like
REVERSE_STRING,
REVERSE_PEN, REVERSE_BALL. This keeps method-naming schemes simple and makes
complex programs easy to follow and modify.</para>
<para>The ability to hide the various implementations of a method while leaving
the interface the same illustrates polymorphism at its lowest level. On a
higher level, polymorphism permits extensive code reuse.</para>
</section>
<section id="xclass"><title>Classes and Instances</title>
<indexterm><primary>class</primary>
<secondary>definition</secondary></indexterm>
<indexterm><primary>instances</primary>
<secondary>definition</secondary></indexterm>
<para>In Rexx, objects are
organized into <emphasis>classes</emphasis>. Classes are like templates;
they define the methods and variables that a group of similar objects have
in common and store them in one place.</para>
<para>If you write a program to manipulate some screen icons, for example, you
might create an Icon class. In that Icon class you can include all the icon
objects with similar actions and characteristics:</para>
<figure><title>A Simple Class</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="SimpleClass" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>All the icon objects might use common methods like DRAW or ERASE. They
might contain common variables like position, color, or size. What makes each
icon object different from one another is the data assigned to its variables.
For the Windows system icon, it might be position="20,20",
while for the shredder it is "20,30" and for information it is "20,40":</para>
<figure><title>Icon Class</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="IconClass" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>Objects that belong to a class are called
<emphasis>instances</emphasis> of that class. As instances of the Icon class,
the Windows system icon, shredder icon, and
information icon <emphasis>acquire</emphasis> the methods and variables
of that class. Instances behave as if they each had their own methods and
variables of the same name. All instances, however, have their own unique
properties&mdash;the <emphasis>data</emphasis> associated with the variables.
Everything else can be stored at the class level.</para>
<figure><title>Instances of the Icon Class</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="IconClassInstances" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>If you must update or change a particular method, you
only have to change it at one place, at the class level. This single update
is then acquired by every new instance that uses the method.</para>
<para>A class that can create instances
of an object is called an <emphasis>object class</emphasis>.
<indexterm><primary>object classes</primary></indexterm>
The Icon class
is an object class you can use to create other objects with similar properties,
such as an application icon or a drives icon.</para>
<para>An object class is like a factory for producing instances of the objects.
</para>
</section>
<section id="abstrac"><title>Data Abstraction</title>
<indexterm><primary>data</primary>
<secondary>abstraction</secondary></indexterm>
<para>The ability to create
new, high-level data types and organize them into a meaningful class structure
is called <emphasis>data abstraction</emphasis>. Data abstraction is at
the core of object-oriented programming. Once you model objects with real-world
properties from the basic data types, you can continue creating, assembling,
and combining them into increasingly complex objects. Then you can use these
objects as if they were part of the original programming language.</para>
</section>
<section id="sub"><title>Subclasses, Superclasses, and Inheritance</title>
<indexterm><primary>inheritance</primary></indexterm>
<indexterm><primary>class</primary>
<secondary>subclasses</secondary></indexterm>
<indexterm><primary>class</primary>
<secondary>superclasses</secondary></indexterm>
<indexterm><primary>multiple inheritance</primary></indexterm>
<indexterm><primary>subclasses</primary></indexterm>
<indexterm><primary>superclasses</primary></indexterm>
<para>When you write your first object-oriented program, you do not have to begin
your real-world modeling from scratch. Rexx provides predefined classes and
methods. From there you can create additional classes and methods of your
own, according to your needs.</para>
<para>Rexx classes are hierarchical. Any subclass (a class below
another class in the hierarchy) <emphasis>inherits</emphasis> the methods and
variables of one or more <emphasis>superclasses</emphasis> (classes above a
class in the hierarchy):</para>
<figure><title>Superclass and Subclasses</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="Subclasses" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>You can add a class to an existing superclass. For example, you might add
the Icon class to the Screen-Object superclass:</para>
<figure><title>The Screen-Object Superclass</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="ScreenObject" scale="70">
</imageobject>
</mediaobject>
</figure>
<para>In this way, the subclass inherits additional methods
from the superclass. A class can have more than one superclass, for example,
subclass Bitmap might have the superclasses Screen-Object and Art-Object.
Acquiring methods and variables from more than one superclass is known as
<emphasis>multiple inheritance</emphasis>:</para>
<figure><title>Multiple Inheritance</title>
<mediaobject>
<imageobject>
<!-- Note! - if we include a /imagedata tag we get an error for DSSSL! -->
<imagedata fileref="MultipleInheritance" scale="70">
</imageobject>
</mediaobject>
</figure>
</section>
<section id="structu"><title>Structure and General Syntax</title>
<indexterm><primary>language</primary>
<secondary>structure and syntax</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>syntax</primary>
<secondary>general</secondary></indexterm>
<indexterm><primary>structure and syntax</primary></indexterm>
<indexterm><primary>variables</primary>
<secondary>aquiring</secondary></indexterm>
<para>A Rexx program is built from a series of
<emphasis>clauses</emphasis> that are composed of: </para>
<itemizedlist>
<listitem><para>Zero or more whitespace characters (blank or horizontal tabs)
(which are ignored)</para></listitem>
<listitem><para>A sequence of tokens (see
<link linkend="xtokens">Tokens</link>)</para></listitem>
<listitem><para>Zero or more whitespace characters (again
ignored)</para></listitem>
<listitem><para>A semicolon (;)
<indexterm><primary>semicolons</primary>
<secondary>within a clause</secondary></indexterm>
delimiter that the line end, certain keywords, or the colon (:)
implies.</para></listitem></itemizedlist>
<para>Conceptually,
each clause is scanned from left to right before processing, and the tokens
composing it are identified. Instruction keywords are recognized at this stage,
comments are removed, and sequences of whitespace characters (except within
literal strings) are converted to single blanks. Whitespace characters adjacent
to operator characters and special
<indexterm><primary>blanks</primary>
<secondary>adjacent to special character</secondary></indexterm>
<indexterm><primary>whitespace</primary>
<secondary>adjacent to special character</secondary></indexterm>
characters are also removed.</para>
<section id="characters"><title>Characters</title>
<indexterm><primary>character</primary>
<secondary>definition</secondary></indexterm>
<para>A <emphasis>character</emphasis> is a member of a
defined set of elements that is used for the
control or representation of data. You can usually enter a character with
a single keystroke. The coded representation of a character
is its representation
in digital form. A character, the letter A, for example, differs from
its <emphasis>coded representation</emphasis> or encoding.
Various coded character
sets (such as ASCII and EBCDIC) use different encodings
for the letter A (decimal
values 65 and 193, respectively). This book uses characters to convey meanings
and not to imply a specific character code, except where otherwise stated.
The exceptions are certain built-in functions that convert between characters
and their representations. The functions C2D, C2X, D2C, X2C, and XRANGE depend
on the character set used.</para>
<indexterm><primary>code page</primary></indexterm>
<indexterm><primary>page, code</primary></indexterm>
<para>A code page specifies the encodings for each character in a set. Be aware
that:
<itemizedlist>
<listitem><para>Some code pages do not contain all characters that Rexx defines
as valid (for example, the logical NOT character).</para></listitem>
<listitem><para>Some characters that Rexx defines
as valid have different encodings in
different code pages, for example the exclamation mark (!).</para></listitem>
</itemizedlist></para>
</section>
<section id="whitespace"><title>Whitespace</title>
<indexterm><primary>whitespace</primary></indexterm>
<para>A whitespace character is one that the interpreter recognizes as a "blank"
or "space" character. There are two characters used by Rexx as whitespace that
can be used interchangeably:
</para>
<variablelist>
<varlistentry><term><emphasis role="bold">(blank)</emphasis></term>
<listitem><para>A "blank" or "space" character. This is represented by '20'X in
ASCII implementations.
</para></listitem></varlistentry>
<varlistentry><term><emphasis role="bold">(horizontal tab)</emphasis></term>
<listitem><para>A "tab". This is represented by '09'X in ASCII implementations.
</para></listitem></varlistentry>
</variablelist>
<para>Horizontal tabs encountered in Rexx program source are converted into
blanks, allowing tab characters and blanks to be use interchangeably in source.
Additionally, Rexx operations such as the PARSE instruction or the SUBWORD()
built-in function will also accept either blank or tab characters as word
delimiters.</para>
</section>
<section id="cmts"><title>Comments</title>
<indexterm><primary>comments</primary></indexterm>
<para>A comment is a sequence of characters delimited by specific characters.
It is ignored by the program but acts as a separator. For example, a token
containing one comment is treated as two tokens.</para>
<para>The interpreter recognizes the following types of comments:</para>
<itemizedlist>
<listitem><para>A line comment, where the comment is limited to one line
<indexterm><primary>comments</primary>
<secondary>line comment</secondary></indexterm>
</para></listitem>
<listitem><para>The standard Rexx comment, where the comment
can cover several lines
<indexterm><primary>comments</primary>
<secondary>standard comment</secondary></indexterm>
</para></listitem></itemizedlist>
<para>A <emphasis>line comment</emphasis> is
started by two subsequent minus signs (--) and ends at the end
of a line. Example:</para>
<indexterm><primary>examples</primary>
<secondary>line comments</secondary></indexterm>
<programlisting>
"Fred"
"Don&apos;t Panic!"
&apos;You shouldn&apos;&apos;t&apos; -- Same as "You shouldn&apos;t"
&quot;&quot;
</programlisting>
<para>In this example, the language processor processes the statements
from <computeroutput>&apos;Fred&apos;</computeroutput> to
<computeroutput>&apos;You shouldn&apos;&apos;t&apos;</computeroutput>, ignores the words following
the line comment, and continues to process the statement
<computeroutput>&quot;&quot;</computeroutput>.</para>
<para>A <emphasis>standard comment</emphasis> is a sequence of characters
(on one or more lines) delimited by /* and */. Within these delimiters any
characters are allowed.
Standard comments can contain other standard comments, as long as each begins
and ends with the necessary delimiters. They are called
<emphasis>nested comments</emphasis>. Standard comments can be anywhere and
of any length.</para>
<indexterm><primary>examples</primary>
<secondary>standard comments</secondary></indexterm>
<programlisting>
/* This is an example of a valid Rexx comment */
</programlisting>
<para>Take special care when commenting out lines of code containing
<computeroutput>/*</computeroutput> or <computeroutput>*/</computeroutput>
as part of a literal string. Consider the following
program segment: </para>
<programlisting>
01 parse pull input
02 if substr(input,1,5) = "/*123"
03 then call process
04 dept = substr(input,32,5)
</programlisting>
<para>To comment out lines 2 and 3, the following change would be incorrect:
</para>
<programlisting>
01 parse pull input
02 /* if substr(input,1,5) = "/*123"
03 then call process
04 */ dept = substr(input,32,5)
</programlisting>
<para>This is incorrect because the language processor would interpret the
<computeroutput>/*</computeroutput> that is part of the literal string
<computeroutput>/*123</computeroutput> as the start
of a nested standard comment. It would not process the rest of the program
because it would be looking for a matching standard comment end
(<computeroutput>*/</computeroutput>).</para>
<para>You can avoid this type of problem by using concatenation for literal
strings containing <computeroutput>/*</computeroutput> or
<computeroutput>*/</computeroutput>; line 2 would be: </para>
<programlisting>
if substr(input,1,5) = "/" || "*123"
</programlisting>
<para>You could comment out lines 2 and 3 correctly as follows: </para>
<programlisting>
01 parse pull input
02 /* if substr(input,1,5) = "/" || "*123"
03 then call process
04 */ dept = substr(input,32,5)
</programlisting>
<para>Both types of comments can be mixed and nested. However, when
you nest the two types, the type of comment that comes first takes precedence
over the one nested. Here is an example:</para>
<programlisting>
"Fred"
"Don&apos;t Panic!"
&apos;You shouldn&apos;&apos;t&apos; /* Same as "You shouldn&apos;t"
"" -- The null string */
</programlisting>
<para>In this example, the language processor ignores everything after
<computeroutput>&apos;You shouldn&apos;&apos;t&apos;</computeroutput> up to the end of the last
line. In this case, the standard comment has precedence over the line comment.
</para>
<para>When nesting the two comment types, make sure that the start
delimiter of the standard comment <computeroutput>/*</computeroutput> is not
in the line commented out with the line comment signs.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
"Fred"
"Don&apos;t Panic!"
&apos;You shouldn&apos;&apos;t&apos; -- Same as /* "You shouldn&apos;t"
"" The null string */
</programlisting>
<para>This example produces an error because the language processor
ignores the start delimiter of the standard comment, which is commented out
using the line comment.</para>
</section>
<section id="xtokens"><title>Tokens</title>
<indexterm><primary>tokens</primary>
<secondary>description</secondary></indexterm>
<para>A <emphasis>token</emphasis> is the unit of low-level syntax from which
clauses are built. Programs written in Rexx are composed of tokens. Tokens
can be of any length, up to an implementation-restricted maximum. They are
separated by whitespace or comments, or by the nature of the tokens themselves.
The classes of tokens are:
</para>
<itemizedlist>
<listitem><para>Literal strings</para></listitem>
<listitem><para>Hexadecimal strings</para></listitem>
<listitem><para>Binary strings</para></listitem>
<listitem><para>Symbols</para></listitem>
<listitem><para>Numbers</para></listitem>
<listitem><para>Operator characters</para></listitem>
<listitem><para>Special characters</para></listitem></itemizedlist>
<section id="litstrings"><title>Literal Strings</title>
<indexterm><primary>tokens</primary>
<secondary>literal strings</secondary></indexterm>
<indexterm><primary>literal</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>null</primary>
<secondary>strings</secondary></indexterm>
<indexterm><primary>string</primary>
<secondary>as literal constant</secondary></indexterm>
<indexterm><primary>string</primary>
<secondary>as name of function</secondary></indexterm>
<indexterm><primary>string</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>string</primary>
<secondary>null</secondary></indexterm>
<indexterm><primary>string</primary>
<secondary>quotations marks in</secondary></indexterm>
<para>A literal string is a sequence including <emphasis>any</emphasis>
characters except line feed (X"10") and delimited by a single quotation mark
(<computeroutput>&apos;</computeroutput>) or a double quotation mark
(<computeroutput>&quot;</computeroutput>). You use
two consecutive double quotation marks
(<computeroutput>&quot;&quot;</computeroutput>) to represent
one double quotation mark (<computeroutput>"</computeroutput>)
within a string delimited by double
quotation marks. Similarly, you use two consecutive single quotation marks
(<computeroutput>&apos;&apos;</computeroutput>) to represent one single quotation mark
(<computeroutput>&apos;</computeroutput>) within a string delimited by single
quotation marks. A literal string
is a constant and its contents are never modified when it is processed. Literal
strings must be complete on a single line. This means that unmatched quotation
marks can be detected on the line where they occur.</para>
<para>A literal string with no characters (that is, a string of length
<computeroutput>0</computeroutput>) is called a
<emphasis>null string</emphasis>.</para>
<para>These are valid strings: </para>
<programlisting>
"Fred"
"Don&apos;t Panic!"
&apos;You shouldn&apos;&apos;t&apos; /* Same as "You shouldn&apos;t" */
"" /* The null string */
</programlisting>
<para><emphasis role="bold">Implementation maximum:</emphasis>
<indexterm><primary>implementation maximum</primary>
<secondary>literal strings</secondary></indexterm>
<indexterm><primary>literal</primary>
<secondary>implementation maximum</secondary></indexterm>
A literal string has no upper bound on the number of characters, limited on
by available memory.
</para>
<para>Note that a string immediately followed by a left parenthesis is
considered to be the name of a function. If immediately followed by the symbol
<varname>X</varname> or <varname>x</varname>, it is considered to be a
hexadecimal string. If followed immediately by the symbol <varname>B</varname>
or <varname>b</varname>, it is considered to be a binary string.</para>
</section>
<section id="hexastrings"><title>Hexadecimal Strings</title>
<indexterm><primary>hexadecimal</primary>
<secondary>digits</secondary></indexterm>
<indexterm><primary>hexadecimal</primary>
<secondary>strings</secondary>
<tertiary>description</tertiary></indexterm>
<indexterm><primary>string</primary>
<secondary>hexidecimal specification of</secondary></indexterm>
<indexterm><primary>tokens</primary>
<secondary>hexadecimal strings</secondary></indexterm>
<para>A hexadecimal string is a literal string, expressed using
a hexadecimal notation of its encoding. It is any sequence of zero or more
hexadecimal digits
(<computeroutput>0</computeroutput>-<computeroutput>9</computeroutput>,
<computeroutput>a</computeroutput>-<computeroutput>f</computeroutput>,
<computeroutput>A</computeroutput>-<computeroutput>F</computeroutput>),
grouped in pairs. A single leading
0 is assumed, if necessary, at the beginning of the string to make an even
number of hexadecimal digits. The groups of digits are optionally separated
by one or more whitespace characters, and the whole sequence is delimited by
single or double quotation marks and immediately followed by the symbol
<computeroutput>X</computeroutput> or <computeroutput>x</computeroutput>.
Neither <computeroutput>x</computeroutput> nor
<computeroutput>X</computeroutput> can be part of a longer symbol. The
whitespace characters, which can only be byte boundaries (and not at the
beginning or end of the string), are to improve readability. The language
processor ignores them.
</para>
<para>A hexadecimal string is a literal string formed by packing the hexadecimal
digits given. Packing the hexadecimal digits removes whitespace and converts
each pair of hexadecimal digits into its equivalent character, for example,
"41"X to A.
</para>
<para>Hexadecimal strings let you include characters in a program even if you
cannot directly enter the characters themselves. These are valid hexadecimal
strings: </para>
<programlisting>
"ABCD"x
"1d ec f8"X
"1 d8"x
</programlisting>
<note><title>Note</title>
<para>A hexadecimal string is <emphasis>not</emphasis> a representation
of a number. It is an escape mechanism that lets a user describe a character
in terms of its encoding (and, therefore, is machine-dependent). In ASCII, "20"X
is the encoding for a blank. In every case, a string of the form "....."x
is an alternative to a straightforward string. In ASCII "41"x and "A"
are identical, as are "20"x and a blank, and must be treated identically.
</para></note>
<para><emphasis role="bold">Implementation maximum:</emphasis>
<indexterm><primary>hexadecimal</primary>
<secondary>strings</secondary>
<tertiary>implementation maximum</tertiary></indexterm>
<indexterm><primary>implementation maximum</primary>
<secondary>hexadecimal strings</secondary></indexterm>
The packed length of a hexadecimal string (the string with whitespace removed)
is unlimited.
</para>
</section>
<section id="binstrings"><title>Binary Strings</title>
<indexterm><primary>binary</primary>
<secondary>digits</secondary></indexterm>
<indexterm><primary>binary</primary>
<secondary>strings</secondary>
<tertiary>description</tertiary></indexterm>
<indexterm><primary>binary</primary>
<secondary>strings</secondary>
<tertiary>nibbles</tertiary></indexterm>
<indexterm><primary>nibbles</primary></indexterm>
<indexterm><primary>string</primary>
<secondary>binary specification of</secondary></indexterm>
<indexterm><primary>tokens</primary>
<secondary>binary strings</secondary></indexterm>
<para>A binary string is a literal string, expressed using
a binary representation of its encoding. It is any sequence of zero or more
binary digits (<computeroutput>0</computeroutput> or
<computeroutput>1</computeroutput>) in groups of 8 (bytes) or 4 (nibbles).
The first group can have less than four digits; in this case, up to three
0 digits are assumed to the left of the first digit, making a total of four
digits. The groups of digits are optionally separated by one or more whitespace
characters, and the whole sequence is delimited by matching single or double
quotation marks and immediately followed by the symbol
<computeroutput>b</computeroutput> or <computeroutput>B</computeroutput>.
Neither <computeroutput>b</computeroutput> nor
<computeroutput>B</computeroutput> can be part of a longer symbol. The
whitespace characters, which can only be byte or nibble boundaries (and not at
the beginning or end of the string), are to improve readability. The language
processor ignores them.
</para>
<para>A binary string is a literal string formed by packing the binary digits
given. If the number of binary digits is not a multiple of 8, leading zeros
are added on the left to make a multiple of 8 before packing. Binary strings
allow you to specify characters explicitly, bit by bit. These are valid binary
strings: </para>
<programlisting>
"11110000"b /* == "f0"x */
"101 1101"b /* == "5d"x */
"1"b /* == "00000001"b and "01"x */
"10000 10101010"b /* == "0001 0000 1010 1010"b */
""b /* == "" */
</programlisting>
<para><emphasis role="bold">Implementation maximum:</emphasis>
<indexterm><primary>binary</primary>
<secondary>strings</secondary>
<tertiary>implementation maximum</tertiary></indexterm>
<indexterm><primary>implementation maximum</primary>
<secondary>binary strings</secondary></indexterm>
The packed length of a binary-literal string is unlimited.</para>
</section>
<section id="xsymbol"><title>Symbols</title>
<indexterm><primary>alphabetics</primary>
<secondary>used in symbols</secondary></indexterm>
<indexterm><primary>names</primary>
<secondary>of variables</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>uppercase translation</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>valid names</secondary></indexterm>
<indexterm><primary>tokens</primary>
<secondary>symbols</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>names</secondary></indexterm>
<para>Symbols are groups of characters, selected
from the:</para>
<itemizedlist>
<listitem><para>English alphabetic characters
(<computeroutput>A</computeroutput>-<computeroutput>Z</computeroutput>
and <computeroutput>a</computeroutput>-<computeroutput>z</computeroutput>).
</para></listitem>
<listitem><para>Numeric characters
(<computeroutput>0</computeroutput>-<computeroutput>9</computeroutput>)
</para></listitem>
<listitem><para>Characters <computeroutput>. ! ?</computeroutput>
and underscore (<computeroutput>_</computeroutput>).
</para></listitem></itemizedlist>
<indexterm><primary>uppercase translation</primary>
<secondary>of symbols</secondary></indexterm>
<para>Any lowercase alphabetic character in a symbol is translated to uppercase
(that is, lowercase
<computeroutput>a</computeroutput>-<computeroutput>z</computeroutput>
to uppercase
<computeroutput>A</computeroutput>-<computeroutput>Z</computeroutput>) before
use.</para>
<para>These are valid symbols: </para>
<programlisting>
Fred
Albert.Hall
WHERE?
</programlisting>
<para>If a symbol does not begin with a digit or a period, you can use it as
a variable and can assign it a value. If you have not assigned a value to
it, its value is the characters of the symbol itself, translated to uppercase
(that is, lowercase
<computeroutput>a</computeroutput>-<computeroutput>z</computeroutput>
to uppercase
<computeroutput>A</computeroutput>-<computeroutput>Z</computeroutput>).
Symbols that begin with a number or a period are constant symbols
and cannot directly be assigned a value. (See
<link linkend="ensym">Environment Symbols</link>.)</para>
<para>One other form of symbol is allowed to support the representation of
numbers in exponential format. The symbol starts with a digit
(<computeroutput>0</computeroutput>-<computeroutput>9</computeroutput>)
or a period, and it can end with the sequence
<computeroutput>E</computeroutput> or <computeroutput>e</computeroutput>,
followed immediately by an optional sign (<computeroutput>-</computeroutput>
or <computeroutput>+</computeroutput>), followed immediately by one
or more digits (which cannot be followed
by any other symbol characters). The sign in this context is part of the symbol
and is not an operator.</para>
<para>These are valid numbers in exponential notation: </para>
<indexterm><primary>exponential notation</primary>
<secondary>example</secondary></indexterm>
<programlisting>
17.3E-12
.03e+9
</programlisting>
</section>
<section id="numbrs"><title>Numbers</title>
<indexterm><primary>numbers</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>rounding</primary>
<secondary>using a character string as a number</secondary></indexterm>
<indexterm><primary>tokens</primary>
<secondary>numbers</secondary></indexterm>
<para>Numbers are character strings consisting of one or more decimal digits,
with an optional prefix of a plus (+) or minus (-) sign, and optionally
including a single period (<computeroutput>.</computeroutput>) that represents
a decimal point. A number can also have a power of 10
<indexterm><primary>powers of ten in numbers</primary></indexterm>
suffixed in conventional exponential notation: an
<computeroutput>E</computeroutput> (uppercase or lowercase),
followed optionally by a plus or minus sign,
then followed by one or more decimal digits defining the power of 10. Whenever
a character string is used as a number, rounding can occur to a precision
specified by the NUMERIC DIGITS instruction (the default is nine digits).
See <link linkend="numarit">Numbers and Arithmetic</link> for
a full definition of numbers.</para>
<para>Numbers
<indexterm><primary>restrictions</primary>
<secondary>embedded in numbers</secondary></indexterm>
can have leading whitespace (before and after the sign) and trailing whitespace.
Whitespace characters cannot be embedded among the digits of a number or in the
exponential part. Note that a symbol or a literal string can be a number. A
number cannot be the name of a variable.
</para>
<para>These are valid numbers: </para>
<programlisting>
12
"-17.9"
127.0650
73e+128
" + 7.9E5 "
</programlisting>
<para>You can specify numbers with or without quotation marks around them. Note
that the sequence <computeroutput>-17.9</computeroutput>
(without quotation marks) in an expression
is not simply a number. It is a minus operator (which can be prefix minus
if no term is to the left of it) followed by a positive number. The result
of the operation is a number, which might be rounded or reformatted into
exponential form depending on the size of the number and the current
NUMERIC DIGITS setting.
</para>
<para>A <emphasis>whole number</emphasis> is a number that has a no decimal
part and that the language
processor would not usually express in exponential notation. That is, it has
no more digits before the decimal point than the current setting of NUMERIC
DIGITS.</para>
<para><emphasis role="bold">Implementation maximum:</emphasis>
<indexterm><primary>numbers</primary>
<secondary>implementation maximum</secondary></indexterm>
<indexterm><primary>implementation maximum</primary>
<secondary>numbers</secondary></indexterm>
<indexterm><primary>whole numbers</primary>
<secondary>description</secondary></indexterm>
The exponent of a number expressed in exponential notation can have
up to nine digits.</para>
</section>
<section id="operatorchar"><title>Operator Characters</title>
<indexterm><primary>concatenation</primary>
<secondary>operator</secondary>
<tertiary>||</tertiary></indexterm>
<indexterm><primary>operator</primary>
<secondary>as special characters</secondary></indexterm>
<indexterm><primary>operator</primary>
<secondary>characters</secondary></indexterm>
<indexterm><primary>tokens</primary>
<secondary>operator characters</secondary></indexterm>
<para>The characters
<computeroutput>+ - \ / % * | &amp; = &not; > &lt;</computeroutput>
and the sequences
<computeroutput>>= &lt;= \> \&lt; \= >&lt; &lt;> == \== // &amp;&amp;
|| ** &not;> &not;&lt; &not;= &not;== >> &lt;&lt; >>= \&lt;&lt;
&not;&lt;&lt; \>> &not;>> &lt;&lt;=</computeroutput> indicate operations
(see <link linkend="opera">Operators</link>).
A few of these are also used in parsing templates, and the equal sign
<indexterm><primary>equal</primary>
<secondary>sign</secondary>
<tertiary>to indicate assignment</tertiary></indexterm>
and the sequences <computeroutput>+=, -=, *= /=, %=, //=, ||=, &amp;=, |=, and &amp;&amp;=</computeroutput>
are also
used to indicate assignment. Whitespace characters adjacent to operator
characters are removed. Therefore, the following are identical in meaning:
</para>
<programlisting>
345>=123
345 >=123
345 >= 123
345 > = 123
</programlisting>
<para>Some of these characters (and some special characters&mdash;see the next
section) might not be available in all character sets. In this case,
appropriate translations can be used.
<indexterm><primary>logical OR operator</primary></indexterm>
In particular, the vertical bar (|) is often
shown as a split vertical bar (&brvbar;).</para>
<note><title>Note</title>
<para>The Rexx interpreter uses ASCII character
124 in the concatenation operator and as the logical OR operator. Depending
on the code page or keyboard for your particular country, ASCII 124 can be
shown as a solid vertical bar (|) or a split vertical bar (&brvbar;).
The character on the screen might not match the character engraved on the
key. If you receive error 13,
<computeroutput>Invalid character in program</computeroutput>, on
an instruction including a vertical bar character, make sure this character
is ASCII 124.</para></note>
<para>Throughout the language, the NOT (&not;)
<indexterm><primary>logical NOT character</primary></indexterm>
<indexterm><primary>NOT operator</primary></indexterm>
character is synonymous with the backslash
<indexterm><primary>backslash, use of</primary></indexterm>
(<computeroutput>\</computeroutput>). You can
use the two characters interchangeably according to availability and personal
preference.</para>
<para>The Rexx interpreter recognizes both ASCII character 170 ('AA'X) and ASCII
character 172 ('AC'X) for the logical NOT operator. Depending on your country,
the &not; might not appear on your keyboard. If the character is not available,
you can use the backslash (\) in place of &not;.
</para>
</section>
<section id="specchar"><title>Special Characters</title>
<indexterm><primary>special</primary>
<secondary>characters and example</secondary></indexterm>
<indexterm><primary>tokens</primary>
<secondary>special characters</secondary></indexterm>
<para>The following characters, together with the operator characters,
have special significance when found outside of literal strings: </para>
<programlisting>
, ; : ( ) [ ] ~
</programlisting>
<indexterm><primary>comma</primary>
<secondary>as a special character</secondary></indexterm>
<indexterm><primary>, (comma)</primary>
<secondary>as a special character</secondary></indexterm>
<indexterm><primary>; semicolon</primary>
<secondary>as a special character</secondary></indexterm>
<indexterm><primary>: (colon)</primary>
<secondary>as a special character</secondary></indexterm>
<indexterm><primary>colon</primary>
<secondary>as a special character</secondary></indexterm>
<para>These characters constitute the set of special characters. They all act
as token delimiters, and
<indexterm><primary>parentheses</primary>
<secondary>adjacent to whitespace</secondary></indexterm> whitespace characters
(blank or horizontal tab)
adjacent to any of these are removed. There is an exception: a whitespace
character adjacent to the outside of a parenthesis or bracket is deleted only if
it is also adjacent to another special character (unless the character is a
parenthesis or bracket and the whitespace character is outside it, too). For
example, the language processor does not remove the blank in
<computeroutput>A&nbsp;(Z)</computeroutput>. This is a concatenation that is
not equivalent to <computeroutput>A(Z)</computeroutput>,
a function call. The language processor removes the blanks in
<computeroutput>(A)&nbsp;+&nbsp;(Z)</computeroutput> because this is equivalent
to <computeroutput>(A)+(Z)</computeroutput>.</para>
</section>
<section id="speccharexmp"><title>Example</title>
<para>The following
example shows how a clause is composed of tokens:</para>
<indexterm><primary>examples</primary>
<secondary>special characters</secondary></indexterm>
<programlisting>
"REPEAT" A + 3;
</programlisting>
<para>This example is composed of six tokens&mdash;a literal string
(<computeroutput>"REPEAT"</computeroutput>), a blank operator, a symbol
(<computeroutput>A</computeroutput>, which can have an assigned
value), an operator (<computeroutput>+</computeroutput>), a second symbol
(<computeroutput>3</computeroutput>, which is
a number and a symbol), and the clause delimiter
(<computeroutput>;</computeroutput>). The blanks
between the <computeroutput>A</computeroutput> and the
<computeroutput>+</computeroutput> and between the
<computeroutput>+</computeroutput> and
the <computeroutput>3</computeroutput> are removed.
However, one of the blanks between the
<computeroutput>"REPEAT"</computeroutput> and the
<computeroutput>A</computeroutput> remains as an operator. Thus, this clause
is treated as though written: </para>
<programlisting>
"REPEAT" A+3;
</programlisting>
</section>
</section>
<section id="imsemi"><title>Implied Semicolons</title>
<indexterm><primary>implied semicolons</primary></indexterm>
<indexterm><primary>semicolons</primary>
<secondary>implied</secondary></indexterm>
<para>The last element in a clause is the semicolon (;) delimiter.
The language processor implies the semicolon at a line end, after certain
keywords, and after a colon if it follows a single symbol. This means that
you need to include semicolons only when there is more than one clause on
a line or to end an instruction whose last character is a comma.</para>
<para>A line end usually marks the end of a clause and, thus, Rexx implies a
semicolon at most end of lines. However, there are the following exceptions:
<itemizedlist>
<listitem><para>The line ends in the middle of a comment. The clause continues
on to the next line.</para></listitem>
<listitem><para>The last token was the continuation character (a comma
or a minus sign) and the
line does not end in the middle of a comment.
(Note that a comment is not a token.)</para></listitem>
</itemizedlist></para>
<para>Rexx automatically implies semicolons after colons (when following a single
symbol or literal string, a label) and after certain keywords when they are in the correct context.
The keywords that have this effect are ELSE, OTHERWISE, and THEN. These
special cases reduce typographical errors significantly. </para>
<note><title>Note</title>
<para>The two characters forming the comment delimiters,
<computeroutput>/*</computeroutput> and
<computeroutput>*/</computeroutput>, must not be split by a line end (that is,
<computeroutput>/</computeroutput> and <computeroutput>*</computeroutput>
should not appear on different lines) because they could not then
be recognized correctly; an implied semicolon would be added.
</para></note>
</section>
<section id="contin"><title>Continuations</title>
<indexterm><primary>, (comma)</primary>
<secondary>as continuation character</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>continuation of</secondary></indexterm>
<indexterm><primary>comma</primary>
<secondary>as continuation character</secondary></indexterm>
<indexterm><primary>continuation</primary>
<secondary>character</secondary></indexterm>
<indexterm><primary>continuation</primary>
<secondary>clauses</secondary></indexterm>
<para>One way to continue a clause on the next line is to use the comma or
the minus sign (-), which is referred to as the
<emphasis>continuation character</emphasis>. The continuation character is
functionally replaced by a blank, and, thus, no semicolon is implied.
One or more comments can follow
the continuation character before the end of the line.</para>
<para>The following example shows how to use the continuation character to
continue a clause:</para>
<indexterm><primary>continuation</primary>
<secondary>example</secondary></indexterm>
<indexterm><primary>examples</primary>
<secondary>continuation</secondary></indexterm>
<programlisting>
say "You can use a comma", -- this line is continued
"to continue this clause."
</programlisting><para>or </para>
<programlisting>
say "You can use a minus"- -- this line is continued
"to continue this clause."
</programlisting>
</section>
</section>
<section id="expopr"><title>Terms, Expressions, and Operators</title>
<indexterm><primary>terms and data</primary></indexterm>
<para>Expressions in Rexx are a general mechanism for combining one or more
pieces of data in various ways to produce a result, usually different from the
original data. All expressions evaluate to objects.
<indexterm><primary>object</primary></indexterm>
</para>
<para>Everything in Rexx is an object.
<indexterm><primary>data</primary>
<secondary>objects</secondary></indexterm>
Rexx provides some objects, which are described in later sections. You can
also define and create objects that are useful in particular applications&mdash;for
example, a menu object for user interaction. See
<link linkend="objects">Modeling Objects</link> for
more information.</para>
<section id="expres"><title>Terms and Expressions</title>
<indexterm><primary>data</primary>
<secondary>terms</secondary></indexterm>
<para><emphasis>Terms</emphasis> are literal strings, symbols, message
terms, function calls, or subexpressions interspersed with zero or
more operators
that denote operations to be carried out on terms.</para>
<para><emphasis role="italic">Literal strings</emphasis>,
which are delimited by quotation marks, are constants.</para>
<para><emphasis>Symbols</emphasis> (no quotation marks) are translated to
uppercase. A symbol that does not begin with a digit or a period can be the
name of a variable; in this case the
<indexterm><primary>value</primary></indexterm>
value of that variable is used. A symbol
that begins with a period can identify an object that the current environment
provides; in this case, that object is used. Otherwise a symbol is treated
as a constant string. A symbol can also be
<emphasis role="italic">compound</emphasis>.</para>
<para><emphasis role="italic">Message terms</emphasis>
are described in <link linkend="mssg">Message Terms</link>.</para>
<para><emphasis role="italic">Function calls</emphasis>
(see <link linkend="funct">Functions</link>), which
are of the following form:
</para>
<programlisting>
<![CDATA[
+-,--------------+
V |
>>-symbolorstring(----+------------+-+--)----------------------><
+-expression-+
]]>
</programlisting>
<para>The <emphasis role="italic">symbolorstring</emphasis> is a symbol or
literal string.</para>
<para>An <emphasis role="italic">expression</emphasis> consists of
one or more terms. A <emphasis role="italic">subexpression</emphasis>
<indexterm><primary>subexpression</primary></indexterm>
is a term in an
expression surrounded with a left and a right parenthesis.</para>
<indexterm><primary>evaluation of expressions</primary></indexterm>
<indexterm><primary>expressions</primary>
<secondary>evaluation</secondary></indexterm>
<para>Evaluation of an expression is left to right, modified by parentheses
and operator precedence in the usual algebraic manner (see
<link linkend="oprpri">Parentheses and Operator Precedence</link>).
Expressions are wholly evaluated, unless an error occurs during evaluation.
</para>
<indexterm><primary>expressions</primary>
<secondary>results of</secondary></indexterm>
<para>As each term is used in an expression, it is evaluated
as appropriate. The result is an object. Consequently, the result of evaluating
any expression is itself an object
<indexterm><primary>object</primary>
<secondary>as data value</secondary></indexterm>
(such as a character string).</para>
</section>
<section id="opera"><title>Operators</title>
<indexterm><primary>arithmetic</primary>
<secondary>operators</secondary></indexterm>
<indexterm><primary>messages to objects</primary>
<secondary>operator as message</secondary></indexterm>
<indexterm><primary>operator</primary>
<secondary>arithmetic</secondary>
<tertiary>description</tertiary></indexterm>
<indexterm><primary>operator</primary>
<secondary>as message</secondary></indexterm>
<para>An <emphasis role="italic">operator</emphasis> is a representation
of an operation, such as an addition, to be carried out on one or two terms.
Each operator, except for the prefix operators, acts on two terms, which can
be symbols, strings, function calls, message terms, intermediate results,
or subexpressions. Each prefix operator acts on the term or subexpression
that follows it. Whitespace characters (and comments) adjacent to operator
characters have no effect on the operator; thus, operators constructed from more
than one character can have embedded whitespace and comments. In addition, one
or more whitespace characters, if they occur in expressions but are not adjacent
to another operator, also act as an operator. The language processor
functionally translates operators into message terms. For dyadic operators,
<indexterm><primary>dyadic operators</primary></indexterm>
which operate on two terms, the
language processor sends the operator as a message to the term on the left,
passing the term on the right as an argument. For example, the sequence </para>
<programlisting>
say 1+2
</programlisting>
<para>is functionally equivalent to:</para>
<programlisting>
say 1~"+"(2)
</programlisting>
<para>The blank concatenation operator sends the message &quot;&nbsp;&quot;
(a single blank), and the abuttal concatenation operator sends the &quot;&quot;
message (a null string). When the &not; character is used in an operator, it
is changed to a <computeroutput>\</computeroutput>. That is, the operators
&not;= and \= both send the message \= to the target object.</para>
<para>For an operator that works on a single term (for example, the
prefix&nbsp;- and prefix&nbsp;+ operators), Rexx sends a message to the term,
with no arguments. This means <computeroutput>-z</computeroutput> has the
same effect as <computeroutput>z~"-"</computeroutput>.</para>
<para>See <link linkend="mthObjectOperators">Operator Methods</link> for operator methods of
the Object class and <link linkend="mthStringArithmeticMethods">Arithmetic Methods</link>
for operator methods of the String class.</para>
<para>There are four types of operators:
<itemizedlist>
<listitem><para>Concatenation</para></listitem>
<listitem><para>Arithmetic</para></listitem>
<listitem><para>Comparison</para></listitem>
<listitem><para>Logical</para></listitem></itemizedlist></para>
<section id="strgcon"><title>String Concatenation</title>
<indexterm><primary>concatenation</primary>
<secondary>of strings</secondary></indexterm>
<indexterm><primary>operator</primary>
<secondary>concatenation</secondary></indexterm>
<indexterm><primary>string</primary>
<secondary>concatenation of</secondary></indexterm>
<para>The concatenation operators combine two strings to form one string by
appending the second string to the right-hand end of the first string. The
concatenation may occur with or without an intervening blank. The concatenation
operators are: </para>
<informaltable frame="none" colsep="0" rowsep="0" pgwide="1">
<tgroup cols="2">
<colspec colnum="1" colwidth="1*">
<colspec colnum="2" colwidth="4*">
<tbody>
<row>
<entry>(blank)</entry>
<entry>
<para>Concatenate terms with one blank in between
<indexterm><primary>blanks</primary></indexterm>
<indexterm><primary>concatenation</primary>
<secondary>as concatenation operator</secondary></indexterm>
<indexterm><primary>concatenation</primary>
<secondary>blank</secondary></indexterm>
</para>
</entry>
</row>
<row>
<entry>||</entry>
<entry>
<para>Concatenate without an intervening blank
<indexterm><primary>|| concatenation operator</primary></indexterm>
<indexterm><primary>concatenation</primary>
<secondary>operator</secondary>
<tertiary>||</tertiary></indexterm>
</para>
</entry>
</row>
<row>
<entry>(abuttal)</entry>
<entry>
<para>Concatenate without an intervening blank
<indexterm><primary>concatenation</primary>
<secondary>abuttal</secondary></indexterm>
<indexterm><primary>abuttal</primary></indexterm>
</para>
</entry>
</row>
</tbody>
</tgroup>
</informaltable>
<para>You can force concatenation without a blank by using the
<computeroutput>||</computeroutput> operator.</para>
<para>The abuttal operator is assumed between two terms that are not separated
by another operator. This can occur when two terms are syntactically distinct,
such as a literal string and a symbol, or when they are only separated by
a comment.</para>
<para><emphasis role="bold">Examples:</emphasis></para>
<para>An example of syntactically distinct terms is: if
<computeroutput>Fred</computeroutput> has the
value <computeroutput>37.4</computeroutput>, then
<computeroutput>Fred"%"</computeroutput> evaluates to
<computeroutput>37.4%</computeroutput>.</para>
<para></para>
<para>If the variable <varname>PETER</varname> has the value
<computeroutput>1</computeroutput>, then <varname>(Fred)(Peter)</varname>
evaluates to <computeroutput>37.41</computeroutput>.</para>
<para>The two adjoining strings, one hexadecimal and one literal,
<computeroutput>"4a 4b"x"LMN"</computeroutput> evaluate to
<computeroutput>JKLMN</computeroutput>.</para>
<para>In the case of </para>
<programlisting>
Fred/* The NOT operator precedes Peter. */&not;Peter
</programlisting>
<para> there is no abuttal operator implied, and the expression is not valid.
However, </para>
<programlisting>
(Fred)/* The NOT operator precedes Peter. */(&not;Peter)
</programlisting><para> results
in an abuttal, and evaluates to <computeroutput>37.40</computeroutput>.</para>
</section>
<section id="xarithm"><title>Arithmetic</title>
<indexterm><primary>numbers</primary>
<secondary>arithmetic on</secondary></indexterm>
<indexterm><primary>operator</primary>
<secondary>arithmetic</secondary>
<tertiary>list</tertiary></indexterm>
<indexterm><primary>operator</primary>
<secondary>comparison</secondary></indexterm>
<para>You can combine character strings that are
valid numbers (see <link linkend="numbrs">Numbers</link>)
using the following arithmetic operators: </para>
<informaltable frame="none" colsep="0" rowsep="0" pgwide="1">
<tgroup cols="2">
<colspec colnum="1" colwidth="1*">
<colspec colnum="2" colwidth="4*">
<tbody>
<row>
<entry>+</entry>
<entry>
<para>Add
<indexterm><primary>+ (addition operator)</primary></indexterm>
<indexterm><primary>addition operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>-</entry>
<entry>
<para>Subtract
<indexterm><primary>- (subtraction operator)</primary></indexterm>
<indexterm><primary>subtraction operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>*</entry>
<entry>
<para>Multiply
<indexterm><primary>* (multiplication operator)</primary></indexterm>
<indexterm><primary>multiplication operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>/</entry>
<entry>
<para>Divide
<indexterm><primary>/ (division operator)</primary></indexterm>
<indexterm><primary>division operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>%</entry>
<entry>
<para>Integer divide (divide and return the integer part of the
result)
<indexterm><primary>% (integer division operator)</primary></indexterm>
<indexterm><primary>integer division operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>//</entry>
<entry>
<para>Remainder (divide and return the remainder&mdash;not modulo, because
the result can be negative)
<indexterm><primary>remainder operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>**</entry>
<entry>
<para>Power (raise a number to a whole-number power)
<indexterm><primary>exponentiation</primary>
<secondary>operator</secondary></indexterm>
<indexterm><primary>power operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>Prefix -</entry>
<entry>
<para>Same as the subtraction:
<computeroutput>0 - number</computeroutput>
<indexterm><primary>prefix - operator</primary></indexterm>
</para>
</entry>
</row>
<row>
<entry>Prefix +</entry>
<entry>
<para>Same as the addition:
<computeroutput>0 + number</computeroutput>
<indexterm><primary>prefix + operator</primary></indexterm>
</para>
</entry>
</row>
</tbody>
</tgroup>
</informaltable>
<para>See <link linkend="numarit">Numbers and Arithmetic</link>
for details about precision, the format of valid numbers, and the
operation rules for arithmetic. Note that if an arithmetic result is
shown in exponential notation, it is likely that rounding has occurred.</para>
</section>
<section id="compari"><title>Comparison</title>
<indexterm><primary>comparisons</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>comparisons</primary>
<secondary>of strings</secondary></indexterm>
<indexterm><primary>equality, testing of</primary></indexterm>
<indexterm><primary>numbers</primary>
<secondary>comparison of</secondary></indexterm>
<indexterm><primary>strict comparison</primary></indexterm>
<indexterm><primary>string</primary>
<secondary>comparison of</secondary></indexterm>
<para>The
comparison operators compare two terms and return the value
<computeroutput>1</computeroutput> if
the result of the comparison is true, or <computeroutput>0</computeroutput>
otherwise.</para>
<para>The strict comparison operators
<indexterm><primary>strict comparison</primary></indexterm>
all have one of the characters defining the operator doubled. The
<computeroutput>==</computeroutput>,
<indexterm><primary>== (strictly equal operator)</primary></indexterm>
<indexterm><primary>strictly equal operator</primary></indexterm>
<computeroutput>\==</computeroutput>,
<indexterm><primary>inequality, testing of</primary></indexterm>
<indexterm><primary>\== (not strictly equal operator)</primary></indexterm>
<indexterm><primary>prefix \ operator</primary></indexterm>
and <computeroutput>&not;==</computeroutput>
<indexterm><primary>&not;== (not strictly equal operator)</primary></indexterm>
<indexterm><primary>strictly not equal operator</primary></indexterm>
operators test for an exact
match between two strings. The two strings must be identical (character by
character) and of the same length to be considered strictly equal. Similarly,
the strict comparison operators such as
<computeroutput>&gt;&gt;</computeroutput>
<indexterm><primary>&gt;&gt; (strictly greater than operator)</primary>
</indexterm>
<indexterm><primary>strictly greater than operator</primary></indexterm>
or <computeroutput>&lt;&lt;</computeroutput>
<indexterm><primary>&lt;&lt; (strictly less than operator)</primary></indexterm>
<indexterm><primary>strictly less than operator</primary></indexterm>
carry out a simple character-by-character comparison, with no padding of either
of the strings being compared. The comparison of the two strings is from
left to right. If one string is shorter than the other and is a leading
substring of another, then it is smaller than (less than) the other.
The strict comparison
<indexterm><primary>comparisons</primary>
<secondary>of numbers</secondary></indexterm>
operators also do not attempt to perform a numeric comparison on the two
operands.</para>
<para>For all other comparison operators, if both terms
involved are numeric, a numeric comparison (see
<link linkend="numcom">Numeric Comparisons</link>) is
effected. Otherwise, both terms are treated as character strings, leading
and trailing whitespace characters are ignored, and the shorter string is padded
with blanks on the right.
</para>
<para>Character comparison and strict comparison operations are both
case-sensitive, and the exact collating order might depend on the
character set used for the implementation. In an ASCII environment,
such as Windows and *nix, the ASCII character value of digits is lower than
that of the alphabetic characters,
and that of lowercase alphabetic characters is higher than that of uppercase
alphabetic characters.</para>
<para>The comparison operators and operations are: </para>
<informaltable frame="none" colsep="0" rowsep="0" pgwide="1">
<tgroup cols="2">
<colspec colnum="1" colwidth="1*">
<colspec colnum="2" colwidth="4*">
<tbody>
<row>
<entry>=</entry>
<entry>
<para>True if the terms are equal (numerically or when padded)
<indexterm><primary>= (equal sign)</primary>
<secondary>equal operator</secondary></indexterm>
<indexterm><primary>equal</primary>
<secondary>operator</secondary></indexterm>
</para>
</entry>
</row>
<row><entry>\=, &not;=</entry>
<entry><para>True if the terms are not equal (inverse of =)
<indexterm><primary>\= (not equal operator)</primary></indexterm>
<indexterm><primary>&not;= (not equal operator)</primary></indexterm>
<indexterm><primary>not equal operator</primary></indexterm>
</para></entry></row>
<row><entry>>
<indexterm><primary>greater than operator (>)</primary></indexterm>
</entry>
<entry><para>Greater than
<indexterm><primary>&gt; (greater than operator)</primary></indexterm>
<indexterm><primary>greater than operator</primary></indexterm>
</para></entry></row>
<row><entry>&lt;
<indexterm><primary>less than operator (&lt;)</primary></indexterm>
</entry>
<entry><para>Less than
<indexterm><primary>&lt; (less than operator)</primary></indexterm>
</para></entry></row>
<row><entry>>&lt;
<indexterm><primary>greater than or less than operator (>&lt;)</primary>
</indexterm>
</entry>
<entry><para>Greater than or less than (same as not equal)
<indexterm><primary>>&lt; (greater than or less than operator)</primary>
</indexterm>
<indexterm><primary>greater than or less than operator</primary></indexterm>
</para></entry></row>
<row><entry>&lt;&gt;
<indexterm><primary>less than or greater than operator (&lt;>)</primary>
</indexterm>
</entry>
<entry><para>Greater than or less than (same as not equal)
<indexterm><primary>&lt;&gt; (less than or greater than operator)</primary>
</indexterm>
</para></entry></row>
<row><entry>&gt;=
<indexterm><primary>greater than or equal to operator (>=)</primary>
</indexterm>
</entry>
<entry><para>Greater than or equal to
<indexterm><primary>&gt;= (greater than or equal operator)</primary>
</indexterm>
<indexterm><primary>greater than or equal operator</primary></indexterm>
</para></entry></row>
<row><entry>\&lt;, &not;&lt;</entry>
<entry><para>Not less than
<indexterm><primary>\&lt; (not less than operator)</primary></indexterm>
<indexterm><primary>&not;&lt; (not less than operator)</primary></indexterm>
<indexterm><primary>not less than operator</primary></indexterm>
</para></entry></row>
<row><entry>&lt;=
<indexterm><primary>less than or equal to operator (&lt;=)</primary></indexterm>
</entry>
<entry><para>Less than or equal to
<indexterm><primary>&lt;= (less than or equal operator)</primary>
</indexterm>
</para></entry></row>
<row><entry>\>, &not;></entry>
<entry><para>Not greater than
<indexterm><primary>\&gt; (not greater than operator)</primary></indexterm>
<indexterm><primary>&not;> (not greater than operator)</primary></indexterm>
<indexterm><primary>not greater than operator</primary></indexterm>
</para></entry></row>
<row><entry>==</entry>
<entry><para>True if terms are strictly equal (identical)
<indexterm><primary>== (strictly equal operator)</primary></indexterm>
<indexterm><primary>strictly equal operator</primary></indexterm>
</para></entry></row>
<row><entry>\==, &not;==</entry>
<entry><para>True if the terms are not strictly equal (inverse of ==)
<indexterm><primary>\== (not strictly equal operator)</primary></indexterm>
<indexterm><primary>&not;== (not strictly equal operator)</primary></indexterm>
<indexterm><primary>strictly not equal operator</primary></indexterm>
</para></entry></row>
<row><entry>&gt;&gt;</entry>
<entry><para>Strictly greater than
<indexterm><primary>&gt;&gt; (strictly greater than operator)</primary>
</indexterm>
<indexterm><primary>strictly greater than operator</primary></indexterm>
</para></entry></row>
<row><entry>&lt;&lt;</entry>
<entry><para>Strictly less than
<indexterm><primary>&lt;&lt; (strictly less than operator)</primary></indexterm>
<indexterm><primary>strictly less than operator</primary></indexterm>
</para></entry></row>
<row><entry>&gt;&gt;=</entry>
<entry><para>Strictly greater than or equal to
<indexterm><primary>&gt;&gt;= (strictly greater than or equal operator)</primary>
</indexterm>
<indexterm><primary>strictly greater than or equal operator</primary></indexterm>
</para></entry></row>
<row><entry>\&lt;&lt;, &not;&lt;&lt;</entry>
<entry><para>Strictly not less than
<indexterm><primary>\&lt;&lt; (strictly not less than operator)</primary>
</indexterm>
<indexterm><primary>&not;&lt;&lt; (strictly not less than operator)</primary>
</indexterm>
<indexterm><primary>strictly not less than operator</primary></indexterm>
</para></entry></row>
<row><entry>&lt;&lt;=</entry>
<entry><para>Strictly less than or equal to
<indexterm><primary>&lt;&lt;= (strictly less than or equal operator)</primary>
</indexterm>
</para></entry></row>
<row><entry>\&gt;&gt;, &not;&gt;&gt;</entry>
<entry><para>Strictly not greater than
<indexterm><primary>\&gt;&gt; (strictly not greater than operator)</primary>
</indexterm>
<indexterm><primary>&not;&gt;&gt; (strictly not greater than operator)</primary>
</indexterm>
<indexterm><primary>strictly not greater than operator</primary></indexterm>
</para></entry></row>
</tbody>
</tgroup>
</informaltable>
<note><title>Note</title>
<para>Throughout the language, the NOT (&not;)
<indexterm><primary>&not; (NOT operator)</primary></indexterm>
character is
synonymous with the backslash(<computeroutput>\</computeroutput>).
<indexterm><primary>backslash, use of</primary></indexterm>
<indexterm><primary>\ (NOT operator)</primary></indexterm>
<indexterm><primary>prefix \ operator</primary></indexterm>
You can use the two
characters interchangeably, according to availability and personal preference.
The backslash can appear in the following operators:
<computeroutput>\</computeroutput> (prefix
not),<computeroutput>\=</computeroutput>, <computeroutput>\==</computeroutput>,
<computeroutput>\&lt;</computeroutput>, <computeroutput>\></computeroutput>,
<computeroutput>\&lt;&lt;</computeroutput>, and
<computeroutput>\>></computeroutput>.
</para></note>
</section>
<section id="logicl"><title>Logical (Boolean)</title>
<indexterm><primary>boolean operations</primary></indexterm>
<indexterm><primary>logical</primary>
<secondary>operations</secondary></indexterm>
<indexterm><primary>operator</primary>
<secondary>logical</secondary></indexterm>
<para>A character string has the value false if it is
<computeroutput>0</computeroutput>, and true
if it is <computeroutput>1</computeroutput>. The logical operators take one or
two such values and return
<computeroutput>0</computeroutput> or
<computeroutput>1</computeroutput> as appropriate. Values other than
<computeroutput>0</computeroutput> or
<computeroutput>1</computeroutput> are not permitted.
</para>
<informaltable frame="none" colsep="0" rowsep="0" pgwide="1">
<tgroup cols="2">
<colspec colnum="1" colwidth="1*">
<colspec colnum="2" colwidth="4*">
<tbody>
<row><entry>&amp;</entry>
<entry><para>AND &mdash; returns <computeroutput>1</computeroutput> if both
terms are true.
<indexterm><primary>&amp; (AND logical operator) operator</primary></indexterm>
<indexterm><primary>AND, logical operator</primary></indexterm>
</para></entry></row>
<row><entry>|
<indexterm><primary>inclusive OR operator</primary></indexterm>
<indexterm><primary>OR, logical</primary></indexterm>
</entry>
<entry><para>Inclusive OR &mdash; returns <computeroutput>1</computeroutput>
if either term or both terms are true.
<indexterm><primary>| inclusive OR operator</primary></indexterm>
</para></entry></row>
<row><entry>&amp;&amp;
<indexterm><primary>exclusive OR operator</primary></indexterm>
<indexterm><primary>XOR, logical</primary></indexterm>
</entry>
<entry><para>Exclusive OR &mdash; returns <computeroutput>1</computeroutput>
if either term, but not both terms, is true.
<indexterm><primary>&amp;&amp; (exclusive OR operator)</primary></indexterm>
</para></entry></row>
<row><entry><emphasis role="bold">Prefix</emphasis> \, &not;
<indexterm><primary>NOT operator</primary></indexterm>
<indexterm><primary>negation</primary>
<secondary>of logical values</secondary></indexterm>
</entry>
<entry><para>Logical NOT&mdash; negates; <computeroutput>1</computeroutput>
becomes <computeroutput>0</computeroutput>, and
<computeroutput>0</computeroutput> becomes <computeroutput>1</computeroutput>.
</para></entry></row>
</tbody>
</tgroup>
</informaltable>
</section>
</section>
<section id="oprpri"><title>Parentheses and Operator Precedence</title>
<indexterm><primary>algebraic precedence</primary></indexterm>
<indexterm><primary>precedence of operators</primary></indexterm>
<indexterm><primary>operator</primary>
<secondary>precedence (priorities) of</secondary></indexterm>
<indexterm><primary>parentheses</primary>
<secondary>in expressions</secondary></indexterm>
<para>Expression
evaluation is from left to right; parentheses and operator precedence modify
this:
<itemizedlist>
<listitem><para>When parentheses are encountered&mdash;other than those that
identify the arguments on messages (see
<link linkend="mssg">Message Terms</link>) and function calls&mdash;the
entire subexpression between the parentheses is evaluated immediately when
the term is required.</para></listitem>
<listitem><para>When the sequence </para>
<programlisting>
term1 operator1 term2 operator2 term3
</programlisting>
<para>is encountered, and <computeroutput>operator2</computeroutput>
has precedence over <computeroutput>operator1</computeroutput>,
the subexpression (<computeroutput>term2 operator2 term3</computeroutput>)
is evaluated first.</para>
<para>Note, however, that individual terms are evaluated from left
to right in the expression (that is, as soon as they are encountered). The
precedence rules affect only the order of
<emphasis role="bold">operations</emphasis>.</para></listitem>
</itemizedlist></para>
<para> For example, <computeroutput>*</computeroutput> (multiply) has a
higher priority than <computeroutput>+</computeroutput> (add), so
<computeroutput>3+2*5</computeroutput> evaluates to
<computeroutput>13</computeroutput> (rather than
the <computeroutput>25</computeroutput> that would result if a
strict left-to-right evaluation occurred).
To force the addition to occur before the multiplication, you could rewrite
the expression as <computeroutput>(3+2)*5</computeroutput>.
Adding the parentheses makes the first
three tokens a subexpression. Similarly, the expression
<computeroutput>-3**2</computeroutput> evaluates
to <computeroutput>9</computeroutput> (instead of
<computeroutput>-9</computeroutput>) because the prefix minus operator
has a higher priority than the power operator.</para>
<para>The order of precedence of the operators is (highest at the top):</para>
<informaltable frame="none" colsep="0" rowsep="0" pgwide="1">
<tgroup cols="2">
<colspec colnum="1" colwidth="1*">
<colspec colnum="2" colwidth="3*">
<tbody>
<row><entry>~&nbsp;&nbsp;&nbsp;~~\</entry><entry>(message send)</entry></row>
<row><entry>+&nbsp;&nbsp;&nbsp;-&nbsp;&nbsp;&nbsp;&not;&nbsp;&nbsp;&nbsp;\</entry><entry>(prefix operators)</entry></row>
<row><entry>**</entry><entry>(power)</entry></row>
<row><entry>*&nbsp;&nbsp;&nbsp;/&nbsp;&nbsp;&nbsp;%&nbsp;&nbsp;&nbsp;//</entry><entry>(multiply and divide)</entry></row>
<row><entry>+&nbsp;&nbsp;&nbsp;-</entry><entry>(add and subtract)</entry></row>
<row><entry>(blank)&nbsp;&nbsp;&nbsp;||&nbsp;&nbsp;&nbsp;(abuttal)</entry><entry>(concatenation with or without blank)</entry></row>
<row><entry>=&nbsp;&nbsp;&nbsp;>&nbsp;&nbsp;&nbsp;&lt;</entry><entry>(comparison operators)</entry></row>
<row><entry>==&nbsp;&nbsp;&nbsp;>>&nbsp;&nbsp;&nbsp;&lt;&lt;</entry><entry>&nbsp;</entry></row>
<row><entry>\=&nbsp;&nbsp;&nbsp;&not;=</entry><entry>&nbsp;</entry></row>
<row><entry>>&lt;&nbsp;&nbsp;&nbsp;&lt;></entry><entry>&nbsp;</entry></row>
<row><entry>\>&nbsp;&nbsp;&nbsp;&not;></entry><entry>&nbsp;</entry></row>
<row><entry>\&lt;&nbsp;&nbsp;&nbsp;&not;&lt;</entry><entry>&nbsp;</entry></row>
<row><entry>\==&nbsp;&nbsp;&nbsp;&not;==</entry><entry>&nbsp;</entry></row>
<row><entry>\>>&nbsp;&nbsp;&nbsp;&not;>></entry><entry>&nbsp;</entry></row>
<row><entry>\&lt;&lt;&nbsp;&nbsp;&nbsp;&not;&lt;&lt;</entry><entry>&nbsp;</entry></row>
<row><entry>>=&nbsp;&nbsp;&nbsp;>>=</entry><entry>&nbsp;</entry></row>
<row><entry>&lt;=&nbsp;&nbsp;&nbsp;&lt;&lt;=</entry><entry>&nbsp;</entry></row>
<row><entry>&amp;</entry><entry>(and)</entry></row>
<row><entry>|&nbsp;&nbsp;&nbsp;&amp;&amp;</entry><entry>(or, exclusive or)</entry></row>
</tbody>
</tgroup>
</informaltable>
<para><emphasis role="bold">Examples:</emphasis></para>
<para>Suppose the symbol <computeroutput>A</computeroutput> is a variable
whose value is <computeroutput>3</computeroutput>,
<computeroutput>DAY</computeroutput> is a variable whose value is
<computeroutput>Monday</computeroutput>, and other variables are
uninitialized. Then:</para>
<indexterm><primary>examples</primary>
<secondary>expressions</secondary></indexterm>
<indexterm><primary>expressions</primary>
<secondary>examples</secondary></indexterm>
<programlisting>
<![CDATA[
A+5 -> "8"
A-4*2 -> "-5"
A/2 -> "1.5"
0.5**2 -> "0.25"
(A+1)>7 -> "0" /* that is, False */
" "="" -> "1" /* that is, True */
" "=="" -> "0" /* that is, False */
" "\=="" -> "1"
/* that is, True */
(A+1)*3=12 -> "1" /* that is, True */
"077">"11" -> "1" /* that is, True */
"077" >> "11" -> "0" /* that is, False */
"abc" >> "ab" -> "1" /* that is, True */
"abc" << "abd" -> "1" /* that is, True */
"ab " << "abd" -> "1" /* that is, True */
Today is Day -> "TODAY IS Monday"
"If it is" day -> "If it is Monday"
Substr(Day,2,3) -> "ond" /* Substr is a function */
"!"xxx"!" -> "!XXX!"
]]>
</programlisting>
<note><title>Note</title>
<para>The Rexx order of precedence usually causes no difficulty because it is the
same as in conventional algebra and other computer languages. There are two
differences from common notations:
<itemizedlist>
<listitem><para>The prefix minus operator always has a higher priority than the
power operator.</para></listitem>
<listitem><para>Power operators (like other operators) are evaluated from
left to right.</para></listitem></itemizedlist></para>
<para>For example: </para>
<programlisting>
-3**2 == 9 /* not -9 */
-(2+1)**2 == 9 /* not -9 */
2**2**3 == 64 /* not 256 */
</programlisting></note>
</section>
<section id="mssg"><title>Message Terms</title>
<para>You can include <emphasis>messages</emphasis> to objects in an expression
wherever a term, such as a literal string, is valid. A message can be sent
to an object to perform an action, obtain a result, or both.</para>
<para>A <emphasis>message term</emphasis> can have one of the following forms:
</para>
<programlisting>
<![CDATA[
>>-receiver-+- ~ --+-messagename--+---------+------------------->
+- ~~ -+ +-:symbol-+
>--+--------------------------+--------------------------------><
+-(--+----------------+--)-+
| +-,----------+ |
| V | |
+---expression-+-+
]]>
</programlisting>
<programlisting>
<![CDATA[
>>-receiver[--+----------------+--]----------------------------><
| +-,----------+ |
| V | |
+---expression-+-+
]]>
</programlisting>
<para>The <emphasis role="italic">receiver</emphasis> is a term (see
<link linkend="expres">Terms and Expressions</link> for a definition
of term). It receives the message. The ~ or ~~ indicates
sending a message. The <emphasis role="italic">messagename</emphasis>
is a literal string or a symbol that is taken as a constant. The
<emphasis role="italic">expression</emphasis>s (separated by commas)
between the parentheses or brackets are the arguments for
the message. The <emphasis role="italic">receiver</emphasis>
and the argument <emphasis role="italic">expressions</emphasis> can
themselves include message terms. If the message has no arguments, you can
omit the parentheses.</para>
<para>The left parenthesis, if present, must immediately follow a token
(<emphasis role="italic">messagename</emphasis> or
<emphasis role="italic">symbol</emphasis>) with no blank in
between them. Otherwise, only the first part of the construct is recognized
as a message term. (A blank operator would be assumed at that point.) Only
a comment (which has no effect) can appear between a token and the left
parenthesis.</para>
<para>You can use any number of <emphasis role="italic">expressions</emphasis>,
separated by commas. The <emphasis role="italic">expressions</emphasis>
are evaluated from left to right and form the arguments during
the execution of the called method. Any ARG, PARSE ARG, or USE ARG instruction or
ARG() built-in function in the called method accesses these objects while the
called method is running. You can omit
<emphasis role="italic">expressions</emphasis>, if appropriate,
by including extra commas.</para>
<para>The <emphasis role="italic">receiver</emphasis> object is evaluated, followed
by one or more <emphasis role="italic">expression</emphasis> arguments.
The message name (in uppercase) and the resulting argument
objects are then sent to the receiver object. The receiver object selects
a method to be run based on the message name
(see <link linkend="meths1">Classes and Inheritance</link>), and
runs the selected method with the specified argument objects. The receiver
eventually returns, allowing processing to continue.</para>
<para>If the message term uses ~, the receiver method must return a result object.
This object is included in the original expression as if the entire message
term had been replaced by the name of a variable whose value is the returned
object.</para>
<para>For example, the message POS is valid for strings, and you could code:
</para>
<programlisting>
c="escape"
a="Position of &apos;e&apos; is:" c~pos("e",3)
/* would set A to "Position of &apos;e&apos; is: 6" */
</programlisting>
<para>If the message term uses ~~, the receiver method need not return
a result object. Any result object is discarded, and the receiver object is
included in the original expression in place of the message term.</para>
<para>For example, the messages INHERIT and SUBCLASS are valid for classes
(see <link linkend="clsClass">The Class Class</link>) and, assuming the
existence of the Persistent class, you could code:</para>
<programlisting>
account = .object~subclass("Account")~~inherit(.persistent)
/* would set ACCOUNT to the object returned by SUBCLASS, */
/* after sending that object the message INHERIT */
</programlisting>
<para>If the message term uses brackets, the message [] is sent to
the receiver object. (The <emphasis role="italic">expression</emphasis>s
within the brackets are available to the receiver object as arguments.)
The effect is the same as for the corresponding ~
form of the message term. Thus, <computeroutput>a[b]</computeroutput>
is the same as <computeroutput>a~"[]"(b)</computeroutput>.</para>
<para>For example, the message [] is valid for arrays
(see <link linkend="clsArray">The Array Class</link>) and you could code:</para>
<programlisting>
a = .array~of(10,20)
say "Second item is" a[2] /* Same as: a~at(2) */
/* or a~"[]"(2) */
/* Produces: "Second item is 20" */
</programlisting>
<indexterm><primary>arguments</primary>
<secondary>passing in messages</secondary></indexterm>
<para>A message can have a variable number of arguments. You need to specify
only those required. For example,
<computeroutput>"ESCAPE"~POS("E")</computeroutput> returns
<computeroutput>1</computeroutput>.</para>
<para>A colon (:) and symbol can follow the message name. In this case, the
symbol must be the name of a variable (usually the special variable SUPER--see
page <link linkend="xsuper">SUPER</link>) or an environment symbol
(see <link linkend="ensym">Environment Symbols</link>).
The resulting value changes the usual method selection. For more information,
see <link linkend="chsrod">Changing the Search Order for Methods</link>.</para>
</section>
<section id="mseq"><title>Message Sequences</title>
<indexterm><primary>messages to objects</primary>
<secondary>~, using</secondary></indexterm>
<indexterm><primary>messages to objects</primary>
<secondary>~~, using</secondary></indexterm>
<para>The ~
<indexterm><primary>~ (tilde or twiddle)</primary></indexterm>
and ~~
<indexterm><primary>~~</primary></indexterm>
forms of message terms
differ only in their treatment of the result object. Using
<computeroutput>~</computeroutput> returns the result of the method.
Using <computeroutput>~~</computeroutput> returns
the object that received the message. Here is an example: </para>
<programlisting>
/* Two ways to use the INSERT method to add items to a list */
/* Using only ~ */
team = .list~of("Bob","Mary")
team~insert("Jane")
team~insert("Joe")
team~insert("Steve")
say "First on the team is:" team~firstitem /* Bob */
say "Last on the team is:" team~lastitem /* Steve */
/* Do the same thing using ~~ */
team=.list~of("Bob","Mary")
/* Because ~~ returns the receiver of the message */
/* each INSERT message following returns the list */
/* object (after inserting the argument value). */
team~~insert("Jane")~~insert("Joe")~~insert("Steve")
say "First on the team is:" team~firstitem /* Bob */
say "Last on the team is:" team~lastitem /* Steve */
</programlisting>
<para>Thus, you would use ~ when you want the returned result to be the
receiver of the next message in the sequence.
</para>
</section>
</section>
<section id="clausin"><title>Clauses and Instructions</title>
<para>Clauses can be subdivided into the following types:
<itemizedlist>
<listitem><para>Null clauses</para></listitem>
<listitem><para>Directives</para></listitem>
<listitem><para>Labels</para></listitem>
<listitem><para>Instructions</para></listitem>
<listitem><para>Assignments</para></listitem>
<listitem><para>Message instructions</para></listitem>
<listitem><para>Keyword instructions</para></listitem>
<listitem><para>Commands</para></listitem></itemizedlist></para>
<section id="nullcla"><title>Null Clauses</title>
<indexterm><primary>clauses</primary>
<secondary>null</secondary></indexterm>
<indexterm><primary>null</primary>
<secondary>clauses</secondary></indexterm>
<para>A clause consisting only of whitespace characters, comments, or both is a
<emphasis>null clause
</emphasis>. It is completely ignored.</para>
<note><title>Note</title>
<para>A null clause is not an instruction; for example, putting an extra
semicolon after the THEN or ELSE in an IF instruction is not equivalent to
using a dummy instruction (as it would be in the C language). The NOP
instruction is provided for this purpose.</para></note>
</section>
<section id="directives"><title>Directives</title>
<indexterm><primary>clauses</primary>
<secondary>directives</secondary></indexterm>
<para>A clause that begins with two colons is a <emphasis>directive</emphasis>.
Directives are nonexecutable code and can start in any column. They
divide a program into separate executable units (methods and routines) and
supply information about the program or its executable units. Directives perform
various functions, such as creating new Rexx classes (::CLASS
directive) or defining a method (::METHOD directive). See
<link linkend="dire">Directives</link> for
more information about directives.</para>
</section>
<section id="labels"><title>Labels</title>
<indexterm><primary>label</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>labels</secondary></indexterm>
<indexterm><primary>colon</primary>
<secondary>as label terminators</secondary></indexterm>
<indexterm><primary>colon</primary>
<secondary>in a label</secondary></indexterm>
<para>A clause that consists of a single symbol
or string followed by a colon is a <emphasis>label</emphasis>. The colon
<indexterm><primary>: (colon)</primary>
<secondary>in a label</secondary></indexterm>
in this context implies a semicolon (clause separator), so no semicolon is
required.</para>
<para>The label's name is taken from the string or symbol part
of the label. If the label uses a symbol for the name, the label's name
is in uppercase. If a label uses a string, the name can contain mixed-case
characters.</para>
<para>Labels identify the targets of CALL instructions, SIGNAL instructions,
and internal function calls. Label searches for CALL, SIGNAL, and internal
function calls are case-sensitive. Label-search targets specified as symbols
cannot match labels with lowercase characters. Literal-string or computed-label
searches can locate labels with lowercase characters.
</para>
<para>Labels can be any number of successive clauses. Several labels can precede
other clauses.
Labels are treated as null clauses and can be
traced selectively to aid debugging.
</para>
<para>
Duplicate labels are permitted, but control is only passed
to the first of any duplicates in a program. The duplicate labels occurring
later can be traced but cannot be used as a target of a CALL, SIGNAL, or
function invocation.</para>
</section>
<section id="instructions"><title>Instructions</title>
<indexterm><primary>clauses</primary>
<secondary>instructions</secondary></indexterm>
<indexterm><primary>instructions</primary>
<secondary>definition</secondary></indexterm>
<para>An <emphasis>instruction</emphasis> consists
of one or more clauses describing some course of action for the language
processor to take. Instructions can be assignments, message instructions,
keyword instructions, or commands.</para>
</section>
<section id="assigns"><title>Assignments</title>
<indexterm><primary>clauses</primary>
<secondary>assignment</secondary></indexterm>
<para>A single clause of
the form <emphasis role="italic">symbol=expression</emphasis> is an instruction
known as an <emphasis>assignment</emphasis>. An assignment gives a (new) value
to a variable. See <link linkend="assinmt">Assignments and Symbols</link>.
</para>
<section><title>Extended Assignments</title>
<para>The character sequences <computeroutput>+=, -=, *= /=, %=, //=, ||=, &amp;=, |=, and &amp;&amp;=</computeroutput>
can be used to create extended assignments. These sequences combine an operation with the assignment.
See <link linkend="extassign">Extended Assignments</link> for more details.</para>
</section>
<section id="msgit"><title>Message Instructions</title>
<indexterm><primary>clauses</primary>
<secondary>message instructions</secondary></indexterm>
<indexterm><primary>instructions</primary>
<secondary>message</secondary></indexterm>
<indexterm><primary>message instructions</primary></indexterm>
<para>A <emphasis>message instruction</emphasis> is a single clause in the
form of a message term (see <link linkend="mssg">Message Terms</link>)
or in the form
<emphasis role="italic">messageterm</emphasis>=<emphasis role="italic">expression</emphasis>.
A message is sent to an object, which responds by performing some action.
See <link linkend="msgi">Message Instructions</link>.</para>
</section>
<section id="keyinst"><title>Keyword Instructions</title>
<indexterm><primary>clauses</primary>
<secondary>keyword instructions</secondary></indexterm>
<indexterm><primary>instructions</primary>
<secondary>keyword</secondary></indexterm>
<indexterm><primary>subkeyword</primary></indexterm>
<para>A <emphasis>keyword instruction</emphasis> is one or more clauses, the
first of which starts
with a keyword that identifies the instruction. Keyword instructions control,
for example, the external interfaces and the flow of control. Some keyword
instructions can include nested instructions. In the following example, the
DO construct (DO, the group of instructions that follow it, and its associated
END keyword) is considered a single keyword instruction.</para>
<programlisting>
DO
instruction
instruction
instruction
END
</programlisting>
<para>A <emphasis>subkeyword</emphasis> is
a keyword that is reserved within the context of a particular instruction,
for example, the symbols TO and WHILE in the DO instruction.</para>
</section>
</section>
<section id="cmds"><title>Commands</title>
<indexterm><primary>clauses</primary>
<secondary>commands</secondary></indexterm>
<indexterm><primary>command</primary>
<secondary>clause</secondary></indexterm>
<para>A <emphasis>command</emphasis> is a clause consisting of an expression
only. The expression is evaluated and the result is passed as a command string
to an external environment.</para>
</section>
</section>
<section id="assinmt"><title>Assignments and Symbols</title>
<indexterm><primary>assignment</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>assignment</secondary></indexterm>
<indexterm><primary>equal</primary>
<secondary>sign</secondary>
<tertiary>to indicate assignment</tertiary></indexterm>
<indexterm><primary>restrictions</primary>
<secondary>first character of variable name</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>assigning values to</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>use of</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>simple</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>setting a new value</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>valid names</secondary></indexterm>
<para>A <emphasis>variable</emphasis> is an object whose value can change
during the running of a
Rexx program. The process of changing the value of a variable is
called <emphasis>assigning</emphasis> a new value to it. The value of a
variable is a single object. Note that an object can be
composed of other objects, such as an array or directory object.</para>
<para>You can assign
a new value to a variable with the ARG, PARSE, PULL, or USE instructions,
the VALUE built-in function, or the
but the most
common way of changing the value of a variable is the assignment instruction
itself. Any clause in the form</para>
<para><emphasis role="italic">symbol</emphasis>=<emphasis role="italic">
expression</emphasis>;</para>
<indexterm><primary>= (equal sign)</primary>
<secondary>assignment operator</secondary></indexterm>
<indexterm><primary>assignment</primary>
<secondary>indicator (=)</secondary></indexterm>
<para>is taken
to be an assignment. The result of
<emphasis role="italic">expression</emphasis> becomes the new value
of the variable named by the symbol to the left of the equal sign.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
/* Next line gives FRED the value "Frederic" */
Fred="Frederic"
</programlisting>
<para>The symbol naming the variable cannot begin with a digit
(<computeroutput>0</computeroutput>-<computeroutput>9</computeroutput>)
or a period.</para>
<para>You can use a symbol
in an expression even if you have not assigned a value to it, because a symbol
has a defined value at all times. A variable to which you have not assigned
<indexterm><primary>uninitialized variable</primary></indexterm>
a value is <emphasis>uninitialized</emphasis>. Its value is the characters
of the symbol itself, translated to uppercase (that is,
lowercase <computeroutput>a</computeroutput>-<computeroutput>z</computeroutput>
to uppercase
<computeroutput>A</computeroutput>-<computeroutput>Z</computeroutput>).
However, if it is a compound symbol (described under
<link linkend="compsym">Compound Symbols</link>), its value is the
derived name of the symbol.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
/* If Freda has not yet been assigned a value, */
/* then next line gives FRED the value "FREDA" */
Fred=Freda
</programlisting>
<indexterm><primary>symbol</primary>
<secondary>classifying</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>constant</secondary></indexterm>
<para>The meaning of a symbol
in Rexx varies according to its context. As a term in an expression, a symbol
belongs to one of the following groups: constant symbols, simple symbols,
compound symbols, environment symbols, and stems. Constant symbols cannot
be assigned new values. You can use simple symbols for variables where the
name corresponds to a single value. You can use compound symbols and stems
for more complex collections of variables although the collection classes
might be preferable in many cases. See
<link linkend="clsCollection">The Collection Classes</link>.</para>
<section id="extassign"><title>Extended Assignments</title>
<indexterm><primary>extended assignments</primary></indexterm>
<indexterm><primary>assignment</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>clauses</primary>
<secondary>extended assignment</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>assigning values to</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>use of</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>setting a new value</secondary></indexterm>
<para>The character sequences <computeroutput>+=, -=, *= /=, %=, //=, ||=, &amp;=, |=, and &amp;&amp;=</computeroutput>
can be used to create extended assignment instructions.
An extended assignment combines a non-prefix operator with
an assignment where the term on the left side of the assignment
is also used as the left term of the operator. For
example,</para>
<programlisting>
a += 1
</programlisting>
<para>is exactly equivalent to the instruction</para>
<programlisting>
a = a + 1
</programlisting>
<para>Extended assignments are processed identically to the longer form of the instruction.</para>
</section>
<section id="constnt"><title>Constant Symbols</title>
<indexterm><primary>constant symbols</primary></indexterm>
<para>A <emphasis role="italic">constant symbol</emphasis> starts with
a digit (<computeroutput>0</computeroutput>-<computeroutput>9</computeroutput>)
or a period.</para>
<para>You cannot change the value of a constant symbol. It is simply the string
consisting of the characters of the symbol (that is, with any lowercase
alphabetic characters translated to uppercase).</para>
<para>These are constant symbols: </para>
<programlisting>
77
827.53
.12345
12e5 /* Same as 12E5 */
3D
17E-3
</programlisting>
<para>Symbols where the first character is a period and the second character
is alphabetic are environment symbols.
<link linkend="ensym">Environment symbols</link>
may have a
value other other than the symbol name.
</para>
</section>
<section id="simpsym"><title>Simple Symbols</title>
<indexterm><primary>simple</primary>
<secondary>symbols</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>simple</secondary></indexterm>
<para>A <emphasis role="italic">simple symbol</emphasis> does not contain
any periods and does not start with a digit
(<computeroutput>0</computeroutput>-<computeroutput>9</computeroutput>).</para>
<para>By default, its value is the characters of the symbol (that is, translated
to uppercase). If the symbol has been assigned a value, it names a variable
and its value is the value of that variable.</para>
<para>These are simple symbols: </para>
<programlisting>
FRED
Whatagoodidea? /* Same as WHATAGOODIDEA? */
?12
</programlisting>
</section>
<section id="stems"><title>Stems</title>
<indexterm><primary>assignment</primary>
<secondary>of stems variables</secondary></indexterm>
<indexterm><primary>array</primary>
<secondary>initialization</secondary></indexterm>
<para>A <emphasis role="italic">stem</emphasis> is
a symbol that contains a single period as the last character of the name. It cannot start with
a digit.</para>
<para>These are stems: </para>
<programlisting>
FRED.
A.
</programlisting><para>The value of a stem is always a Stem object. (See
<link linkend="clsStem">The Stem Class</link>.)
The stem variable's Stem object is automatically created the first time
you use the stem variable or a
<link linkend="compsym">compound variable</link>
containing the stem variable name.
The Stem object's assigned name is
the name of the stem variable (with the characters translated to uppercase).
If the stem variable has been assigned a value, or the Stem object has been
given a default value, the assigned name overrides the default stem name.
A reference to a stem variable will return the associate Stem object.
</para>
<indexterm><primary>compound</primary>
<secondary>variable</secondary>
<tertiary>setting new value</tertiary></indexterm>
<indexterm><primary>stem of a variable</primary>
<secondary>assignment to</secondary></indexterm>
<para>When a stem is the target of an assignment, the action taken
depends on the value being assigned. If the new value is a Stem object,
the new Stem object will replace the Stem object that is currently associated
with the stem variable. This can result in multiple stem variables referring to
the same Stem object, effectively creating a variable alias.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
hole. = "empty"
hole.19 = "full"
say hole.1 hole.mouse hole.19
/* Says "empty empty full" */
hole2. = hole. /* copies reference to hole. stem to hole2. */
say hole2.1 hole2.mouse hole2.19
/* Also says "empty empty full" */
</programlisting>
<para>If the new value is not a Stem object,
a new Stem object is created and assigned to the stem variable, replacing the
Stem object currently associated with the stem variable.</para>
<para>
The new value assigned to the
stem variable is given to the new Stem object as a default value. Following
the assignment, a reference to any compound symbol with that stem variable
returns the new value until another value is assigned to the stem, the Stem
object, or the individual compound variable.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
hole. = "empty"
hole.19 = "full"
say hole.1 hole.mouse hole.19
/* says "empty empty full" */
</programlisting>
<indexterm><primary>initialization</primary>
<secondary>of arrays</secondary></indexterm>
<indexterm><primary>initialization</primary>
<secondary>of compound variables</secondary></indexterm>
<para>Thus, you can initialize an entire collection of compound variables to the same value.</para>
<para>You can pass stem collections as function, subroutine, or method
arguments.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
/* CALL RANDOMIZE count, stem. calls routine */
Randomize: Use Arg count, stem.
do i = 1 to count
stem.i = random(1,100)
end
return
</programlisting>
<para>The USE ARG instruction functions as an assignment instruction. The variable
STEM. in the example above is functionally equivalent to:</para>
<programlisting>
stem. = arg(2)
</programlisting>
<note><title>Note</title>
<para>USE ARG must be used to access the stem variable as a collection.
PARSE and PARSE ARG will force the stem to be a string value.</para></note>
<para>Stems can also be returned as function, subroutine, or method results.
The resulting return value is the Stem object associated with the stem variable.
</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
/* RANDOMIZE(count) calls routine */
Randomize: Use Arg count
do i = 1 to count
stem.i = random(1,100)
end
return stem.
</programlisting>
<para>When a stem. variable is used in an expression context, the stem variable
reference returns the associated Stem object. The Stem object will forward
many object messages to it's default value. For example, the STRING method
will return the Stem object's default value's string representation:</para>
<programlisting>
total. = 0
say total. /* says "0" */
</programlisting>
<para>The [] method with no arguments will return the currently associated
default value.
variables can always be obtained by using the stem. However,
this is not the same as using a compound variable whose derived name is the
null string.</para>
<programlisting>
total. = 0
null = ""
total.null = total.null + 5
say total.[] total.null /* says "0 5" */
</programlisting>
<para>You can use the DROP, EXPOSE, and PROCEDURE instructions to manipulate
collections of variables, referred to by their stems.
<computeroutput>DROP FRED.</computeroutput> assigns
a new Stem object to the specified stem. (See
<link linkend="keyDrop">DROP</link>.) <computeroutput>EXPOSE FRED.</computeroutput>
and <computeroutput>PROCEDURE EXPOSE FRED.</computeroutput> expose all possible
variables with that stem (see <link linkend="keyExpose">EXPOSE</link> and
<link linkend="keyProcedure">PROCEDURE</link>).</para>
<para>The DO instruction can also iterate over all of the values
assigned to a stem variable. See <link linkend="keyDo">DO</link> for more details.
</para>
<para><emphasis role="bold">Notes:</emphasis></para>
<orderedlist>
<listitem><para>When the ARG, PARSE, PULL, or USE instruction, the VALUE
built-in function, or the variable pool interface changes a variable, the
effect is identical with an assignment.
</para></listitem>
<listitem><para>Any clause that starts with a symbol and whose second token is
(or starts with) an equal sign (<computeroutput>=</computeroutput>)
is an assignment, rather than an expression
(or a keyword instruction). This is not a restriction, because you can ensure
that the clause is processed as a command, such as by putting a null string
before the first name, or by enclosing the expression in
parentheses. </para>
<para>If you unintentionally use a Rexx keyword as the variable
name in an assignment, this should not cause confusion. For example, the
following clause is an assignment, not an ADDRESS instruction:</para>
<programlisting>
Address="10 Downing Street";
</programlisting>
</listitem>
<listitem><para>You can use the VAR function (see
<link linkend="bifVar">VAR</link>) to test whether
a symbol has been assigned a value. In addition, you can set
<link linkend="uninit">SIGNAL ON NOVALUE</link>
to trap the use of any uninitialized variables (except when they are tails
in compound variables or stem variables, which are always initialized with a Stem object
when first used.)
</para></listitem>
</orderedlist>
</section>
<section id="compsym"><title>Compound Symbols</title>
<indexterm><primary>tail</primary></indexterm>
<indexterm><primary>stem of a variable</primary>
<secondary>description</secondary></indexterm>
<indexterm><primary>assignment</primary>
<secondary>of compound variables</secondary></indexterm>
<indexterm><primary>associative storage</primary></indexterm>
<indexterm><primary>content addressable storage</primary></indexterm>
<indexterm><primary>array</primary>
<secondary>setting up</secondary></indexterm>
<indexterm><primary>compound</primary>
<secondary>symbols</secondary></indexterm>
<indexterm><primary>derived names of variables</primary></indexterm>
<indexterm><primary>compound</primary>
<secondary>variable</secondary>
<tertiary>description</tertiary></indexterm>
<indexterm><primary>period</primary>
<secondary>causing substitution in variable names</secondary></indexterm>
<indexterm><primary>substitution</primary>
<secondary>in variable names</secondary></indexterm>
<indexterm><primary>symbol</primary>
<secondary>compound</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>compound</secondary></indexterm>
<para>A <emphasis role="italic">compound symbol</emphasis>
contains at least one period and two other characters.
It cannot start with a digit or a period, and if there is only one period
it cannot be the last character.</para>
<para>The name begins with a stem (that
part of the symbol up to and including the first period) and is followed by
a tail, which are parts of the name (delimited by periods)
<indexterm><primary>. (period)</primary>
<secondary>causing substitution in variable names</secondary></indexterm>
that are constant
symbols, simple symbols, or null. Note that you cannot use constant symbols
with embedded signs (for example, 12.3E+5) after a stem; in this case the
whole symbol would not be valid.</para>
<para>These are compound symbols: </para>
<programlisting>
FRED.3
Array.I.J
AMESSY..One.2.
</programlisting>
<para>Before the
symbol is used, that is, at the time of reference, the language processor
substitutes in the compound symbol the character string values of any simple
symbols in the tail (<computeroutput>I</computeroutput>,
<computeroutput>J</computeroutput>, and
<computeroutput>One</computeroutput> in the
examples), thus generating a new, derived tail. The value of a compound symbol
is, by default, its the name of the Stem object associated with the stem variable
concatenated to the
derived tail or, if it has been used
as the target of an assignment, the value of Stem element named by the derived
tail.</para>
<para>The substitution in the symbol permits arbitrary indexing (subscripting)
of collections of variables that have a common stem. Note that the values
substituted can contain <emphasis>any</emphasis> characters (including
periods and blanks). Substitution is done only once.</para>
<para>More formally, the derived name of a compound variable that is referenced
by the symbol </para>
<programlisting>
s0.s1.s2. --- .sn
</programlisting>
<para>is given by </para>
<programlisting>
d0.v1.v2. --- .vn
</programlisting>
<para>where <computeroutput>d0</computeroutput> is the name of the Stem
object associated with the stem variable <computeroutput>s0</computeroutput> and
<computeroutput>v1</computeroutput> to <computeroutput>vn</computeroutput>
are the values of the constant or simple symbols
<computeroutput>s1</computeroutput> through <computeroutput>sn</computeroutput>.
Any of the symbols <computeroutput>s1</computeroutput> to
<computeroutput>sn</computeroutput> can be null. The values
<computeroutput>v1</computeroutput> to <computeroutput>vn</computeroutput>
can also be null and can contain <emphasis>any</emphasis> characters (including periods).
Lowercase characters are not translated to uppercase,
blanks are not removed, and periods have no special significance. There is
no limit on the length of the evaluated name.</para>
<para>Some examples of simple and compound symbols follow in the form of a small
extract from a Rexx program: </para>
<programlisting>
a=3 /* assigns "3" to the variable A */
z=4 /* "4" to Z */
c="Fred" /* "Fred" to C */
a.z="Fred" /* "Fred" to A.4 */
a.fred=5 /* "5" to A.FRED */
a.c="Bill" /* "Bill" to A.Fred */
c.c=a.fred /* "5" to C.Fred */
y.a.z="Annie" /* "Annie" to Y.3.4 */
say a z c a.a a.z a.c c.a a.fred y.a.4
/* displays the string: */
/* "3 4 Fred A.3 Fred Bill C.3 5 Annie" */
</programlisting>
<para>You can use compound symbols to set up arrays and lists of variables in
which the subscript is not necessarily numeric, thus offering a great scope
for the creative programmer. A useful application is to set up an array in
which the subscripts are taken from the value of one or more variables,
producing a form of associative memory (content-addressable).</para>
<section id="evcoms"><title>Evaluated Compound Variables</title>
<para>The value of a stem variable is always a Stem object (see
<link linkend="clsStem">The Stem Class</link> for
details). A Stem object is a type of collection that supports the []
and []= methods used by other collection classes. The [] method
provides an alternate means of accessing compound variables that also allows
embedded subexpressions.</para>
<para><emphasis role="bold">Examples:</emphasis></para>
<programlisting>
a=3 /* assigns "3" to the variable A */
z=4 /* "4" to Z */
c="Fred" /* "Fred" to C */
a.[z]="Fred" /* "Fred" to A.4 */
a.[z+1]="Rick" /* "Rick" to A.5 */
a.[fred]=5 /* "5" to A.FRED */
a.[c]="Bill" /* "Bill" to A.Fred */
c.[c]=a.fred /* "5" to C.Fred */
y.[a,z]="Annie" /* "Annie" to Y.3.4 */
say a z c a.[a] a.[z] a.[z+1]
a.[c] c.[a] a.[fred] y.[a,z]
/* displays the string: */
/* "3 4 Fred A.3 Fred Rick Bill C.3 5 Annie" */
</programlisting>
</section>
</section>
<section id="ensym"><title>Environment Symbols</title>
<indexterm><primary>symbols</primary>
<secondary>environment</secondary></indexterm>
<para>An environment symbol starts with a period and has at least one other character.
This character must not be a digit. By default the value of an environment
symbol is the string consisting of the characters of the symbol (translated
to uppercase). If the symbol identifies an object in the current environment,
its value is the mapped object.</para>
<para>These are environment symbols: </para>
<programlisting>
.method // A reference to the Rexx Method class
.true // The Rexx "true" object. Has the value "1"
.xyz // Normally the value .XYZ
</programlisting>
<para>When you use an environment symbol, the language processor performs a
series of searches to see if the environment symbol has an assigned value. The
search locations and their ordering are:
<orderedlist>
<listitem><para>The directory of classes declared on ::CLASS directives (see
<link linkend="clasdi">::CLASS</link>)
within the current program package or added to the current package using
the <link linkend="mthPackageAddClass">addClass() method</link>.</para></listitem>
<listitem><para>The directory of PUBLIC classes declared on ::CLASS directives
of other files included with a ::REQUIRES directive or added to the current
Package instance using the <link linkend="mthPackageAddClass">addPackage() method</link>.
</para></listitem>
<listitem><para>The local environment directory specific to the current
interpreter instance. The local
environment includes process-specific
objects such as the .INPUT and .OUTPUT objects. You can directly access the
local environment directory by using the .LOCAL environment symbol. (See
<link linkend="locenv">The Local Environment Object (.LOCAL)</link>.)</para>
</listitem>
<listitem><para>The global environment directory. The global environment
includes all
permanent Rexx objects such as the Rexx supplied classes (.ARRAY and so on)
and constants such as .TRUE and .FALSE. You can directly access the global
environment by using the .ENVIRONMENT environment symbol (see
<link linkend="envo">The Environment Object</link>).
Entries in the global environment directory can also be accessed via the VALUE
built-in function (see <link linkend="bifValue">VALUE</link>)
by using a null string for the
<emphasis role="italic">selector</emphasis> argument.</para></listitem>
<listitem><para>Rexx defined symbols. Other simple environment symbols are
reserved for use by <link linkend="oneof">Rexx built-in environment objects</link>.
The currently defined built-in
objects are .RS, .LINE, .METHODS, .ROUTINES, and .CONTEXT.</para></listitem>
</orderedlist>
</para>
<para>If an entry is not found for an environment symbol, then the default
character string value is used.</para>
<note><title>Note</title>
<para>You can place entries in both the .LOCAL
and the .ENVIRONMENT directories for programs to use. To avoid conflicts with
future Rexx defined entries, it is recommended that the entries that you place
in either directory include at least one period in the entry name.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
/* establish settings directory */
.local~setentry("MyProgram.settings", .directory~new)
</programlisting>
</note>
</section>
</section>
<section id="msgi"><title>Message Instructions</title>
<indexterm><primary>message instructions</primary></indexterm>
<indexterm><primary>message sequence instructions</primary></indexterm>
<indexterm><primary>instructions</primary>
<secondary>message</secondary></indexterm>
<para>You can send a message to an object to perform an action, obtain a result,
or both. You use a message instruction if the main purpose of the message
is to perform an action. You use a message term (see
<link linkend="mssg">Message Terms</link>)
if the main purpose of the message is to obtain a result.</para>
<para>A <emphasis>message instruction</emphasis> is a clause of the form:
</para>
<programlisting>
<![CDATA[
>>-messageterm--+-------------+--;-----------------------------><
+-=expression-+
]]>
</programlisting>
<para>If there is only a <emphasis role="italic">messageterm</emphasis>,
the message is sent in exactly the same way as for a message term (see
<link linkend="mssg">Message Terms</link>). If the message
yields a result object, it is assigned to the sender's special variable RESULT.
If you use the ~~ form of message term, the receiver object
is used as the result. If there is no result object, the variable RESULT is
dropped (becomes uninitialized).
A message term using ~~ is sometimes referred to as a
<emphasis role="italic">cascading message</emphasis>.
</para>
<para><emphasis role="bold">Example:</emphasis></para>
<indexterm><primary>examples</primary>
<secondary>message instructions</secondary></indexterm>
<programlisting>
mytable~add("John",123)
</programlisting>
<para>This sends the message ADD to the object MYTABLE. The ADD method need not
return a result. If ADD returns a result, the result is assigned to the variable
RESULT.</para>
<para>The equal sign (=) sets a value. If
<computeroutput>=expression</computeroutput> follows
the message term, a message is sent to the receiver object with an
<computeroutput>=</computeroutput> concatenated to the end of the
message name. The result of evaluating
the expression is passed as the first argument of the message.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
person~age = 39 /* Same as person~"AGE="(39) */
table[i] = 5 /* Same as table~"[]="(5,i) */
</programlisting>
<para>The expressions are evaluated in the order in which the arguments are
passed to the method. That is, the language processor evaluates the
<computeroutput>=expression</computeroutput> first. Then it evaluates
the argument expressions within any [] pairs from left to right.</para>
<para>The extended assignment form may also be used with messaging terms.</para>
<para><emphasis role="bold">Example:</emphasis></para>
<programlisting>
table[i] += 1 -- Same as table[i] = table[i] + 1
</programlisting>
<para>See <link linkend="extassign">Extended Assignments</link> for more details</para>
</section>
<section id="cmdhost"><title>Commands to External Environments</title>
<para>Issuing commands to the surrounding environment is an integral part of
Rexx.</para>
<section id="xenvir"><title>Environment</title>
<indexterm><primary>default</primary>
<secondary>environment</secondary></indexterm>
<para>The base system for the language processor is assumed to include
at least one environment for processing commands. An environment is selected by
default on entry to a Rexx program. You can change the environment by using
the ADDRESS instruction. You can find out the name of the current environment
by using the ADDRESS built-in function. The underlying operating system defines
environments external to the Rexx program. The environments selected depend
on the caller. Normally the default environment is the used shell, mostly "CMD"
on Windows systems and "bash" on Linux systems.
If called from an editor that accepts subcommands from
the language processor, the default environment can be that editor.</para>
<para>A Rexx program can issue commands&mdash;called
<emphasis>subcommands</emphasis>&mdash;to other application programs.
For example, a Rexx program written
for a text editor can inspect a file being edited, issue subcommands to make
changes, test return codes to check that the subcommands have been processed
as expected, and display messages to the user when appropriate.</para>
<para>An application that uses Rexx as a macro language must register its
environment with the Rexx language processor. See the
<citetitle pubwork="book">Open Object Rexx: Programming Guide</citetitle>
for a discussion of this mechanism.</para>
</section>
<section id="commnds"><title>Commands</title>
<indexterm><primary>command</primary>
<secondary>alternative destinations</secondary></indexterm>
<indexterm><primary>command</primary>
<secondary>issuing to host</secondary></indexterm>
<indexterm><primary>host commands</primary>
<secondary>issuing commands to underlying operating system</secondary>
</indexterm>
<indexterm><primary>special</primary>
<secondary>variables</secondary>
<tertiary>RC</tertiary></indexterm>
<para>To send a command to the currently addressed environment, use a clause
of the form:</para>
<programlisting>
expression;
</programlisting>
<para>The expression (which must not be an expression that forms a valid message
instruction&mdash;see <link linkend="msgi">Message Instructions</link>)
is evaluated, resulting in a character string value
(which can be the null string), which is then prepared as appropriate
and submitted to the environment specified by the current ADDRESS setting.
</para>
<para>The environment then processes the command and returns control
to the language processor after setting a return code. A
<emphasis>return code</emphasis> is a string, typically a number,
that returns some information
about the command processed. A return code usually indicates if a command
was successful but can also represent other information. The language processor
places this return code in the Rexx special variable RC.
<indexterm><primary>return</primary>
<secondary>code</secondary>
<tertiary>as set by commands</tertiary></indexterm>
<indexterm><primary>RC (return code)</primary>
<secondary>set by commands</secondary></indexterm>
<indexterm><primary>altering</primary>
<secondary>special variables</secondary></indexterm>
<indexterm><primary>variable</primary>
<secondary>special</secondary>
<tertiary>RC</tertiary></indexterm>
See <link linkend="spvard">Special Variables</link>.</para>
<para>In addition to setting a return code, the underlying system can also
indicate to the language processor if an error or failure occurred. An
<emphasis>error</emphasis> is a condition raised by a command to which a program
that uses that command can respond. For example, a locate command to an editing
system might report <computeroutput>requested string not found</computeroutput>
as an error. A <emphasis>failure</emphasis> is a condition raised by a command
to which a program that uses that command cannot respond, for example, a
command that is not executable or cannot be found.</para>
<para>Errors
<indexterm><primary>error</primary>
<secondary>definition</secondary></indexterm>
and failures in commands can affect Rexx processing if a condition
trap for ERROR or FAILURE is ON (see
<link linkend="condtra">Conditions and Condition Traps</link>). They can also
<indexterm><primary>failure, definition</primary></indexterm>
<indexterm><primary>error</primary>
<secondary>from commands</secondary></indexterm>
cause the command to be traced if <computeroutput>TRACE E</computeroutput>
or <computeroutput>TRACE F</computeroutput> is
set. <computeroutput>TRACE Normal</computeroutput> is the same as
<computeroutput>TRACE F</computeroutput> and is the
default&mdash;see <link linkend="keyTrace">TRACE</link>.</para>
<para>The .RS environment symbol can also be used to detect command failures
and errors. When the command environment indicates that a command failure
has occurred, the Rexx environment symbol .RS has the value
<computeroutput>-1</computeroutput>.
When a command error occurs, .RS has a value of
<computeroutput>1</computeroutput>. If the command
did not have a FAILURE or ERROR condition, .RS is
<computeroutput>0</computeroutput>.</para>
<para>Here is an example of submitting a command. Where the default
environment is Windows, the sequence:</para>
<programlisting>
fname = "CHESHIRE"
exten = "CAT"
"TYPE" fname"."exten
</programlisting>
<para>would result in passing the string
<computeroutput>TYPE CHESHIRE.CAT</computeroutput> to
the command processor, CMD.EXE.
The simpler expression:</para>
<programlisting>
"TYPE CHESHIRE.CAT"
</programlisting>
<para>has the same effect.</para>
<para>On return, the return code placed in RC will have the value
0 if the file CHESHIRE.CAT were typed, or a nonzero value if the file could
not be found in the current directory.</para>
<note><title>Note</title>
<para>Remember that the expression is evaluated before
it is passed to the environment. Constant portions of the command should be
specified as literal strings.</para></note>
<para><emphasis role="bold">Windows Example:</emphasis></para>
<programlisting>
delete "*".lst /* not "multiplied by" */
var.003 = anyvalue
type "var.003" /* not a compound symbol */
w = any
dir"/w" /* not "divided by ANY" */
</programlisting>
<para><emphasis role="bold">Linux Example:</emphasis></para>
<programlisting>
rm "*".lst /* not "multiplied by" */
var.003 = anyvalue
cat "var.003" /* not a compound symbol */
w = any
ls "/w" /* not "divided by ANY" */
</programlisting>
<para>
Enclosing an entire message instruction in parentheses causes
the message result to be used as a command. Any clause that is a message
instruction is not treated as a command. Thus, for example, the clause </para>
<programlisting>
myfile~linein
</programlisting>
<para>causes the returned line to be assigned to the variable RESULT, not to
be used as a command to an external environment, while</para>
<programlisting>
(myfile~linein)
</programlisting>
<para>would submit the return value from the linein method as a command to the external
environment.</para>
</section>
</section>
<section id="linux"><title>Using Rexx on Windows and Unix</title>
<para></para>
<para>Rexx programs can call other Rexx programs as external
functions or subroutines with the
<link linkend="keyCall">call</link> instruction.</para>
<para>If a program is called with the
<link linkend="keyCall">call</link> instruction, the program runs in the same
process as the calling program.
If you call another program by a Rexx command, the program is executed in
a new process and therefore does not share .environment, .local,
or the Windows/Unix shell environment.</para>
<para><emphasis role="bold">Examples:</emphasis></para>
<programlisting>
call "other.REX" /* runs in the same process */
"rexx other.REX" /* runs in a new child process */
"start rexx other.REX" /* runs in a new detached process */
</programlisting>
<para>When Rexx programs call other Rexx programs as commands, the return code
of the command is the exit value of the called program provided that this
value is a whole number in the range -32768 to 32767. Otherwise, the exit
value is ignored and the called program is given a return code of 0.</para>
</section>
</chapter>

Get latest updates about Open Source Projects, Conferences and News.

Sign up for the SourceForge newsletter:





No, thanks