BASIC 编程/规范 BASIC
BASIC 编程语言已经标准化,首先是在美国(美国)由美国国家标准协会(ANSI)标准化,后来在欧洲由欧洲计算机制造商协会(ECMA)标准化,从而产生了美国国家标准 (ANS) X3.60-1978 用于最小 BASIC 和 X3.113-1987 用于完整 BASIC(由前者制定),以及欧洲计算机制造商协会 标准 55 用于最小 BASIC(1978 年制定)和 标准 116 用于完整 BASIC(1986 年制定)。
标准的目标是促进 BASIC 程序在各种系统之间的可互换性,并且通过这两个组织之间的严格合作,能够在相应的 ANSI 和 ECMA 标准之间保持完全兼容性。
标准建立了,除其他外
- 用 BASIC 编写的程序的语法,以及
- 解释用 BASIC 编写的程序含义的语义规则。
如今,只有 ECMA 标准公开可用。
允许的字符集由以下内容给出:
- 从 A 到 Z 的大写字母集,
- 从 0 到 9 的数字集,
- 符号集 !, #, $, %, &, (, ), +, -, *, /, ^, ., ,, ;, :, <, =, >, _, ?, ', "
- 空格字符
最小 BASIC 中的保留关键字为(总共 26 个):
- BASE
- DATA
- DEF
- DIM
- END
- FOR
- GO
- GOSUB
- GOTO
- IF
- INPUT
- LET
- NEXT
- ON
- OPTION
- RANDOMIZE
- READ
- REM
- RESTORE
- RETURN
- STEP
- STOP
- SUB
- THEN
- TO
其含义将在接下来的部分中解释。
变量在 BASIC 中用于保存字符字符串或数值,后者可以是标量或矢量性质。
对于字符字符串的变量,每个变量名由 A - Z 之间的单个字母和美元符号 $ 组成。因此,A$、B$、...、Z$ 都是字符字符串的有效变量名,而 A# 或 Z% 则不是。
对于数值标量变量,每个变量名由 A - Z 之间的单个字母和一个可选数字组成。因此,A、B、C1、D2 等是标量值的有效变量名,而 A11、B22 等则不是。
对于数值矢量变量,每个变量名由 A - Z 之间的单个字母和一个或两个数字组成,数字之间用逗号分隔,并用括号括起来以表示一维或二维数组。因此,A(1)、B(2)、C(1,1)、D(2,2) 等是矢量值的有效变量名。
这种约定使得 BASIC 中不需要显式声明变量,因为美元符号用于区分字符字符串和数值,而下标的存在则用于区分矢量变量和标量变量。
字符字符串由允许的字符集中任何字符的组合定义,这些字符组合用双引号括起来,任何字符字符串的长度限制为 18 个字符(在打印或备注语句中的字符字符串除外,将在后面看到,它们可以与行号和行长限制一样长)。因此,""、" "、"1 2 3 4 5 6 7 8 9"、"A B C D E F G H I"、"! # $ % & ... ' " 等都是允许的字符字符串,而 "1 2 3 4 5 6 7 8 9 0"、"A B C D E F G H I J"、"! # $ % & ( ) + - * / ^ . , ; : < = > _ ? ' " 等则不是,因为它们超过了 18 个字符的限制。
数值常量以十进制表示法的位置表示法表示标量数值。可选符号数值常量有四种一般语法形式:
- 隐式点表示 (sd...d),例如 1、2、+1、-2 等,
- 显式点未缩放表示 (sd...drd...d),例如 1.0、2.0、+1.0、-2.0 等,
- 显式点缩放表示 (sd...drd...dEsd...d),例如 1.0E1、2.0E-1、+1.0E+1.0、-2.0E-2.0 等,
- 隐式点缩放表示 (sd...dEsd...d),例如 1.0E1、2.0E-1、+1.0E+1、-2.0E-2 等,
其中
- s 是一个可选符号 (+ 或 -) ,
- d 是一个十进制数字 (0 - 9) ,
- r 是一个句点 (.) ,以及
- E 表示 10 的幂。
数值常量可以有任意数量的数字,但内部至少要有六位有效数字,范围在 1E-38 和 1E+38 之间。
大小小于机器无穷小的数值常量将被替换为零,而大小大于机器无穷大的常量将被替换为具有相应符号的机器无穷大。
BASIC 是一种面向行的语言,从某种意义上说,BASIC 程序可以看作是一系列行,最后一行是结束行,每一行都包含一个关键字。此外,每一行都以一个唯一的行号开头,作为该行中包含的语句的标签。
因此,在 BASIC 中,每个程序都可以用以下 巴科斯-诺尔范式 (BNF) 表示
- program = block end-line
- block = line / for-block
- line = line-number statement
- line-number = digit digit? digit? digit?
- end-line = line-number end-statement
- end-statement = END
- statement = data-statement / def-statement / dimension-statement / gosub-statement / goto-statement / if-then-statement / input-statement / let-statement / on-goto-statement / option-statement / print-statement / randomize-statement / read-statement / remark-statement / restore-statement / return-statement / stop-statement
因此,以下简单的示例是 BASIC 程序的有效示例:
- 一个两行程序(只有一个注释语句,用于记录程序,不产生输出,和一个结束语句,用于终止程序)
10 REM "REMARK STATEMENT" 20 END
- 一个三行程序(只有一个注释语句,一个打印语句,用于打印一个字符串,和一个结束语句)
10 REM "HELLO WORLD PROGRAM" 20 PRINT "HELLO, WORLD!" 30 END
程序行按顺序执行,从第一行开始,直到
- 控制语句指示其他操作,或
- 发生异常情况,导致程序异常终止,或
- 执行停止语句或结束语句。
因此,在第一个示例中,第一行,10 REM "REMARK STATEMENT"
,由一个非控制语句组成,该语句不产生输出或内部活动,然后传递到第二行,20 END
,该行由一个控制语句组成,即结束语句,该语句结束程序。
在第二个示例中,在注释语句行和结束语句行之间存在一个额外的行,该行由一个打印语句组成,也是一个非控制语句,用于打印一个字符串。
行号的值是正整数,前导零没有影响。因此,1、01、10、010 等都是有效的行号。通常,行号以 5 或 10 的倍数给出,例如 10、20、30、40 等,这在需要在现有行之间插入额外行的情况下留出空间。
此外,行可以长达 72 个字符,因此为行号保留 4 个字符,并在行号和关键字之间用空格作为分隔符,则一行中可打印的字符还剩下 67 个。
空格可以在 BASIC 程序中的任何位置出现,不会影响程序的执行,并且可以用来提高程序的可读性。
程序中的所有关键字可以至少由一个空格前缀,如果不在行尾,也可以至少由一个空格后缀。
空格不应出现在
- 行的开头
- 行号中
- 关键字中
- 数值常量中
- 函数或变量名中
- 双字符关系符号中
程序变量
[edit | edit source]BASIC 中的变量与数值或字符串值相关联,在数值的情况下,可以是简单变量,也可以是对一维或二维数组元素的引用,然后被称为下标变量或复合变量。
如前所述,简单数值变量由一个大写字母后跟一个可选的单个数字命名,而下标变量由一个大写字母后跟一个或两个数字命名,在最后一种情况下,数字之间用逗号分隔,并用括号括起来。
字符串变量也由一个大写字母后跟一个美元符号命名。
在程序执行的任何时刻,一个数值变量与一个单一数值相关联,而一个字符串变量与一个单一字符串值相关联,与变量相关联的值可能会在程序执行过程中被程序语句更改。
与字符串变量相关联的字符串的长度可以在程序执行期间更改,从空字符串的长度 0 变化到 18 个字符。
简单数值变量和字符串变量通过它们在程序中的出现隐式声明(由于给定的命名约定,也不需要类型定义),虽然在程序开始时将它们初始化或设置为有意义的值,然后在任何语句中使用它们是一种良好的编程实践。
另一方面,下标变量引用一维或二维数组中由下标值或值选择的元素,下标是整数值。
除非在维度语句(稍后将看到)中明确声明,否则下标变量会通过它们在程序中的首次出现隐式声明,在这种情况下,每个下标的范围应理解为从零到十,包括零和十,除非存在一个选项语句,表示该范围从一到十,包括一和十。
必须注意的是,同一个字母不能同时用作简单变量名和复合变量名,也不能同时用作一维数组名和二维数组名。
相反,这种限制不适用于简单变量和字符串变量,它们的名字除了美元符号外可以相同。
因此,以下简单的示例是 BASIC 程序的有效示例:
- 前面的三行程序,带有一个稍微不同的注释行和一个新的字符串,用于指示要打印的 pi 值
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 PRINT "PI = 3.14159265" 30 END
- 一个修改后的四行程序,它使用 let 语句在第二行将数值常量 3.14159265 赋值给数值变量 P,以及一个包含字符串常量和数值变量的打印语句,作为一个逗号分隔的参数列表,位于第三行
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET P = 3.14159265 30 PRINT "PI = ", P 40 END
- 一个修改后的五行程序,仍然使用 let 语句在第二行将数值常量 3.14159265 赋值给数值变量 P,现在还使用 let 语句在第三行将字符常量 "PI = " 赋值给字符串变量 P$ - 第四行的打印语句现在由字符串变量和数值变量组成的逗号分隔的参数列表组成
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET P = 3.14159265 30 LET P$ = "PI = " 40 PRINT P$, P 50 END
语句
[edit | edit source]到目前为止,我们已经了解了如何通过 let 语句在程序中声明/初始化简单数值变量和字符串变量,以及如何使用打印语句打印它们。
有时,不仅需要打印变量的值,无论是数值还是字符,还需要将该值作为输入引入程序,以便计算数值或根据条件的值打印消息。对于这些情况,需要使用表达式、数学函数和控制语句,我们将在本节中介绍。
输入/输出、数学运算符、表达式
[edit | edit source]表达式通常分为数值表达式和字符串表达式。
在数值表达式的例子中,这些表达式是由变量、常量、数学函数以及加法、减法、乘法、除法和乘方运算构成的。
数值表达式的形成和计算遵循正常的代数规则,上标符号、星号、斜杠、加号和减号分别用于表示乘方运算、乘法运算、除法运算、加法运算和减法运算。
除非括号另有规定,否则首先执行乘方运算,然后执行乘法和除法,最后执行加法和减法,其中优先级相同的运算从左到右关联。因此,A - B - C 被解释为 (A - B) - C,A / B / C 被解释为 (A / B) / C,A - B / C 被解释为 A - (B / C),因为在前两个表达式中,所有数学运算符的优先级都相同,因此从左到右计算,而在最后一个表达式中,运算符之间存在不同的优先级,因此除法在减法之前计算。
以下例子以简单的方式说明了到目前为止看到的概念
- 一个程序,它打印数值常量 1.4142 的乘方 2 的值(也计算 1.4142 的平方),以及一些文本
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 PRINT "THE SQUARE OF 1.4142 IS ", 1.4142^2 30 END
- 一个程序,它定义一个数值变量 S,其值为 1.4142,并打印该数值变量的乘方 2 的值(也计算 1.4142 的平方),以及一些文本
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET S = 1.4142 30 PRINT "THE SQUARE OF ", S, " IS ", S^2 40 END
- 一个程序,它定义一个数值变量 S,其值为 1.4142,计算 S 乘以 S 的积(也计算 1.4142 的平方),将该值赋值给一个数值变量 S2,并打印 S 和 S2 的值,以及一些文本作为字符串常量
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET S = 1.4142 30 LET S2 = S * S 40 PRINT "THE SQUARE OF ", S, " IS ", S2 50 END
- 一个程序,它定义一个数值变量 S,其值为 1.4142,另一个变量 S2 为 2.0000,并打印 S2 除以 S 的运算结果,以及一些文本作为字符串常量
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET S = 1.4142 30 LET S2 = 2.0000 40 PRINT "THE SQUARE ROOT OF ", S2, " IS APPROXIMATELY ", (S2 / S) 50 END
- 一个与前面程序类似的程序,它定义一个数值变量 S,其值为 1.4142,另一个变量 S2 为 2.0000,但打印 S 减去 S2 除以 S 的结果的运算结果(从而给出近似值的精度度量 - 这是我们稍后将要看到的用于计算数字平方根的数值方法的核心),以及一些文本作为字符串常量
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET S = 1.4142 30 LET S2 = 2.0000 40 PRINT S, " AND THE QUOTIENT OF ", S2, " BY ", S, " DIFFER BY ", (S - S2 / S) 50 END
- 一个与前面程序略有不同的程序,它要求用户输入一个数字,用于计算该数字的平方
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET S = 0.0 30 PRINT "THIS PROGRAM CALCULATES THE SQUARE OF A NUMBER" 40 INPUT "PLEASE ENTER THE NUMBER WHOSE SQUARE IS TO BE CALCULATED: ", S 50 PRINT "THE SQUARE OF ", S, " IS ", S^2 60 END
数学函数
[edit | edit source]到目前为止,我们已经了解了如何定义数值变量和字符变量、编写行的规则、基本输入和输出以及简单算术的规则。
但如果需要计算一个数字的平方根,该怎么办?为此,默认情况下提供了基本的数学函数。这些函数是
- 一个数字的绝对值,ABS(X)
- 一个数字的反正切值,ATN(X)
- 一个以弧度表示的数字的余弦值,COS(X)
- 一个数字的指数值,EXP(X)
- 一个数字的整数部分,INT(X)
- 一个数字的自然对数值,LOG(X)
- 一个数字的符号,SGN(X)
- 一个以弧度表示的数字的正弦值,SIN(X)
- 一个正数的平方根,SQR(X)
- 一个在区间 (0,1) 中均匀分布的伪随机数,RND()
- 一个以弧度表示的数字的正切值,TAN(X)
让我们看一些例子
- 一个程序,它使用提供的 SQR 数学函数计算 2 的平方根
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET S2 = 2.0 30 LET S = SQR(S2) 40 PRINT "THE SQUARE ROOT OF ", S2, " IS ", S 50 END
- 一个程序,它要求用户输入一个数字,用于计算该数字的余弦值
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET X = 0.0 30 INPUT "PLEASE ENTER THE NUMBER WHOSE COSINE IS TO BE CALCULATED: ", X 40 PRINT "THE COSINE OF ", X, " IS ", COS(X) 50 END
- 一个程序,它要求用户输入一个数字,用于计算该数字的正弦值
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET X = 0.0 30 INPUT "PLEASE ENTER THE NUMBER WHOSE SINE IS TO BE CALCULATED: ", X 40 PRINT "THE SINE OF ", X, " IS ", SIN(X) 50 END
- 一个程序,它要求用户输入一个数字,用于计算该数字的正切值
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET X = 0.0 30 INPUT "PLEASE ENTER THE NUMBER WHOSE TAN IS TO BE CALCULATED: ", X 40 PRINT "THE TAN OF ", X, " IS ", TAN(X) 50 END
- 一个程序,它要求用户输入一个数字,用于计算该数字的指数值
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET X = 0.0 30 INPUT "PLEASE ENTER THE NUMBER WHOSE EXP IS TO BE CALCULATED: ", X 40 PRINT "THE EXP OF ", X, " IS ", EXP(X) 50 END
- 一个程序,它要求用户输入一个数字,用于计算该数字的自然对数值
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 LET X = 0.0 30 INPUT "PLEASE ENTER THE NUMBER WHOSE LOG IS TO BE CALCULATED: ", X 40 PRINT "THE LOG OF ", X, " IS ", LOG(X) 50 END
- 一个程序,用于打印一个在区间 (0,1) 中均匀分布的伪随机数
10 REM "SIMPLE PROGRAM FOR DEMONSTRATION PURPOSES" 20 PRINT "PSEUDO-RANDOM NUMBER UNIFORMLY DISTRIBUTED IN (0,1): ", RND() 30 END
最小 BASIC 示例程序可在相应页面找到。