cuex/opn.h: Additional Interface for Operations
[cuex: Expressions]

Data Structures

struct  cuex_opn
struct  cuex_opn_source

Defines

#define cuex_sizeof_opn(N)   (sizeof(struct cuex_opn) - sizeof(void *) + (N)*sizeof(void *))
#define CUEX_OPN_ITER(opr, opn, sub, STMT)
#define CUEX_OPN_CONJ_RETURN(opr, opn, sub, EXPR)
#define CUEX_OPN_DISJ_RETURN(opr, opn, sub, EXPR)
#define CUEX_OPN_TRAN(opr, opn, old_sub, EXPR)
#define CUEX_OPN_TRAN_NULL(opr, opn, old_sub, EXPR)
#define cuex_opn_comm_A   cuex_opn_comm_iterA
#define cuex_opn_comm_Ak   cuex_opn_comm_iterAk
#define cuex_opn_comm_img   cuex_opn_comm_iterimg
#define cuex_opn_comm_imgk   cuex_opn_comm_iterimgk

Functions

cuex_opn_t cuex_opn (cuex_meta_t opr,...)
cuex_opn_t cuex_opn_by_valist (cuex_meta_t opr, va_list operand_valist)
cuex_opn_t cuexP_opn_by_arr_with_ctor (cuex_meta_t opr, cuex_t *arr)
cuex_opn_t cuex_opn_by_arr (cuex_meta_t opr, cuex_t *arr)
cu_rank_t cuex_opn_arity (cuex_t opn)
cuex_t cuex_opn_at (cuex_t opn, int i)
cuex_tcuex_opn_begin (cuex_t opn)
cuex_tcuex_opn_end (cuex_t opn)
cuex_opn_t cuex_opn2_left (cuex_meta_t opr, cuex_t x, cuex_t y)
cuex_opn_t cuex_opn2_right (cuex_meta_t opr, cuex_t x, cuex_t y)
cu_rank_t cuex_arity (cuex_t e)
cu_bool_t cuex_opn_comm_iterA (cu_clop(f, cu_bool_t, cuex_t), cuex_t e)
cu_bool_t cuex_opn_comm_iterAk (cu_clop(f, cu_bool_t, int, cuex_t), cuex_t e)
cuex_t cuex_opn_comm_iterimg (cu_clop(f, cuex_t, cuex_t), cuex_t e)
cuex_t cuex_opn_comm_iterimgk (cu_clop(f, cuex_t, int, cuex_t), cuex_t e)
void cuex_opn_ncomm_source_init (cuex_opn_source_t src, cuex_t e)
cu_ptr_source_t cuex_opn_ncomm_source (cuex_t e)
void cuex_opn_comm_source_init (cuex_opn_source_t src, cuex_t e)
cu_ptr_source_t cuex_opn_comm_source (cuex_t e)

Define Documentation

#define CUEX_OPN_CONJ_RETURN ( opr,
opn,
sub,
EXPR   ) 
Value:
do {                                                                    \
    int cuexL_i, cuexL_r = cuex_opr_r(opr);                             \
    for (cuexL_i = 0; cuexL_i < cuexL_r; ++cuexL_i) {                   \
        cuex_t sub = cuex_opn_at(opn, cuexL_i);                         \
        if (!(EXPR))                                                    \
            return cu_false;                                            \
    }                                                                   \
} while (0)

A template for iterating over operands of an operaton as long as a condition holds. Given an operation opn with operator opr, bind each operand to sub and evaluate EXPR. If EXPR returns false, immediately return false from the surrounding function. This macro declares sub as cuex_t such that it is in scope when EXPR is evaluated.

#define CUEX_OPN_DISJ_RETURN ( opr,
opn,
sub,
EXPR   ) 
Value:
do {                                                                    \
    int cuexL_i, cuexL_r = cuex_opr_r(opr);                             \
    for (cuexL_i = 0; cuexL_i < cuexL_r; ++cuexL_i) {                   \
        cuex_t sub = cuex_opn_at(opn, cuexL_i);                         \
        if (EXPR)                                                       \
            return cu_true;                                             \
    }                                                                   \
} while (0)

Analogous to CUEX_OPN_CONJ_RETURN, but return true if EXPR evaluates to true.

#define CUEX_OPN_ITER ( opr,
opn,
sub,
STMT   ) 
Value:
do {                                                                    \
    int cuexL_i, cuexL_r = cuex_opr_r(opr);                             \
    for (cuexL_i = 0; cuexL_i < cuexL_r; ++cuexL_i) {                   \
        cuex_t sub = cuex_opn_at(opn, cuexL_i);                         \
        STMT;                                                           \
    }                                                                   \
} while (0)

A template for iterating over operands of an operation. Given an operation opn with operator opr, bind each operand to sub and call STMT. This macro declares sub as cuex_t such that it is in scope when STMT is evaluated.

