Initializing help system before first use

Structures for passing information

Complex numbers are usually represented as a+bi where a and b are real numbers. a is called the real part and bi the imaginary part. We implement the following C structure to store a complex number:

typedef struct
    {
     int refcnt;              /* For reference count */
     double re, im;           /* Real and imaginary parts */
    } s_complex;

List of subroutines

The main interest of this example lies in the definition of its list of subroutines which actually is a list of operators:

static XPRMdsofct tabfct[]=
    {
     {"@&", 1000, XPRM_TYP_EXTN, 1, "complex:|complex|", cx_new0},
     {"@&", 1001, XPRM_TYP_EXTN, 1, "complex:r", cx_new1},
     {"@&", 1002, XPRM_TYP_EXTN, 2, "complex:rr", cx_new2},
     {"@0", 1003, XPRM_TYP_EXTN, 0, "complex:", cx_zero},
     {"@1", 1004, XPRM_TYP_EXTN, 0, "complex:", cx_one},
     {"@:", 1005, XPRM_TYP_NOT,  2, "|complex||complex|", cx_asgn},
     {"@:", 1006, XPRM_TYP_NOT,  2, "|complex|r", cx_asgn_r},
     {"@+", 1007, XPRM_TYP_EXTN, 2, "complex:|complex||complex|", cx_pls},
     {"@+", 1008, XPRM_TYP_EXTN, 2, "complex:|complex|r", cx_pls_r},
     {"@*", 1009, XPRM_TYP_EXTN, 2, "complex:|complex||complex|", cx_mul},
     {"@*", 1010, XPRM_TYP_EXTN, 2, "complex:|complex|r", cx_mul_r},
     {"@-", 1011, XPRM_TYP_EXTN, 1, "complex:|complex|", cx_neg},
     {"@/", 1012, XPRM_TYP_EXTN, 2, "complex:|complex||complex|", cx_div},
     {"@/", 1013, XPRM_TYP_EXTN, 2, "complex:|complex|r", cx_div_r1},
     {"@/", 1014, XPRM_TYP_EXTN, 2, "complex:r|complex|", cx_div_r2},
     {"@=", 1015, XPRM_TYP_BOOL, 2, "|complex||complex|", cx_eql},
     {"@=", 1016, XPRM_TYP_BOOL, 2, "|complex|r", cx_eql_r}
    };

In the order of their appearance this list defines the following operators:

@&
creation (construction)
@0
zero element for sums
@1
one element for products
@:
assignment
@+
addition
@*
multiplication
@-
negation
@/
division
@=
comparison (test of equality)

For most operators in the list above several versions are defined, with different types or combinations of types. The only type conversion that is carried out automatically by Mosel is from integer to real (but not the other way round), and no conversions involving external types. It is therefore necessary to define all the operations between two numbers for two complex numbers and also for a complex and a real number. For commutative operations (addition, multiplication, comparison) it is only required to define one version combining the two types, the other sense is deduced by Mosel: for example, if complex + real is defined, Mosel `knows' how to calculate real + complex. For division (not commutative) we need to define every case separately.

List of types

The definition of the new type in the list of types that is passed to Mosel looks as follows:

static XPRMdsotyp tabtyp[]=
    {
     {"complex", 1, XPRM_DTYP_PNCTX|XPRM_DTYP_RFCNT|XPRM_DTYP_APPND,
      cx_create, cx_delete, cx_tostr, cx_fromstr, cx_copy, cx_compare}
    };

The type-related functions (cx_create: creation, cx_delete: deletion, cx_tostr: transformation to a string, cx_fromstr: initialization from a string, cx_copy: copying, cx_compare: comparison) could be implemented in a similar way to what has been shown for the task module in the previous chapters. But, for practical purposes, this rudimentary memory management may not be efficient enough. In this chapter we therefore give an example of improved memory management for external types. This includes new versions of the type instance creation and deletion functions, an adaptation of the reset service, and the definition of additional list structures for storing information in the module context.

The functions for converting types to or from strings and also the copy and compare functions described for the task module only require minor modifications to adapt them to this example. Their definition will not be repeated in this chapter.
The list of services (merely consisting of the reset service) and the main interface structure are also very similar to those of the task module, and the module initialization function remains the same except for its name. We therefore refrain from printing them here.

The complete source code of the complex module is among the module examples provided with the Mosel distribution and on the Xpress website.

© 2001-2020 Fair Isaac Corporation. All rights reserved. This documentation is the property of Fair Isaac Corporation (“FICO”). Receipt or possession of this documentation does not convey rights to disclose, reproduce, make derivative works, use, or allow others to use it except solely for internal evaluation purposes to determine whether to purchase a license to the software described in this documentation, or as otherwise set forth in a written software license agreement between you and FICO (or a FICO affiliate). Use of this documentation and the software described in it must conform strictly to the foregoing permitted uses, and no other use is permitted.