Revision history for KeyPgType


Revision [23985]

Last edited on 2020-07-01 03:29:10 by fxm [added sentence about how to pre-size a variable-length (dynamic) array data member in its declaration]
Additions:
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString|String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data. For sizing the structure of the array descriptor in the Type, a variable-length (dynamic) array data member must be always declared by using ##[[KeyPgAny|Any(s)]]## in place of the array bounds, in order to fix the amount of dimensions based on the number of Anys specified. A variable-length (dynamic) array data member can also be pre-sized in its declaration by using syntax with ##[[KeyPgRedim|Redim]]##.
Deletions:
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString|String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data. For sizing the structure of the array descriptor in the Type, a variable-length (dynamic) array data member must be always declared by using ##[[KeyPgAny|Any(s)]]## in place of the array bounds, in order to fix the amount of dimensions based on the number of Anys specified.


Revision [22748]

Edited on 2019-07-03 02:16:52 by fxm [completed text in "Variable-length data"]
Additions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying such arrays, or their erasing).
Deletions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying such arrays, or erasing).


Revision [22747]

Edited on 2019-07-03 02:01:54 by fxm [completed text in "Variable-length data"]
Additions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying such arrays, or erasing).
Deletions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying such arrays).


Revision [22722]

Edited on 2019-06-26 09:55:05 by fxm [added 'Extends Zstring' and 'Extends Wstring' links]
Additions:
- ##[[KeyPgExtendsZstring|Extends Zstring]]##
- ##[[KeyPgExtendsWstring|Extends Wstring]]##


Revision [22629]

Edited on 2019-03-11 20:40:05 by JeffMarshall [add alias option]
Additions:
**Type** //typename// [[[KeyPgAlias|Alias]] "alternatename"] [[[KeyPgExtends|Extends]] //base_typename//] [[[KeyPgField|Field]] = //alignment//]
##[[KeyPgAlias|Alias]] "alternatename"## specifies that if ##//typename//## must be encoded (mangled) in to a public symbol (as in an object module or library), then specifically use ##//alternate//## name instead of the usual encoding (mangling) of ##//typename//##.
- ##[[KeyPgAlias|Alias (Name)]]##
Deletions:
**Type** //typename// [[[KeyPgExtends|Extends]] //base_typename//] [[[KeyPgField|Field]] = //alignment//]


Revision [22558]

Edited on 2019-01-31 08:48:44 by fxm [Added syntax with Redim]
Additions:
[[KeyPgRedim|Redim]] //arrayname(array dimensions)// [[KeyPgAs|As]] //[[DataType|DataType]]//


Revision [22533]

Edited on 2018-12-21 07:25:47 by fxm [Var-len array fields in a Type are processed as pseudo-objects by the implicit member procedures]
Additions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying such arrays).
Deletions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying arrays).


Revision [22532]

Edited on 2018-12-21 04:00:24 by fxm [Var-len array fields in a Type are processed as pseudo-objects by the implicit member procedures]
Additions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support [re]sizing and copying arrays).
Deletions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support resizing and copying arrays).


Revision [22531]

Edited on 2018-12-21 03:56:58 by fxm [Var-len array fields in a Type are processed as pseudo-objects by the implicit member procedures]
Additions:
Variable-length array fields are considered as pseudo-objects when they are declared in a ##**Type**##, just like variable-length strings (the implicit copy constructor and the implicit let operator themselves support resizing and copying arrays).


Revision [21367]

Edited on 2016-04-15 08:11:36 by fxm [Added link to 'Coercion and Conversion']

No Differences

Revision [21366]

Edited on 2016-04-15 08:08:04 by fxm [Added link to 'Coercion and Conversion']
Additions:
- [[ProPgDataConversion|Coercion and Conversion]]


Revision [21275]

Edited on 2016-03-22 12:53:05 by fxm [Type/Union structure simplified in example 3]
Additions:
Union UbyteOctal
number As Ubyte
Type
d0 : 3 As Ubyte
d1 : 3 As Ubyte
d2 : 2 As Ubyte
End Type
End Union
Deletions:
Type UbyteOctal
Union
number As Ubyte
Type
d0 : 3 As Ubyte
d1 : 3 As Ubyte
d2 : 2 As Ubyte
End Type
End Union
End type


Revision [21273]

Edited on 2016-03-19 04:41:14 by fxm [Added an example of bitfields]
Additions:
This is an example of conversion from an Ubyte to a digit string in base 8 (octal string), by using bitfields in a local UDT (conversion equivalent to 'Oct(x, 3)'):
{{fbdoc item="filename" value="examples/manual/udt/type3.bas"}}%%(freebasic)
Function UbyteToOctalString (Byval b As Ubyte) As String

Type UbyteOctal
Union
number As Ubyte
Type
d0 : 3 As Ubyte
d1 : 3 As Ubyte
d2 : 2 As Ubyte
End Type
End Union
End type

Dim uo As UbyteOctal
uo.number = b
Return uo.d2 & uo.d1 & uo.d0

End Function
For I As Integer = 0 To 255
Print Using "###: "; I;
'' Print Oct(I, 3),
Print UbyteToOctalString(I), '' this line is thus equivalent to the previous one
Next I
Print
Sleep


Revision [21267]

