4GL Programming language
Introduction
Short, quick-and-dirty, general intro to x4GL
4GL Programs
Structure of a program
DATABASE section
GLOBALS section
Functions
MAIN block
DEFINE section
4GL Commands
4GL programming language was born in Informix corp., about 15 years ago. Because of that, and not to conflict with with 4GL as general programming concept (BASIC is in principle also Fourth Generation Language, as opposed to C, that is Third Generation Language), we should refer to basic 4GL syntax as I-4GL.
Today, even among Informix-distributed products, there is distinction among "classic" I-4GL and D4GL (Informix name for 4Js 4gl compiler), that introduced number of language enhancements. Then Informix implemented some of this enhancements back to "classic" 4gl, and added some of it's own (v 7.3), that 4Js in turn implemented in 'Universal Compiler" V3 (this is actual name for 4Js product that Informix distributes under the name "D4GL" - Dynamic 4GL.)
Confused? Why am I not surprised. So here is how we will refer to different implementations of LANGUAGE syntax:
I4GL - Informix non-GUI, a.k.a. "classic" products syntax, V 7.3
D4GL - 4Js extended syntax, including I4GL
A4GL - Aubit 4GL specific syntax, including I4GL.
x4GL - all of the above as general name for all
Lucky for us, Querix decided that it will not change language, and instead do all GUI related configuration from separate configuration files.
Aubit 4GL, as package, and A4GL, as language definition, is a superset of I4GL. Our first aim is to provide full UNCONDITIONAL compatibility with I4GL.
Since this means that 90% of the syntax used in A4GL will be I4GL, and since this document is not intended to be I4GL manual, we strongly suggest that if you refer to existing Informix documentation and tutorials downloadable from there web site, and books about 4gl, like:
Informix Unleashed, (ISBN 0672306506) complete book in HTML format about Informix products, by John McNally. You will find several complete chapters about 4GL language there, including chapters on Informix database servers. You will also learn there that "To develop with a 4gl, the developer does not have to be an expert programmer".
(I have asked the author for permission to include his book in Aubit 4GL distribution, but received no answer)
The rest of this page will serve more like quick and dirty crash course to give you some idea how the I4GL look like, as the language. For A4GL extensions. please refer to the appropriate sections of this manual.
Summary:
To learn I4GL, refer to Informix manuals for Informix-4GL version 7.3 ( http://www.informix.com or direct links to Informix 4gl by example, Informix 4gl concepts and use, Informix 4gl Reference Manual - please remember that exact locations can change, and if they do, use search function on Informix web site to find new locations of this documents), and third-party books
To learn about A4GL extensions, read this manual
To get some idea about how I4GL looks like, and get some idea about combined I4GL and A4GL functionality, continue reading this page
To get 4GL code examples, go to http://www.informix.com/idn and look for Example application, or download one of GNU 4GL programs from http://www.falout.com
4GL Programs
Structure of a program
DATABASE section
GLOBALS section
Functions
MAIN block
DEFINE section
4GL Commands
A 4gl program consists of a series of modules and forms. Each 4gl module can contain functions and reports and each program must contain exactly one 'main' section and must end in a .4gl extension. C modules can also be included in programs
database section
globals section
function/report/main block
.
.
.
.function/report/main block
This section is optional and is of the format :
DATABASE database-name
The database name is actually the DATA SOURCE NAME (DSN) from the ODBC drivers.
This optional section allows you to define variables which are accessible to all modules. There is normally a single file (typically called 'globals.4gl') where variables are defined. All other modules which need these variables then include that file using the a global statement .
eg.
globals.4gl
GLOBALS
DEFINE a INTEGER
END GLOBALS
module.4gl
GLOBALS "globals.4gl"
Note: In Aubit 4GL the any 'globals' module (containing the GLOBALS / END GLOBALS) must be compiled first.
A function in 4GL is a set of commands which are executed when called from another block of code. A function can accepts parameters and can return values.
A function is defined :
FUNCTION function-name ( parameter-list )
define-section
commands
END FUNCTION
Values are returned using the RETURN keyword:
RETURN value
Each program must contain a main section - it is the starting point in any program.
MAIN
define-section
commands
END MAIN
This optional section allows you to define variables which may be used subsequently:
In its simplest form
DEFINE variable_names datatype
or
DEFINE CONSTANT constant_name "Value"
DEFINE CONSTANT constant_name Number-Value
More than one variable can be defined as any type in the same statement by separating the names with a comma:
DEFINE a,b,c INTEGER
Available datatypes are :
SMALLINT (2 byte integer)
INTEGER (4 byte integer)
CHAR (Single character 'string')
CHAR(n) (n character string
MONEY
DECIMAL (These are not fully implemented)
FLOAT (8 byte floating point number - (C double))
SMALLFLOAT (4 byte floating point number - (C float))
DATE (date - number of days since 31/12/1899)
DATETIME
INTERVAL
BYTE
TEXT
VARCHAR Unimplemented yet
LIKE tablename.columnname '1
RECORD LIKE tablename.* '1
'1 - can only be used when the module has a DATABASE statement These copy the datatypes directly from the database either for a simple column, or to generate an entire record (see below)
Special datatypes are :
ARRAY [n] OF datatype defines an array
RECORD .. END RECORD defines a record structure
ASSOCIATE ....
These special types are used with the other datatypes.
Arrays
Syntax:
DEFINE vars ARRAY [n] OF datatype
Eg.
DEFINE lv_arr ARRAY[200] OF INTEGER
defines an array of 200 elements each being an integer
Elements of an array are indexed from 1 to the number of elements specified.
IMPORTANT: NO BOUNDS CHECKS ARE MADE, accessing elements which are outside those defined (ie <1 or > n) will result in an error (Usually a core dump).
Eg
LET lv_arr[1]=1
.
LET lv_arr[200]=200
LET lv_arr[201]=201 # this will cause a program fault!
Records
Records are structured groups of data, with the entries are separated by commas.
Elements within a record are accessed via the record name '.' element name.
Syntax
DEFINE recordname RECORD
element datatype,
.
.
element datatype
END RECORD
Eg.
DEFINE lv_rec RECORD
elem1 CHAR(10),
elem2 INTEGER
END RECORD
Defines a record with two elements.
Eg.
LET lv_rec.elem1="string1"
Record may also be nested and used in conjunction with arrays.
The following are all therefore valid:
DEFINE lv_record ARRAY[20] OF RECORD
elem1 CHAR(20),
elem2 INTEGER
END RECORDDEFINE lv_record RECORD
a ARRAY[200] of INTEGER,
b CHAR(20)
END RECORDDEFINE lv_record RECORD
subrecord1 RECORD
elem1 CHAR(10),
elem2 INTEGER
END RECORD,
subrecord2 RECORD
elem2 DATE
END RECORD
END RECORD
ASSOCIATE ARRAYS
Associative arrays allow you to access data from an array using a string as a subscript rather than an integer. For example:
LET age<<"bob">>=40
DISPLAY age<<"bob">>
This can be especially useful when dealing with codes and code desciptions:
LET lv_desc<<"A">>="Active"
LET lv_desc<<"I">>="Inactive"
LET lv_desc<<"R">>="Running"
LET lv_desc<<"D">>="Deleted"
LET lv_state="A"
.
.
DISPLAY lv_desc<<lv_state>>
(This is for illustration, the data would normally be read from a database!)
To define an associate array:
DEFINE name ASSOCIATE [CHAR] (nc) WITH ARRAY [nx] OF datatype
Where nc is the number of characters to use for the index, and nx is the total number of elements that may be stored.
PERFORMANCE NOTE:
Internally, associate arrays are stored using hash tables, for performance reasons always declare 'nx' larger than is actually required. A factor of two is optimum in most cases.
Again the datatype used in this form of array may be a RECORD, ARRAY etc.
Eg.
DEFINE lv_asoc1 ASSOCIATE CHAR(10) WITH ARRAY[10] OF INTEGER
DEFINE lv_asoc3 ASSOCIATE (10) WITH ARRAY[10] OF INTEGER
DEFINE lv_asoc2 ASSOCIATE CHAR(10) WITH ARRAY[10] OF RECORD
element1 CHAR(10),
element2 CHAR(20)
END RECORD
Constants
Constants are defined using
DEFINE CONSTANT name value
Eg.
DEFINE CONSTANT max_num_vars 30
DEFINE CONSTANT err_string "There is an error"
IF num_vars>max_num_vars THEN
ERROR err_string
END IF
It is also possible to use constants in any subsequent define sections:
DEFINE CONSTANT num_elems 20
DEFINE lv_arr ARRAY [num_elems] OF INTEGER
IF num_vars<=num_elems THEN
LET lv_arr[num_vars]=1
END IF
(syntax and documentation in Informix manuals)
CALL
CASE
CLEAR
CLOSE
CODE
CONSTRUCT
CONTINUE
CREATE
CURRENT WINDOW
DECLARE
DISPLAY
DROPS
ERROR
EXECUTE
EXIT PROGRAM
EXT
FINISH
FOR
FOREACH
GOTO
HIDE
HIDE OPTION
IF
INIT
INPUT
LABEL
LET
LOAD
LOCATE
MENU
MESSAGE
MOVE
NEXT FIELD
NEXT OPTION
OPEN
OPENS
OPTIONS
OUTPUT
PAUSE SCREEN
PREPARE
PROMPT
REPORT
RETURN
RUN
SET
SET DATABASE
SHOW
SHOW OPTION
SLEEP
SQL
SQLCODE
START
START RPC
STOP RPC
UNLOAD
WHENEVER
WHILE
DEFER
SYNTAX
DEFER INTERRUPT
...etc...