User Tools

Site Tools


whole-array_20operations_20in_20structures

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

whole-array_20operations_20in_20structures [2018/03/31 13:19]
127.0.0.1 external edit
whole-array_20operations_20in_20structures [2018/04/17 19:29] (current)
tbest3112 Added syntax highlighting
Line 2: Line 2:
  
 //by Richard Russell, August 2013//\\ \\  As it states in the main [[http://​www.bbcbasic.co.uk/​bbcwin/​manual/​bbcwin2.html#​members|help documentation]] the 'whole array' operations (e.g. assignment, arithmetic and the SUM and MOD functions) cannot be used with arrays which are structure members. Similarly, you cannot pass a structure-member array as the parameter of an FN or PROC. These limitations arise because of the need to maintain compatibility with versions of BBC BASIC prior to the introduction of structures.\\ \\  Usually these limitations are not serious, for example to initialise the contents of an array one can simply use a loop:​\\ ​ //by Richard Russell, August 2013//\\ \\  As it states in the main [[http://​www.bbcbasic.co.uk/​bbcwin/​manual/​bbcwin2.html#​members|help documentation]] the 'whole array' operations (e.g. assignment, arithmetic and the SUM and MOD functions) cannot be used with arrays which are structure members. Similarly, you cannot pass a structure-member array as the parameter of an FN or PROC. These limitations arise because of the need to maintain compatibility with versions of BBC BASIC prior to the introduction of structures.\\ \\  Usually these limitations are not serious, for example to initialise the contents of an array one can simply use a loop:​\\ ​
 +<code bb4w>
         DIM struct{array(3,​2)}         DIM struct{array(3,​2)}
         FOR R% = 0 TO 3         FOR R% = 0 TO 3
Line 8: Line 9:
           NEXT           NEXT
         NEXT R%         NEXT R%
 +</​code>​
 However there may be occasions when it would be convenient to be able to use the whole-array operations. Fortunately there is a way, although it has a few restrictions. By calling the procedure **PROC_arrayalias** (listed below) it is possible to create a conventional array which is an //alias// of an array in a structure. If a whole-array operation is performed on this alias array, the array in the structure is also affected, and if the structure array is modified the alias array also changes.\\ \\  So for example an equivalent functionality to the code above may be achieved as follows:​\\ ​ However there may be occasions when it would be convenient to be able to use the whole-array operations. Fortunately there is a way, although it has a few restrictions. By calling the procedure **PROC_arrayalias** (listed below) it is possible to create a conventional array which is an //alias// of an array in a structure. If a whole-array operation is performed on this alias array, the array in the structure is also affected, and if the structure array is modified the alias array also changes.\\ \\  So for example an equivalent functionality to the code above may be achieved as follows:​\\ ​
 +<code bb4w>
         DIM struct{array(3,​2)}         DIM struct{array(3,​2)}
         PROC_arrayalias(struct{},​ alias(), nil%, nil%, nil%)         PROC_arrayalias(struct{},​ alias(), nil%, nil%, nil%)
         alias() = -1         alias() = -1
 +</​code>​
 Note the use of dummy variables **nil%** to 'pad out' the procedure call to the correct number of parameters. It is possible to create up to four - expandable to nine, see below - alias arrays in this way, each one corresponding to a different array within the structure (non-array members are ignored in this process). So for example:​\\ ​ Note the use of dummy variables **nil%** to 'pad out' the procedure call to the correct number of parameters. It is possible to create up to four - expandable to nine, see below - alias arrays in this way, each one corresponding to a different array within the structure (non-array members are ignored in this process). So for example:​\\ ​
 +<code bb4w>
         DIM test{a%(0), b%, c#(3,2), d$, e$(1)}         DIM test{a%(0), b%, c#(3,2), d$, e$(1)}
         PROC_arrayalias(test{},​ one%(), two#(), three$(), nil%)         PROC_arrayalias(test{},​ one%(), two#(), three$(), nil%)
 +</​code>​
 Here the three arrays **one%()**, **two#()** and **three$()** become aliases of the structure members **test.a%()**,​ **test.c#​()** and **test.e$()** respectively. It is important that the type suffix (%, #, $ etc.) of the alias array is the same as the structure member. If there is an array for which you have no need of an alias, pass a dummy variable for that parameter.\\ \\  As stated previously, any of the whole-array operations (except SWAP) may be performed on the alias arrays, even something as simple as determining the dimensions:​\\ ​ Here the three arrays **one%()**, **two#()** and **three$()** become aliases of the structure members **test.a%()**,​ **test.c#​()** and **test.e$()** respectively. It is important that the type suffix (%, #, $ etc.) of the alias array is the same as the structure member. If there is an array for which you have no need of an alias, pass a dummy variable for that parameter.\\ \\  As stated previously, any of the whole-array operations (except SWAP) may be performed on the alias arrays, even something as simple as determining the dimensions:​\\ ​
 +<code bb4w>
         DIM test{a%(0), b%, c#(3,2), d$, e$(1)}         DIM test{a%(0), b%, c#(3,2), d$, e$(1)}
         PROC_arrayalias(test{},​ nil%, two#(), nil%, nil%)         PROC_arrayalias(test{},​ nil%, two#(), nil%, nil%)
         maxrow% = DIM(two#(), 1)         maxrow% = DIM(two#(), 1)
         maxcol% = DIM(two#(), 2)         maxcol% = DIM(two#(), 2)
 +</​code>​
 Sadly there are a few limitations to this technique:​\\ ​ Sadly there are a few limitations to this technique:​\\ ​
  
Line 29: Line 37:
   * The memory layout of the structure changes, so (e.g.) it cannot be passed to an API function.   * The memory layout of the structure changes, so (e.g.) it cannot be passed to an API function.
 \\  As a warning that the layout of the structure is changed the **DIM(struct{})** function, which gives the structure'​s size in bytes, returns an increased value. \\ \\  Here is the **PROC_arrayalias** procedure. Up to five more parameters (which must have the formal variables **E%**, **F%**, **G%**, **H%** and **I%**) may be added if there are more arrays in the structure. No other code changes are required.\\ ​ \\  As a warning that the layout of the structure is changed the **DIM(struct{})** function, which gives the structure'​s size in bytes, returns an increased value. \\ \\  Here is the **PROC_arrayalias** procedure. Up to five more parameters (which must have the formal variables **E%**, **F%**, **G%**, **H%** and **I%**) may be added if there are more arrays in the structure. No other code changes are required.\\ ​
 +<code bb4w>
         DEF PROC_arrayalias(RETURN s{}, RETURN A%, RETURN B%, RETURN C%, RETURN D%)         DEF PROC_arrayalias(RETURN s{}, RETURN A%, RETURN B%, RETURN C%, RETURN D%)
         LOCAL J%,​K%,​L%,​M%,​N%,​O%,​P%,​Q%,​R%,​S%,​T%         LOCAL J%,​K%,​L%,​M%,​N%,​O%,​P%,​Q%,​R%,​S%,​T%
Line 94: Line 103:
         !!^s{} += O%         !!^s{} += O%
         ENDPROC         ENDPROC
 +</​code>​
whole-array_20operations_20in_20structures.txt ยท Last modified: 2018/04/17 19:29 by tbest3112