Edited on 2016-03-18 07:04:03 by fxm [Finalized note on bitfields]
Additions:
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types (up to 32-bit for 32-bit development or 64-bit for 64-bit development) are valid. The sizes of the declared data-types, large enough to contain the bit patterns, affect how the bitfields are placed in memory.
A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).
Deletions:
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types (up to 32-bit for 32-bit development or 64-bit for 64-bit development) are valid. The sizes of the declared data-types, large enough to contain the bit patterns, affect how the bitfields are placed in memory. A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).


Revision [21266]

Edited on 2016-03-18 03:26:12 by fxm [Finalized note on bitfields]
Additions:
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types (up to 32-bit for 32-bit development or 64-bit for 64-bit development) are valid. The sizes of the declared data-types, large enough to contain the bit patterns, affect how the bitfields are placed in memory. A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).
Deletions:
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types up to 32-bit for 32-bit development or 64-bit for 64-bit development are valid (the declared data-type must be long enough to contain the bit pattern). A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).


Revision [21265]

Edited on 2016-03-17 03:33:47 by fxm [Complemented note on bitfields]
Additions:
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types up to 32-bit for 32-bit development or 64-bit for 64-bit development are valid (the declared data-type must be long enough to contain the bit pattern). A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).
Deletions:
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types up to 32-bit for 32-bit development or 64-bit for 64-bit development are valid. A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).


Revision [21259]

Edited on 2016-03-16 07:24:44 by fxm [Added note on bitfields]
Additions:
//Note on bitfields ( ##//fieldname// : //bits//## )//
Bitfields can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types up to 32-bit for 32-bit development or 64-bit for 64-bit development are valid. A bitfield does not have any address (one cannot get a pointer to it and its offset inside the structure).
Deletions:
//Note on bitfields (syntax 'fieldname : bits')//
They can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types up to 32-bit for 32-bit development or 64-bit for 64-bit development are valid.


Revision [21258]

Edited on 2016-03-16 05:20:28 by fxm [Added note on bitfields]
Additions:
//Note on bitfields (syntax 'fieldname : bits')//
They can only be declared inside a type or a union, and allow to specify some very small objects of a given number of bits in length. Each field is accessed and manipulated as if it were an ordinary member of the structure. Only integer data-types up to 32-bit for 32-bit development or 64-bit for 64-bit development are valid.


Revision [20561]

