Scope refers to the visibility of declarations within the source code. That is, given a particular declaration, the scope of the declaration determines where it is legal to reference that declaration in code or not. With Firewing, there are three main levels of scope:
- Block Scope - Available within the code block in which an item is declared
- Subroutine and Function Scope - Available to all code within the subroutine or function in which an item is declared
- Module Scope - Available to all code within the module in which an item is declared
A block is a set of statements which is enclosed within certain types of declaration statements. Examples of this type of statement include:
- Do…Loop Until
- If…ElseIf…Else…End If
- Select…End Select
- While…End While
- With…End With
An item declared inside one of above statements can be considered local to that statement block. For example,
If a = b Then Const varInit = 10 Dim var As Byte = a * varInit End If
In this example, varInit and var are local to the block that begins with "if a = b then" and ends with "end if". This means that varInit and var cannot be seen outside of the if…then statement block. For example,
If a = b Then Const varInit = 10 Dim var As Byte = a * varInit End If Var = 100
Will generate a "variable not declared" compilation error when trying to assign 100 to var, because var does not exist outside of the if…then statement block.
An item declared within a subroutine or function is not available outside that procedure. Only the subroutine or function that contains the declaration can use it. Variables at the subroutine or function level are commonly referred to as local variables. If you declare an item at the subroutine or function level, it can be seen by all other block scope items within that routine. For example,
Imports USART Sub Main() Dim found As Boolean = False If USART.DataAvailable Then found = True End If End Sub
Because found is declared at the subroutine level, if can be referenced within the if…then statement block. Another way to think of subroutine or function scope is that of having a super block scope, in which all other block scopes live.
Any item declared inside a module but outside of a subroutine or function has module scope. By default, any declarations that have module scope are private. That is, only subroutine and functions within the module can access the private declaration item. Other modules or programs cannot access a declaration item that is private. If you want other programs or modules to see a declaration, it must be explicitly declared as public. The private and public keywords are often referred to as access modifiers, because they control the accessibility of declaration types.
A public declaration is therefore the interface to a module. Remember, all Firewing declarations are private by default. If you want other modules or programs to access them, they must be explicitly declared as public. For example,
Imports USART Module MyUtils ' private helper Function GetMax(ByRef array() As Byte) As Byte GetMax = 0 For index As Byte = 0 To UBound(array) If array(index) > GetMax Then GetMax = array(index) End If Next End Function ' public interface Public Sub DisplayMax(ByRef array() As Byte) USART.Write("MAX = ", CStr(GetMax(array)), 13, 10) End Sub End Module
The module is named MyUtils, which declares a private helper function called GetMax() and a public interface subroutine called DisplayMax(). The DisplayMax() subroutine uses the private helper GetMax() to calculate the maximum array value, before outputting via the USART module's Write() subroutine. We can now use this module in a program, to output the maximum value of an array,
Imports USART Imports MyUtils Sub Main() Dim array(5) As Byte For index As Byte = 0 To UBound(array) array(index) = USART.ReadByte Next MyUtils.DisplayMax(array) End Sub
However, if you try and make a call to the private helper function GetMax() from the program, an error is generated during compilation.
|It's sometimes useful to understand how the compiler finds a declaration. For example, if your subroutine or function references a variable called Index, it will first look to see if a local variable or parameter called Index has been declared. If it cannot be found, then it will then look in the current module or program to see if the variable has been declared at the module level. If it has still not been found, it will then search all imported files referenced in the current module to see if any public variables called Index have been declared. If it still cannot be found, an error is generated.|