====== Variables ====== XC=BASIC is a statically typed programming language which means that the type of a variable is known at compile time. All variables have a type and that type cannot change. ===== Defining Variables ===== In an XC=BASIC program, all variables must be defined before they're used. Either you define them using the [[DIM]] statement (this is called //explicit// definition) or the compiler will auto-define them in certain situations. The latter is called //implicit// definition. ==== Explicit Definition ==== The ''DIM'' statement may be used to explicitly define variables. Here are some examples of variable definition using ''DIM'': DIM enemy_count AS INT DIM score AS DECIMAL DIM gravity AS FLOAT DIM name$ AS STRING * 16 Apart from the ''DIM'' statement, there are other cases where you may explicitly define a variable. You will learn about those later. Defining variable types by using sigils (the ''#'', ''%'' and ''!'' suffixes) is no longer supported in XC=BASIC. The ''$'' character is allowed at the end of variable names for readability but the variable won't be defined as ''STRING'' just because the ''$'' sign is there. You //must// use ''DIM'' to define Strings. ==== Implicit Definition ==== If an undefined variable is encountered by the compiler, it will try to define it silently. For example: a = 5 PRINT a The above program works because the compiler implicitly defines the variable ''a'' in the first line. But what will its type be? The compiler first checks the right hand side of the assignment, in this case the number ''5''. As stated previously, a number between 0 and 255 is best represented by the Byte type, and therefore the compiler will infer ''a'' to be of type Byte. This is called an //inferred type// because the compiler examines the expression and, using the above stated rules, decides which type best represents it. This seems very convenient, but it is something you should generally avoid so that the compiler will not automatically assign data types you don't intend and/or produce results that are inaccurate yet hard to track down in code. Take the following example: a = 5 a = a + 300 PRINT a In CBM BASIC, where the only numeric type is ''FLOAT'', you can safely expect the result to be ''305''. In XC=BASIC this is not the case. Let's break down the above example and see how the compiler will handle it: - The compiler defines ''a'' as ''BYTE'' and assigns the value ''5'' to it. - The expression ''a + 300'' is evaluated. Since ''300'' is an ''INT'', the expression will be evaluated as ''INT'', resulting to ''305''. - Now the result must be assigned to ''a''. The number ''305'' can't be assigned to a ''BYTE'', so it will be truncated to 8 bits. - The result is ''49''. Since, on the surface, the result does not make any sense to a human mind, it might be difficult to track down the problem. We can fix the above program by explicitly defining ''a'' as ''INT'': DIM a AS INT a = 5 a = a + 300 ' The result is: 305 PRINT a It is recommended that you define variables explicitly rather than let the compiler guess their types to avoid issues like the example above. Unlike CBM BASIC variables, which are automatically initialized to ''0'', XC=BASIC does not provide any initialization of variables. This means that you cannot assume anything about the value of a variable until you have assigned some value to it. The initial value of a variable is simply whatever happens to be in the memory location XC=BASIC assigns to the variable. ====== Constants ====== Constants are simple textual labels that represent numeric values //in compile time//. When the compiler encounters a constant, it will replace it with the value it represents. The benefits of using constants instead of variables are: * As opposed to variables, no memory is allocated for constants * Constants are faster to evaluate than variables Always use constants over variables whenever possible to save memory and speed up program execution. See the [[CONST]] keyword reference page for more information. ====== Arrays ====== Arrays are similar to arrays in CBM BASIC. * They must be explicitly defined in all cases using ''DIM'' * The maximum number of dimensions is 3 A few examples of defining arrays: DIM cards(52) AS BYTE DIM my_cards(5) AS BYTE DIM matrix(5, 5) AS FLOAT Accessing array members is done using the usual BASIC syntax: DIM my_array(3, 3) AS LONG x = my_array(0, 1) Array indices are zero-based which means the first item's index is ''0''. For performance reasons, array bounds are not checked at runtime. If you use an index that is out of the bounds, the result will be unpredictable. DIM numbers(10) AS LONG ' This will compile fine but ' probably break your program because ' the last index in the array is 9. i = 10 numbers(i) = 9999 ====== Variable Scope ====== There are three scopes in XC=BASIC: * SHARED: the widest scope, a shared variable is visible in all Code Modules. A Code Module is a single source file (for example: //program.bas//). Learn more about [[code_modules|Code Modules here]]. * GLOBAL: the variable is visible in the current Code Module (in the source file where it was defined). * LOCAL: the variable is only visible within the ''SUB'' or ''FUNCTION'' where it was defined. If you define a variable outside a ''SUB'' or ''FUNCTION'', it will be defined in the **Global** scope by default which means that it can be accessed from everywhere within that BAS source file (even from within ''SUB''s and ''FUNCTION''s), but not from other files. If you define a variable inside a ''SUB'' or ''FUNCTION'', it will be defined in the **Local** scope of that ''SUB'' or ''FUNCTION'' and it won't be accessible from anywhere else. Using the ''SHARED'' keyword in a ''DIM'' statement, you can make a variable visible from all Code Modules: ' This file is first.bas ' 'a' is a global variable in this file only DIM a AS INT ' 'b' is a shared variable visible in other files as well DIM SHARED b AS INT a = 5 b = 10 INCLUDE "second.bas" ' Will print: 5 PRINT a ' Will print: 11 PRINT b ' This file is second.bas ' 'a' is a global variable in this file only ' It doesn't collide with the other 'a' in first.bas DIM a AS INT a = 6 ' We can access 'b' from first.bas b = 11 ====== Fast Variables ====== If you define a variable as ''FAST'', it will be reserved on the zero page, making it faster under the hood to reference and operate on. The space on zero page is limited ([[v3:memory_model|37-74 bytes, depending on target machine]]), but that's enough space to supply a relatively generous number of FAST variables. DIM FAST ix AS BYTE FOR ix = 0 TO 255 ' A very fast loop NEXT When no more variables can be placed on the zero page, the compiler will emit a warning and ignore the ''FAST'' directive from then on. <- datatypes|Previous page ^ variables|Variables ^ operators|Next page ->