Pseudo-functions
Divider

A pseudo-function is a construct that is formed like a function call, but which isn't. There are two basic types:

Function-style macros are user-defined pseudo-functions. They are discussed here. This section mainly documents the compiler's built-in pseudo-functions. The names of all of these functions are reserved words. Here is a list of them: SizeOf, Defined, MacroString, New, Delete, Class, and Function.

New and Delete can be overloaded to become real functions.

Cast

cast-pseudofunction: Cast (expression: type-spec [[,] extra-arguments]) 

This pseudo-function changes the type of an expression, optionally providing arguments to a type-cast function.

The word "cast" is used in the sense of "casting to a mold".  Using the Cast pseudo-function on an expression is referred to as type-casting the expression.  The return value of the Cast function is always the specified type-spec.  The compiler has a built-in ability to cast many different types to many other types; the type-casts the compiler can perform are listed or described in the sections associated with a given type, and are not listed here.

Here are some examples:

Var X: Integer;                                    // Line 1
Var Y: Int8;                                       // Line 2
Var Z: String("0x10A");                            // Line 3
                                                   // Line 4
X = Cast (Z: Integer); // Sets X to 0x10A or 266   // Line 5
Y = Cast (X: Int8); // Sets Y to 0xA or 10         // Line 6
Z = Cast (Y: String, Hex); // Sets Z to "0xA"      // Line 7

Line 5 tells the compiler to convert Z to an integer before assigning it to X.  Line 6 tells the compiler to convert X to Int8 before assigning it to Y.  Line 7 tells the compiler to convert Y to a string in hexadecimal format (because of the extra argument Hex.)  The first two conversions could have been done implicitly, except that the compiler would issue a warning due to the decrease in precision; the last conversion needed to be done explicitly in order to produce a hex-format string.

An implicit type cast is a cast performed automatically by the compiler.  For example, if line 5 had been:

X = Z;

The compiler would perform the type-cast implicitly from String to Integer, because X must store an Integer, not a String. However, since String is considered to be a higher-precision type, the compiler would issue a warning because a conversion to Integer, in some cases, results in data loss.  The use of an explicit cast removes the warning.

Note: The use of the ternary operator does not conflict with the Cast syntax.  For example:

StdOut.Print Cast (X < 100 ? X : Y : String);
// Compiles okay, is interpreted as:
StdOut.Print Cast ((X < 100 ? X : Y): String);

SizeOf

sizeof-pseudofunction: SizeOf (type-spec | expression)

If the contents of the brackets can be interpreted as identifying a type name, the size of that type is returned. Here are some examples:

If it is not recognized as a type name, it is evaluated as an expression, and the value of the pseudo-function is the size of the type of the expression. For example, if X is a Double:

If the expression contains side effects (that is, it contains a function call, assignment, or other operation), those side effects are executed at run-time; however, they do not affect the value of the pseudo-function. For example, if N is an Integer and X is a Double:

N = SizeOf (X = 5);

In this case, X is set to 5 at run-time, but the value of the pseudo-function is predetermined at compile-time to be 8.

If the expression evaluates to

then the size is determined at run-time and the pseudo-function-call becomes equivalent to:

(Class(expression).Size)

In all other cases, the size is determined at compile time and the value of the pseudo-function is considered by the compiler to be a constant.

Defined and DefinedString

defined-pseudofunction: Defined (identifier)
definedstring-pseudofunction: DefinedString (identifier [(arguments)])

Both of these pseudo-functions prevent the macro identifier within the brackets to be expanded. Defined() evaluates to a Boolean: True if the identifier is defined, and False if it is not. DefinedString(), on the other hand, evaluates to the expansion of the macro in the form of a string literal. Arguments can be provided for the macro only if the macro expects arguments. If the macro expects arguments but you don't provide them, the original argument names are used. If the identifier specified is not defined, the pseudo-function evaluates to "".

Example:

Compile ANumber "Hello\n";
...
Compile If DefinedString(ANumber).Right(1) == '\n':
...
Compile Else:
...
Compile EndIf;

Both of these pseudo-functions can be evaluated to constants at compile-time.

New and Delete

new-pseudofunction: New (new-spec | (new-spec))
new-spec
: [delimiter] type-spec [initialize-spec] [delimiter [extra-arguments]]
delete-pseudofunction: Delete (delete-spec | (delete-spec)
delete-spec: [delimiter] lvalue-expression [extra-arguments]

Both New and Delete can be called using the form of a function-call statement, in which case the brackets are omitted.

These functions create/destroy an object or set of objects using dynamically-allocated memory. type-spec specifies the type of the object to create, which can be an array. It can also be a reference type, or a simple type like Integer, though there wouldn't be much point in creating a single object that small.

When writing an overloaded New pseudo-function, the first argument must be an Integer; this argument is the size of the resolvedtype. There may be delimiter(s) before the first argument, which then, unless optional, must be present in the call to New. The return type of an overloaded New can be any reference type.

When writing an overloaded Delete function, the first argument must be of the type @ Direct. This reference will contain the address of the lvalue passed to it, or four bytes before if an array is being deleted. An overloaded Delete doesn't need to return a value, but it may have one.

There may be additional arguments and/or delimiters to New and Delete, which are represented by extra-arguments in the syntax above. The built-in versions of New and Delete have neither delimiters nor extra arguments. These have global scope; it is only legal to overload the bare forms of New and Delete within a Class.

When specifying dimensions to New, all but the most major dimension must be constant. The most major dimension is generally not constant, but it can be. The return type of New is a reference (@) to the type being created.

Class

class-pseudofunction: Class (resolvedtype | expression)

The Class pseudo-function evaluates to a Const Class of the built-in type Class, so that you can get information about the class. If the contents of the brackets can be interpreted as identifying a type name, the pseudo-function evaluates to the Class instance associated with the type specified.  Otherwise, the argument is evaluated as an expression.  If the result of the expression is a value A,

If the expression contains side effects (that is, it contains a function call, assignment, or other operation), those side effects are executed at run-time; however, they do not affect the value of the pseudo-function. For example, if C is a @ Class and X is a Double:

@C = @Class (X = 5);

In this case, X is set to 5 at run-time, but the value of the pseudo-function is preset at compile-time to the Class instance associated with Double.

A statement cannot be initiated with this pseudo-function because the keyword Class may be interpreted as the beginning of a Class statement.

Function

function-pseudofunction: Function ( text )

This pseudo-function returns the specified function so that its address can be taken.  The result of this pseudo-function is special in that it is not a data type, but rather a function type.  Normally you can't do anything with a function except call it, but the value returned from this pseudo-function cannot be called.  There are only two things you can do with the returned value:

The text is formed like a function-call statement except that no arguments or delimiters may be provided to the function.  A statement cannot be initiated with this pseudo-function.

Table of Contents Qwertie's Site/Mirror
Next
Previous
Hosted by www.Geocities.ws

1