Edited on 2016-02-10 16:09:46 by DkLwikki [Update link format]
Additions:
//fieldname1// [[KeyPgAs|As]] //[[DataType|DataType]]//
//fieldname2// [[KeyPgAs|As]] //[[DataType|DataType]]//
[[KeyPgAs|As]] //[[DataType|DataType]]// //fieldname3//, //fieldname4//
**Type** //typename// [[[KeyPgExtends|Extends]] //base_typename//] [[[KeyPgField|Field]] = //alignment//]
[[[KeyPgVisPrivate|Private:]]|[[KeyPgVisPublic|Public:]]|[[KeyPgVisProtected|Protected:]]]
[[KeyPgDeclare|Declare]] [[KeyPgMemberSub|Sub]]|[[KeyPgMemberFunction|Function]]|[[KeyPgConstructor|Constructor]]|[[KeyPgDestructor|Destructor]]|[[KeyPgProperty|Property]]|[[KeyPgOperator|Operator]] ...
[[KeyPgStatic|Static]] //variablename// [[KeyPgAs|As]] //[[DataType|DataType]]//
//fieldname// [[KeyPgAs|As]] //[[DataType|DataType]]// [= //initializer//]
//fieldname//(//array dimensions//) [[KeyPgAs|As]] //[[DataType|DataType]]// [= //initializer//]
//fieldname//([[KeyPgAny|Any]] [, [[KeyPgAny|Any]]...]) [[KeyPgAs|As]] [[DataType|DataType]]
//fieldname// : //bits// [[KeyPgAs|As]] //[[DataType|DataType]]// [= //initializer//]
[[KeyPgAs|As]] [[DataType|DataType]] //fieldname// [= //initializer//], ...
[[KeyPgAs|As]] [[DataType|DataType]] //fieldname//(//array dimensions//) [= //initializer//], ...
[[KeyPgAs|As]] [[DataType|DataType]] //fieldname//([[KeyPgAny|Any]] [, [[KeyPgAny|Any]]...])
[[KeyPgAs|As]] [[DataType|DataType]] //fieldname// : //bits// [= //initializer//], ...
[[KeyPgUnion|Union]]
//fieldname// [[KeyPgAs|As]] //[[DataType|DataType]]//
//fieldname// [[KeyPgAs|As]] //[[DataType|DataType]]//
[[KeyPgUnion|End Union]]
- Inheritance through the use of the [[KeyPgExtends|Extends]] keyword
- Member procedures such as [[KeyPgMemberSub|subs]] or [[KeyPgMemberFunction|functions]], including ##[[KeyPgAbstract|Abstract]]## or ##[[KeyPgVirtual|Virtual]]## ones
- Member procedures with special semantic meaning such as [[KeyPgConstructor|constructors]] or a [[KeyPgDestructor|destructor]]
- ##[[KeyPgStatic|Static]]## member variables
- Member visibility specifiers: ##[[KeyPgVisPublic|Public:]]##, ##[[KeyPgVisPrivate|Private:]]##, ##[[KeyPgVisProtected|Protected:]]##
Types lay out their fields consecutively in memory, following the native alignment and padding rules (described on the ##[[KeyPgField|Field]]## page). Special care must be taken when using Types for file I/O or interacting with other programs or programming languages, in case the alignment and padding rules are different. The optional ##[[KeyPgField|Field]] = //number//## specifier can be used to change the behavior on the ""FreeBASIC"" side.
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString|String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data. For sizing the structure of the array descriptor in the Type, a variable-length (dynamic) array data member must be always declared by using ##[[KeyPgAny|Any(s)]]## in place of the array bounds, in order to fix the amount of dimensions based on the number of Anys specified.
Currently, fixed-length string fields of ##[[KeyPgString|String]] * //N//## type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up ##//N//+1## bytes, instead of just ##N## bytes. A possible work-around is to declare the field ##As [[KeyPgString|String]] * (//N//-1)##, though this will not work in future releases if the null terminator is removed. Another alternative is to use a ##[[KeyPgByte|Byte]]## or ##[[KeyPgUbyte|UByte]]## array with the proper size.
' less to avoid misalignments '/
res[i - Lbound(ub)] = ub(i)
- Object-related features such as functions declared inside ##**Type**## blocks are supported only with the //[[CompilerOptlang|-lang fb]]// dialect since version 0.17b
- In the //[[CompilerOptlang|-lang fb]]// and //[[CompilerOptlang|-lang fblite]]// dialects, the default ##**Field**## alignment parameter depends on the target platform.
- With the //[[CompilerOptlang|-lang qb]]// dialect the fields are aligned to byte boundaries by default, unless otherwise specified.
- ##[[KeyPgTypeAlias|Type (Alias)]]##
- ##[[KeyPgTypeTemp|Type (Temporary)]]##
- ##[[KeyPgUnion|Union]]##
- ##[[KeyPgEnum|Enum]]##
- ##[[KeyPgTypeof|Typeof]]##
- ##[[KeyPgOffsetof|OffsetOf]]##
- ##[[KeyPgField|Field]]##
- ##[[KeyPgExtends|Extends]]##
- ##[[KeyPgWith|With]]##
Deletions:
//fieldname1// [[KeyPgAs As]] //[[DataType DataType]]//
//fieldname2// [[KeyPgAs As]] //[[DataType DataType]]//
[[KeyPgAs As]] //[[DataType DataType]]// //fieldname3//, //fieldname4//
**Type** //typename// [[[KeyPgExtends Extends]] //base_typename//] [[[KeyPgField Field]] = //alignment//]
[[[KeyPgVisPrivate Private:]]|[[KeyPgVisPublic Public:]]|[[KeyPgVisProtected Protected:]]]
[[KeyPgDeclare Declare]] [[KeyPgMemberSub Sub]]|[[KeyPgMemberFunction Function]]|[[KeyPgConstructor Constructor]]|[[KeyPgDestructor Destructor]]|[[KeyPgProperty Property]]|[[KeyPgOperator Operator]] ...
[[KeyPgStatic Static]] //variablename// [[KeyPgAs As]] //[[DataType DataType]]//
//fieldname// [[KeyPgAs As]] //[[DataType DataType]]// [= //initializer//]
//fieldname//(//array dimensions//) [[KeyPgAs As]] //[[DataType DataType]]// [= //initializer//]
//fieldname//([[KeyPgAny Any]] [, [[KeyPgAny Any]]...]) [[KeyPgAs As]] [[DataType DataType]]
//fieldname// : //bits// [[KeyPgAs As]] //[[DataType DataType]]// [= //initializer//]
[[KeyPgAs As]] [[DataType DataType]] //fieldname// [= //initializer//], ...
[[KeyPgAs As]] [[DataType DataType]] //fieldname//(//array dimensions//) [= //initializer//], ...
[[KeyPgAs As]] [[DataType DataType]] //fieldname//([[KeyPgAny Any]] [, [[KeyPgAny Any]]...])
[[KeyPgAs As]] [[DataType DataType]] //fieldname// : //bits// [= //initializer//], ...
[[KeyPgUnion Union]]
//fieldname// [[KeyPgAs As]] //[[DataType DataType]]//
//fieldname// [[KeyPgAs As]] //[[DataType DataType]]//
[[KeyPgUnion End Union]]
- Inheritance through the use of the [[KeyPgExtends Extends]] keyword
- Member procedures such as [[KeyPgMemberSub subs]] or [[KeyPgMemberFunction functions]], including ##[[KeyPgAbstract Abstract]]## or ##[[KeyPgVirtual Virtual]]## ones
- Member procedures with special semantic meaning such as [[KeyPgConstructor constructors]] or a [[KeyPgDestructor destructor]]
- ##[[KeyPgStatic Static]]## member variables
- Member visibility specifiers: ##[[KeyPgVisPublic Public:]]##, ##[[KeyPgVisPrivate Private:]]##, ##[[KeyPgVisProtected Protected:]]##
Types lay out their fields consecutively in memory, following the native alignment and padding rules (described on the ##[[KeyPgField Field]]## page). Special care must be taken when using Types for file I/O or interacting with other programs or programming languages, in case the alignment and padding rules are different. The optional ##[[KeyPgField Field]] = //number//## specifier can be used to change the behavior on the ""FreeBASIC"" side.
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data. For sizing the structure of the array descriptor in the Type, a variable-length (dynamic) array data member must be always declared by using ##[[KeyPgAny Any(s)]]## in place of the array bounds, in order to fix the amount of dimensions based on the number of Anys specified.
Currently, fixed-length string fields of ##[[KeyPgString String]] * //N//## type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up ##//N//+1## bytes, instead of just ##N## bytes. A possible work-around is to declare the field ##As [[KeyPgString String]] * (//N//-1)##, though this will not work in future releases if the null terminator is removed. Another alternative is to use a ##[[KeyPgByte Byte]]## or ##[[KeyPgUbyte UByte]]## array with the proper size.
' less to avoid misalignments '/
res[i - Lbound(ub)] = ub(i)
- Object-related features such as functions declared inside ##**Type**## blocks are supported only with the //[[CompilerOptlang -lang fb]]// dialect since version 0.17b
- In the //[[CompilerOptlang -lang fb]]// and //[[CompilerOptlang -lang fblite]]// dialects, the default ##**Field**## alignment parameter depends on the target platform.
- With the //[[CompilerOptlang -lang qb]]// dialect the fields are aligned to byte boundaries by default, unless otherwise specified.
- ##[[KeyPgTypeAlias Type (Alias)]]##
- ##[[KeyPgTypeTemp Type (Temporary)]]##
- ##[[KeyPgUnion Union]]##
- ##[[KeyPgEnum Enum]]##
- ##[[KeyPgTypeof Typeof]]##
- ##[[KeyPgOffsetof OffsetOf]]##
- ##[[KeyPgField Field]]##
- ##[[KeyPgExtends Extends]]##
- ##[[KeyPgWith With]]##


Revision [17367]

Edited on 2014-11-05 03:35:47 by FxMwikki [Local type cannot have procedures members or static data members.]
Additions:
Types may also contain nested types or unions, allowing data members to be grouped as desired. Nested types/unions are not allowed to contain member procedures or static member variables (same restriction for local types/unions).
Deletions:
Types may also contain nested types or unions, allowing data members to be grouped as desired. Nested types/unions are not allowed to contain member procedures or static member variables.


Revision [17253]

Edited on 2014-09-09 14:50:11 by FxMwikki [A dynamic array data member must be declared by using Any in order to fix the amount of dimensions]
Additions:
//fieldname//([[KeyPgAny Any]] [, [[KeyPgAny Any]]...]) [[KeyPgAs As]] [[DataType DataType]]
[[KeyPgAs As]] [[DataType DataType]] //fieldname//([[KeyPgAny Any]] [, [[KeyPgAny Any]]...])


Revision [17252]

Edited on 2014-09-08 17:15:58 by FxMwikki [A dynamic array data member must be declared by using Any on order to fix the amount of dimensions]
Additions:
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data. For sizing the structure of the array descriptor in the Type, a variable-length (dynamic) array data member must be always declared by using ##[[KeyPgAny Any(s)]]## in place of the array bounds, in order to fix the amount of dimensions based on the number of Anys specified.
Deletions:
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data.


Revision [17251]

Edited on 2014-09-08 16:29:05 by FxMwikki [Formatting]
Additions:
In ""FreeBASIC"", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data.
Deletions:
In ""FreeBASIC", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data.


Revision [17043]

Edited on 2014-04-26 12:31:16 by DkLwikki [Mention static member vars and abstract/virtual]
Additions:
- Member procedures such as [[KeyPgMemberSub subs]] or [[KeyPgMemberFunction functions]], including ##[[KeyPgAbstract Abstract]]## or ##[[KeyPgVirtual Virtual]]## ones
- ##[[KeyPgStatic Static]]## member variables
Deletions:
- Member procedures such as [[KeyPgMemberSub subs]] or [[KeyPgMemberFunction functions]]


Revision [17042]

Edited on 2014-04-26 12:29:10 by DkLwikki [Rework for dynamic array fields]
Additions:
##**Type**## is used to declare custom data types containing one or more data fields, including integer types, floating point types, fixed-size or variable-length (dynamic) arrays, fixed-size or variable-length strings, bitfields, or other user-defined types.
Types may also contain nested types or unions, allowing data members to be grouped as desired. Nested types/unions are not allowed to contain member procedures or static member variables.
//Variable-length data//
In ""FreeBASIC", Type data structures must ultimately be fixed-size, such that the compiler knows how much memory to allocate for objects of that Type. Nevertheless, Types may contain variable-length (dynamic) string or array data members. However, the string's/array's data will not be embedded in the Type directly. Instead, the Type will only contain a ##[[KeyPgString String]]##/array descriptor structure, which ""FreeBASIC"" uses behind the scenes to manage the variable-length string/array data.
Because of that, saving such a Type into a file will write out the descriptor, not the actual string/array data. In order to embed strings/arrays into Types directly, fixed-length strings/arrays must be used.
Similarly, when maintaining dynamic data manually through the use of pointers within a Type, it does usually not make sense to save the Type to a file, because the address stored in the pointer field will be written to file, not the actual memory it points to. Addresses are meaningful to a specific process only though, and cannot be shared that way.
//Special note on fixed-length strings//
Deletions:
##**Type**## is used to declare custom data types containing one or more data fields, including integer types, floating point types, fixed-size arrays, strings, bitfields, and other unnamed user-defined types or unions.
//Dynamic data//
Types can contain dynamic strings, but note that the Type will contain the ##[[KeyPgString String]]## descriptor structure, not the string data itself, which afterall is dynamically allocated and can be of variable length, and thus can not be inserted into the Type. Because of that, saving such a Type into a file will write out the string descriptor, not the actual string data. In order to embed strings into Types directly, fixed-length strings must be used. Similarly, when maintaining dynamic data manually through the use of pointers within a Type, it does usually not make sense to save the Type to a file, because the address stored in the pointer field will be written to file, not the actual memory it points to. Addresses are meaningful to a specific process only though, and cannot be shared that way.
//Special note on fixed length strings//
//Remark//
Nested unnamed type or union cannot have function members or static data members.


Revision [16945]

Edited on 2013-09-13 05:40:35 by FxMwikki [Nested unnamed type or union also cannot have static data members]
Additions:
Nested unnamed type or union cannot have function members or static data members.
Deletions:
Nested unnamed type or union cannot have function members.


Revision [16881]

Edited on 2013-07-15 13:49:10 by DkLwikki [Add static member vars]
Deletions:
[[KeyPgStatic Static]] [[KeyPgAs As]] //[[DataType DataType]]// //variable1//, //variable2//


Revision [16880]

Edited on 2013-07-15 13:48:07 by DkLwikki [Add static member vars]
Additions:
[[KeyPgStatic Static]] //variablename// [[KeyPgAs As]] //[[DataType DataType]]//
[[KeyPgStatic Static]] [[KeyPgAs As]] //[[DataType DataType]]// //variable1//, //variable2//


Revision [16811]

Edited on 2013-05-19 14:05:16 by FxMwikki [Nested unnamed type or union cannot have function members]
Additions:
##**Type**## is used to declare custom data types containing one or more data fields, including integer types, floating point types, fixed-size arrays, strings, bitfields, and other unnamed user-defined types or unions.
//Remark//
Nested unnamed type or union cannot have function members.
Deletions:
##**Type**## is used to declare custom data types containing one or more data fields, including integer types, floating point types, fixed-size arrays, strings, bitfields, and other user-defined types or unions.


Revision [16663]

Edited on 2013-03-22 14:07:24 by FxMwikki [Corrected typo in 'ub2str()']
Additions:
res[i - Lbound(ub)] = ub(i)
Deletions:
res[i] = ub(i)


Revision [16662]

Edited on 2013-03-22 13:00:31 by FxMwikki [In 'ub2str()', the local variable 'length' is now useless]
Deletions:
dim as integer length = ubound(ub) + 1


Revision [16661]

Edited on 2013-03-22 11:51:04 by CountingPine [More versatile ub2str() (allow nonzero lower bounds)]
Additions:
Currently, fixed-length string fields of ##[[KeyPgString String]] * //N//## type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up ##//N//+1## bytes, instead of just ##N## bytes. A possible work-around is to declare the field ##As [[KeyPgString String]] * (//N//-1)##, though this will not work in future releases if the null terminator is removed. Another alternative is to use a ##[[KeyPgByte Byte]]## or ##[[KeyPgUbyte UByte]]## array with the proper size.
dim as string res = space(ubound(ub) - lbound(ub) + 1)
for i as integer = lbound(ub) to ubound(ub)
res[i] = ub(i)
next
Deletions:
Currently, fixed-length string fields of ##[[KeyPgString String]] * //N//## type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up ##//N//+1## bytes, instead of just ##N## bytes. A possible work-around is to declare the field ##As [[KeyPgString String]] * (//N//-1)##, though this will not work in future releases if the null terminator is removed. Another alternative is to use a ##[[KeyPgByte Byte]]## array with the proper size.
dim as string res = space(length)
for i as integer = 0 to length-1
res[i] = ub(i): next


Revision [16485]

Edited on 2012-12-01 13:01:40 by CountingPine [Formatting]
Additions:
Types lay out their fields consecutively in memory, following the native alignment and padding rules (described on the ##[[KeyPgField Field]]## page). Special care must be taken when using Types for file I/O or interacting with other programs or programming languages, in case the alignment and padding rules are different. The optional ##[[KeyPgField Field]] = //number//## specifier can be used to change the behavior on the ""FreeBASIC"" side.
Types can contain dynamic strings, but note that the Type will contain the ##[[KeyPgString String]]## descriptor structure, not the string data itself, which afterall is dynamically allocated and can be of variable length, and thus can not be inserted into the Type. Because of that, saving such a Type into a file will write out the string descriptor, not the actual string data. In order to embed strings into Types directly, fixed-length strings must be used. Similarly, when maintaining dynamic data manually through the use of pointers within a Type, it does usually not make sense to save the Type to a file, because the address stored in the pointer field will be written to file, not the actual memory it points to. Addresses are meaningful to a specific process only though, and cannot be shared that way.
//Special note on fixed length strings//
Currently, fixed-length string fields of ##[[KeyPgString String]] * //N//## type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up ##//N//+1## bytes, instead of just ##N## bytes. A possible work-around is to declare the field ##As [[KeyPgString String]] * (//N//-1)##, though this will not work in future releases if the null terminator is removed. Another alternative is to use a ##[[KeyPgByte Byte]]## array with the proper size.
Deletions:
Types lay out their fields consecutively in memory, following the native alignment and padding rules (described on the [[KeyPgField Field page]]). Special care must be taken when using Types for file I/O or interacting with other programs or programming languages, in case the alignment and padding rules are different. The optional ##[[KeyPgField Field = number]]## specifier can be used to change the behavior on the ""FreeBASIC"" side.
Types can contain dynamic strings, but note that the Type will contain the [[KeyPgString string descriptor]] structure, not the string data itself, which afterall is dynamically allocated and can be of variable length, and thus can not be inserted into the Type. Because of that, saving such a Type into a file will write out the string descriptor, not the actual string data. In order to embed strings into Types directly, fixed-length strings must be used. Similarly, when maintaining dynamic data manually through the use of pointers within a Type, it does usually not make sense to save the Type to a file, because the address stored in the pointer field will be written to file, not the actual memory it points to. Addresses are meaningful to a specific process only though, and cannot be shared that way.
//Special note on string * N//
Currently, fixed-length string fields of [[KeyPgString String * N]] type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up N+1 bytes, instead of just N bytes. A possible work-around is to declare the field As String * N-1, or to use a byte array with the proper size.


Revision [16444]

Edited on 2012-11-16 10:21:57 by DkLwikki [simplify syntax, rewrite description]
Additions:
//fieldname1// [[KeyPgAs As]] //[[DataType DataType]]//
//fieldname2// [[KeyPgAs As]] //[[DataType DataType]]//
[[KeyPgAs As]] //[[DataType DataType]]// //fieldname3//, //fieldname4//
**Type** //typename// [[[KeyPgExtends Extends]] //base_typename//] [[[KeyPgField Field]] = //alignment//]
[[[KeyPgVisPrivate Private:]]|[[KeyPgVisPublic Public:]]|[[KeyPgVisProtected Protected:]]]

[[KeyPgDeclare Declare]] [[KeyPgMemberSub Sub]]|[[KeyPgMemberFunction Function]]|[[KeyPgConstructor Constructor]]|[[KeyPgDestructor Destructor]]|[[KeyPgProperty Property]]|[[KeyPgOperator Operator]] ...

//fieldname// [[KeyPgAs As]] //[[DataType DataType]]// [= //initializer//]
//fieldname//(//array dimensions//) [[KeyPgAs As]] //[[DataType DataType]]// [= //initializer//]
//fieldname// : //bits// [[KeyPgAs As]] //[[DataType DataType]]// [= //initializer//]

[[KeyPgAs As]] [[DataType DataType]] //fieldname// [= //initializer//], ...
[[KeyPgAs As]] [[DataType DataType]] //fieldname//(//array dimensions//) [= //initializer//], ...
[[KeyPgAs As]] [[DataType DataType]] //fieldname// : //bits// [= //initializer//], ...

[[KeyPgUnion Union]]
//fieldname// [[KeyPgAs As]] //[[DataType DataType]]//
**Type**
//fieldname// [[KeyPgAs As]] //[[DataType DataType]]//
...
**End Type**
...
[[KeyPgUnion End Union]]

##**Type**## is used to declare custom data types containing one or more data fields, including integer types, floating point types, fixed-size arrays, strings, bitfields, and other user-defined types or unions.
Types support various functionality related to object-oriented programming:
- Inheritance through the use of the [[KeyPgExtends Extends]] keyword
- Member procedures such as [[KeyPgMemberSub subs]] or [[KeyPgMemberFunction functions]]
- Member procedures with special semantic meaning such as [[KeyPgConstructor constructors]] or a [[KeyPgDestructor destructor]]
- Member visibility specifiers: ##[[KeyPgVisPublic Public:]]##, ##[[KeyPgVisPrivate Private:]]##, ##[[KeyPgVisProtected Protected:]]##
//Memory layout//
Types lay out their fields consecutively in memory, following the native alignment and padding rules (described on the [[KeyPgField Field page]]). Special care must be taken when using Types for file I/O or interacting with other programs or programming languages, in case the alignment and padding rules are different. The optional ##[[KeyPgField Field = number]]## specifier can be used to change the behavior on the ""FreeBASIC"" side.
//Dynamic data//
Types can contain dynamic strings, but note that the Type will contain the [[KeyPgString string descriptor]] structure, not the string data itself, which afterall is dynamically allocated and can be of variable length, and thus can not be inserted into the Type. Because of that, saving such a Type into a file will write out the string descriptor, not the actual string data. In order to embed strings into Types directly, fixed-length strings must be used. Similarly, when maintaining dynamic data manually through the use of pointers within a Type, it does usually not make sense to save the Type to a file, because the address stored in the pointer field will be written to file, not the actual memory it points to. Addresses are meaningful to a specific process only though, and cannot be shared that way.
//Special note on string * N//
Currently, fixed-length string fields of [[KeyPgString String * N]] type have an extra null terminator at their end, for compatibility with C strings, making them incompatible with QB strings inside Types, because they actually use up N+1 bytes, instead of just N bytes. A possible work-around is to declare the field As String * N-1, or to use a byte array with the proper size.
Deletions:
//fieldname1// [[KeyPgAs as]] //[[DataType DataType]]//
//fieldname2// [[KeyPgAs as]] //[[DataType DataType]]//
**Type** //typename// [ [[KeyPgExtends Extends]] //base_typename// ] [ [[KeyPgField Field]] = //alignment// ]
[ [[KeyPgVisPrivate Private]]: ]
[ [[KeyPgVisPublic Public]]: ]
[ [[KeyPgVisProtected Protected]]: ]
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgConstructor constructor]] [ ( [ //parameters// ] ) ]
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgDestructor destructor]] [ () ]
[[KeyPgDeclare declare]] [ [[KeyPgStaticMember Static]] | [[KeyPgConstMember Const]] ] [[KeyPgMemberSub sub]] //fieldname// [//calling convention specifier//] [ [[KeyPgAlias alias]] //external_name// ] [ ( [ //parameters// ] ) ] [ [[KeyPgStatic Static]] ]
[[KeyPgDeclare declare]] [ [[KeyPgStaticMember Static]] | [[KeyPgConstMember Const]] ] [[KeyPgMemberFunction function]] //fieldname// [//calling convention specifier//] [ [[KeyPgAlias alias]] //external_name// ] [ ( [ //parameters// ] ) ] [ [[KeyPgAs as]] [[DataType datatype]] ] [ [[KeyPgStatic Static]] ]
//fieldname// [ ( //array subscripts// ) | : //bits// ] [[KeyPgAs as]] //[[DataType DataType]]// [ = //initializer// ]
[[KeyPgAs as]] [[DataType DataType]] //fieldname// [ ( //array subscripts// ) | : //bits// ] [ = //initializer// ], ...
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgOperator operator]] //operatorname//[ ( [ //parameters// ] ) ]
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgProperty property]] //fieldname//[ ( [ //parameters// ] ) ] [ [[KeyPgAs as]] [[DataType datatype]] ]
{{fbdoc item="param"}}
##//alignment//##
Specifies the padding byte limit for data fields alignment.
##//fieldname//##
Name of the data field or member procedure.
##//external_name//##
Name of field as seen when externally linked.
##//parameters//##
The parameters to be passed to a member procedure.
##//array subscripts//##
Subscripts to declare a fixed-length array.
##//bits//##
Number of bits a data field occupies (only valid for integer numeric data-types up to 32-bit types).
##//initializer//##
Default initializer for the data field.
##//operatorname//##
The name of the operator to be overloaded.
##//calling convention specifier//##
Can be ##[[KeyPgCdecl Cdecl]]##, ##[[KeyPgStdcall Stdcall]]## or ##[[KeyPgPascal Pascal]]##.
##**Type**## is used to declare custom data types containing one or more bit, scalar, array or other ##**Type**## fields.
Types support member functions including ##[[KeyPgConstructor Constructor]]##, ##[[KeyPgDestructor Destructor]]##, ##[[KeyPgMemberFunction Function]]##, ##[[KeyPgOperator Operator]]##, ##[[KeyPgProperty Property]]## and ##[[KeyPgMemberSub Sub]]##.
Fields default to ##[[KeyPgVisPublic Public:]]## member access unless, ##[[KeyPgVisPrivate Private:]]## or ##[[KeyPgVisProtected Protected:]]## is specified.
An anonymous ##[[KeyPgUnion Union]]## can be nested in a ##**Type**## declaration.
##[[KeyPgExtends Extends]]## can optionally be used to create a user-defined type that is derived from another type and inherits its members.
The optional ##[[KeyPgField Field]]=//number//## when given will change the default padding byte limit for data fields alignment. ##[[KeyPgField Field]]=1## will disable any alignment, making the ##**Type**## contiguous in memory.
##**Type**## can be used to return a temporary type variable. See ##[[KeyPgTypeTemp Type()]]##.
##**Type**## can be used to declare a type definition ( i.e. an alias or alternative name ) for an already declared or yet to be declared type. See ##[[KeyPgTypeAlias Type (Alias)]]##
Data fields may have an optional default ##//initializer//## value. This default value initializes the data field immediately before any constructor is called.
##[[KeyPgStaticMember Static]]## immediately preceding ##[[KeyPgMemberSub Sub]]## or ##[[KeyPgMemberFunction Function]]## indicates that no hidden ##[[KeyPgThis This]]## parameter is to be passed to the member procedure.
##[[KeyPgConstMember Const]]## immediately preceding ##[[KeyPgMemberSub Sub]]##, ##[[KeyPgMemberFunction Function]]##, ##[[KeyPgConstructor Constructor]]##, ##[[KeyPgDestructor Destructor]]##, ##[[KeyPgProperty Property]]## or ##[[KeyPgOperator Operator]]## indicates that the hidden ##[[KeyPgThis This]]## parameter is to be considered read-only.
**Warning** Special care must be taken when using a user defined type for file I/O. It is recommended to use ##Field = 1## for such cases, and it may be required to read files created by other applications.
UDTs that contain pointers to data should not be written to file as-is: when the data is read later, the pointers will almost certainly be invalid, and the data they pointed to will no longer be available. Instead, custom input/output routines should be used, to save the allocated data in a different format in the file. This includes UDTs containing variable-length strings.
Additionally, reading fixed length strings in UDT's from files is problematic: at present, fixed-length strings contain an extra NULL character on the end. To preserve alignment the field would need to be declared with one char less than the actual size and accessing the field by its name makes the last character unavailable. It also means there may be potential problems passing the string to functions that expect the NULL character to be there.
A better solution is to use ubyte arrays, this requires a couple of auxiliary functions converting to/from string. See the example.