Note:
The opr parameter is redundant since it must be exactly cuex_meta(opn). It is passed as an optimisation, since the caller usually must have obtained it before using this template, in order to determine that opn is in fact an operation.
#define CUEX_OPN_TRAN ( opr,
opn,
old_sub,
EXPR   ) 
Value:
do {                                                                    \
    int cuexL_i, cuexL_r = cuex_opr_r(opr);                             \
    for (cuexL_i = 0; cuexL_i < cuexL_r; ++cuexL_i) {                   \
        cuex_t old_sub, cuexL_new_sub;                                  \
        old_sub = cuex_opn_at(opn, cuexL_i);                            \
        cuexL_new_sub = EXPR;                                           \
        if (old_sub != cuexL_new_sub) {                                 \
            cuex_t *new_arr = cu_salloc(sizeof(cuex_t)*cuexL_r);        \
            memcpy(new_arr, cuex_opn_begin(opn), sizeof(cuex_t)*cuexL_r); \
            new_arr[cuexL_i] = cuexL_new_sub;                           \
            for (++cuexL_i; cuexL_i < cuexL_r; ++cuexL_i) {             \
                old_sub = cuex_opn_at(opn, cuexL_i);                    \
                new_arr[cuexL_i] = EXPR;                                \
            }                                                           \
            opn = cuex_opn_by_arr(opr, new_arr);                        \
            break;                                                      \
        }                                                               \
    }                                                                   \
} while (0)

A template to transform an operation. Reassign opn with an operation of operator opr, which must be the same as the operator of opn, with operands obtained as follows. For each operand of opn, bind it to old_sub and then evaluate EXPR to obtain the new operand. old_sub is declared locally by this macro and is in scope where EXPR is evaluated.

#define CUEX_OPN_TRAN_NULL ( opr,
opn,
old_sub,
EXPR   ) 
Value:
do {                                                                    \
    int cuexL_i, cuexL_r = cuex_opr_r(opr);                             \
    for (cuexL_i = 0; cuexL_i < cuexL_r; ++cuexL_i) {                   \
        cuex_t old_sub, cuexL_new_sub;                                  \
        old_sub = cuex_opn_at(opn, cuexL_i);                            \
        cuexL_new_sub = EXPR;                                           \
        if (!cuexL_new_sub) {                                           \
            opn = NULL;                                                 \
            break;                                                      \
        }                                                               \
        if (old_sub != cuexL_new_sub) {                                 \
            cuex_t *new_arr = cu_salloc(sizeof(cuex_t)*cuexL_r);        \
            memcpy(new_arr, cuex_opn_begin(opn), sizeof(cuex_t)*cuexL_r); \
            new_arr[cuexL_i] = cuexL_new_sub;                           \
            for (++cuexL_i; cuexL_i < cuexL_r; ++cuexL_i) {             \
                old_sub = cuex_opn_at(opn, cuexL_i);                    \
                new_arr[cuexL_i] = EXPR;                                \
                if (new_arr[cuexL_i] == NULL)                           \
                    break;                                              \
            }                                                           \
            if (cuexL_i == cuexL_r)                                     \
                opn = cuex_opn_by_arr(opr, new_arr);                    \
            else                                                        \
                opn = NULL;                                             \
            break;                                                      \
        }                                                               \
    }                                                                   \
} while (0)

A template to transform an operation, with loop-termination on failure. Same as CUEX_OPN_TRAN, except that EXPR is allowed to return NULL, in which case the loop terminates an opn is assigned NULL.


Function Documentation

cu_rank_t cuex_arity ( cuex_t  e  ) 

The arity if e is an operator, the compound size if e is a compound, otherwise 0.

cuex_opn_t cuex_opn ( cuex_meta_t  opr,
  ... 
)

Create an operation of opr applied to the vararg arguments. The function expects cuex_opr_r(opr) vararg arguments of type cuex_t, which should be dynamically typed objects and operations.

cuex_opn_t cuex_opn2_left ( cuex_meta_t  opr,
cuex_t  x,
cuex_t  y 
)

Return left-associated application of opr on x and y. Time complexity is linear in the number of top-level opr in y.

Precondition:
opr is a binary operator.
cuex_opn_t cuex_opn2_right ( cuex_meta_t  opr,
cuex_t  x,
cuex_t  y 
)

Return right-associated application of opr on x and y. Time complexity is linear in the number of top-level opr in x.

Precondition:
opr is a binary operator.
cu_rank_t cuex_opn_arity ( cuex_t  opn  ) 

Returns the arity of the operator of opn.

cuex_t cuex_opn_at ( cuex_t  opn,
int  i 
)

Returns operand i of opn, counting from zero.

cuex_t* cuex_opn_begin ( cuex_t  opn  ) 

Returns the start of the operand array of opn.

cuex_opn_t cuex_opn_by_arr ( cuex_meta_t  opr,
cuex_t arr 
)

Create an operation of opr applied to arr. The array should contain cuex_opr_r(opr) values of dynamically typed objects and operations.

cuex_opn_t cuex_opn_by_valist ( cuex_meta_t  opr,
va_list  operand_valist 
)

As cuex_opn, but with varargs prepared by caller.

cuex_t* cuex_opn_end ( cuex_t  opn  ) 

Returns past-the-end of the operand array.

Generated 2009-11-23 for culibs-0.25 using Doxygen. Maintained by Petter Urkedal.