Revision [16194]

Edited on 2012-05-28 16:26:57 by FxMwikki ['Field =' defines the padding byte limit for data fields alignment]
Additions:
- The default ##**Field**## alignment parameter is 8 bytes for Windows targets (this difference with regard to 4 bytes applies only to Longint and Double members).
Deletions:
- The default ##**Field**## alignment parameter is 8 bytes for Windows targets.


Revision [16192]

Edited on 2012-05-28 04:33:56 by FxMwikki ['Field =' defines the padding byte limit for data fields alignment]
Additions:
- The default ##**Field**## alignment parameter is 4 bytes for DOS and Linux targets.
- The default ##**Field**## alignment parameter is 8 bytes for Windows targets.
- In the //[[CompilerOptlang -lang fb]]// and //[[CompilerOptlang -lang fblite]]// dialects, the default ##**Field**## alignment parameter depends on the target platform.
Deletions:
- The default field alignment is 4 bytes for DOS and Linux targets.
- The default field alignment is 8 bytes for Windows targets.
- In the //[[CompilerOptlang -lang fb]]// and //[[CompilerOptlang -lang fblite]]// dialects, the default field alignment depends on the target platform.


Revision [16190]

Edited on 2012-05-28 03:48:06 by FxMwikki ['Field =' defines the padding byte limit for data fields alignment]
Additions:
Specifies the padding byte limit for data fields alignment.
The optional ##[[KeyPgField Field]]=//number//## when given will change the default padding byte limit for data fields alignment. ##[[KeyPgField Field]]=1## will disable any alignment, making the ##**Type**## contiguous in memory.
Deletions:
Specifies the byte alignment for data fields.
The optional ##[[KeyPgField Field]]=//number//## when given will change the default field alignment. ##[[KeyPgField Field]]=1## will disable any alignment, making the ##**Type**## contiguous in memory.


Revision [16119]

Edited on 2012-02-09 02:52:24 by FxMwikki [Fix: Const is allowed on more than just sub/function methods]
Additions:
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgConstructor constructor]] [ ( [ //parameters// ] ) ]
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgDestructor destructor]] [ () ]
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgOperator operator]] //operatorname//[ ( [ //parameters// ] ) ]
[[KeyPgDeclare declare]] [ [[KeyPgConstMember Const]] ] [[KeyPgProperty property]] //fieldname//[ ( [ //parameters// ] ) ] [ [[KeyPgAs as]] [[DataType datatype]] ]
##[[KeyPgConstMember Const]]## immediately preceding ##[[KeyPgMemberSub Sub]]##, ##[[KeyPgMemberFunction Function]]##, ##[[KeyPgConstructor Constructor]]##, ##[[KeyPgDestructor Destructor]]##, ##[[KeyPgProperty Property]]## or ##[[KeyPgOperator Operator]]## indicates that the hidden ##[[KeyPgThis This]]## parameter is to be considered read-only.
Deletions:
[[KeyPgDeclare declare]] [[KeyPgConstructor constructor]] [ ( [ //parameters// ] ) ]
[[KeyPgDeclare declare]] [[KeyPgDestructor destructor]] [ () ]
[[KeyPgDeclare declare]] [[KeyPgOperator operator]] //operatorname//[ ( [ //parameters// ] ) ]
[[KeyPgDeclare declare]] [[KeyPgProperty property]] //fieldname//[ ( [ //parameters// ] ) ] [ [[KeyPgAs as]] [[DataType datatype]] ]
##[[KeyPgConstMember Const]]## immediately preceding ##[[KeyPgMemberSub Sub]]## or ##[[KeyPgMemberFunction Function]]## indicates that the hidden ##[[KeyPgThis This]]## parameter is to be considered read-only.


Revision [15893]

Edited on 2012-02-01 06:07:22 by FxMwikki [Bits fields only valid for integer numeric data-types up to 32-bit types]
Additions:
Number of bits a data field occupies (only valid for integer numeric data-types up to 32-bit types).
Deletions:
Number of bits a data field occupies.


Revision [15816]

Edited on 2012-01-24 09:10:56 by DkLwikki [Mention EXTENDS in syntax & description]
Additions:
**Type** //typename// [ [[KeyPgExtends Extends]] //base_typename// ] [ [[KeyPgField Field]] = //alignment// ]
##[[KeyPgExtends Extends]]## can optionally be used to create a user-defined type that is derived from another type and inherits its members.
Deletions:
**Type** //typename// [ [[KeyPgField Field]] = //alignment// ]


Revision [15646]

Edited on 2012-01-13 12:03:04 by CountingPine [Link to KeyPgExtends]
Additions:
- ##[[KeyPgExtends Extends]]##


Revision [15025]

Edited on 2010-12-31 02:26:01 by CoNexion ["With" really should have been added here when it was added.]
Additions:
- ##[[KeyPgWith With]]##


Revision [14187]

Edited on 2009-07-06 01:40:19 by CountingPine [Add simple type format to syntax, sort See Also section by approximate relevance]
Additions:
**Type** //typename//
//fieldname1// [[KeyPgAs as]] //[[DataType DataType]]//
//fieldname2// [[KeyPgAs as]] //[[DataType DataType]]//


Revision [12868]

The oldest known version of this page was created on 2008-04-02 15:35:47 by CountingPine [Add simple type format to syntax, sort See Also section by approximate relevance]
Valid XHTML :: Valid CSS: :: Powered by WikkaWiki



sf.net phatcode