Wednesday, February 13, 2013

Simple Math Expressions

Time to get back to the technical stuff.  One of my outstanding work items is to finish up Simple Math for inclusion in the QDM-based HQMF guide as we agreed to at the HL7 Working Group meeting.  I spent some time with Marc Hadley on the phone a few weeks back, and we firmed up what it would consist of, which I report here:

Simple Expressions

Simple expressions is a language for expressions based on JavaScript, whose purpose is to enable simple computations in HL7 specifications such as HQMF.  It allows elements of the model found in a standard or implementation guide to be accessed and computed with.  The language is based on JavaScript to formalize the behaviors of the computation model, but it need not be implemented using a JavaScript interpreter.

Note: We should likely be more specific as to what version of JavaScript it is based upon.  I'd propose ECMAScript 5.1 would be a good starting point.

Note: Strings needed to be added to support dynamic construction of messages for HeD, so this is now "Simple Expressions" instead of Simple Math.

Identifiers

Identifiers in Simple Math follow the rules of JavaScript identifiers with a few simplifications to make them more usable in other implementation environments.

identifier ::= [a-zA-Z][a-zA-Z0-9_]*

Data Types

The data types of Simple Math are the Date and String objects and numbers and Booleans.  Literals for null, strings, numbers and Boolean values are represented as in JavaScript.  Regular expressions and function declarations are not supported.  The Date object will be wrapped to support additional member operations supporting date arithmetic, and we'll need to evaluate that further.

Regular expressions are not supported.

We will add support for a limited set of HL7 data types: IVL_TS, IVL_PQ, PQ and perhaps CD seem to be the most likely.

Operations

The language does not support assignments or side effects, thus, there are no assignment operators, nor post- or pre-increment/decrement operators, nor a delete operator.  Bit operators (~, &, |, ^, <<, >> or >>>) are also not supported.

The strict equivalence === and !== are not supported.

Given the lack of side effects in this language, there is no need for a comma operator, since it serves to order expressions, and evaluates to the last expression.  If you would write an expression as expr1, expr2 in JavaScript, then in Simple Expressions, all you need write is expr2.

The instanceof and typeof operators are allowed.

Note: We hadn't come to a conclusion on the ternary operator ?:.  This is rather useful, but not readily supported in other implementation environments.  One of the challenges is that according to the rules of ECMAScript, only one of the two expressions after the ? is evaluated, and this may not be readily implemented elsewhere.  I think we allow it, and simply note that some implementations may not be able to fully implement the semantics as specified.  It's therefore a warning to users to use the ternary operator sparingly if they want their expressions to be computable on the widest number of platforms.

Note: We also haven't come to a conclusion on whether arrays are needed or not.

Miscellaneous

  • Comments within expressions aren't supported because they can be included in the surrounding XML where the expression is used.
  • There are no multi-step expressions.  Line breaks are treated like white space in an expression, and there is no need to terminate an expression with a ; because it is terminated by context.
  • String expressions force conversion of numbers to strings, just as in Java Script.

Implementing the Language

One of my design goals for implementing this language was that common expressions in the language should be readily converted to another implementation language through an appropriate sequence of regular expression substitutions.   As the language is currently specified, this amounts in C, C++, C#, Java and JavaScript to being an identity transform (or nearly so).  

My test case for success would be to build an implementation that converts common expressions in Simple Expressions to SQL.

3 comments:

  1. Hi Keith,

    I have related question. may be not completely related but you can shed some light on it.
    As you know that a clinical statement in CDA R2 can be associated with zero or more “Criterion” through “precondition”.

    Definition of "precondition from CDA R2:

    4.3.8.2 precondition
    The precondition class, derived from the ActRelationship class, is used along with the Criterion class to express a condition that must hold true before some over activity occurs.

    This means that the precondition must be true for a service/activity to be performed.

    Questions:
    Since a clinical statement can be associated with zero or more “Criterion” through precondition, what would happen in case there are TWO Criterions, one is TRUE and other is FALSE? What should be the default operator in order to arrive at the final decision point whether a service/activity should be performed or not? Should it be allTrue (AND) or atLeastOneTrue(OR?

    Thanks!


    ReplyDelete
    Replies
    1. In the HL7 Clinical Statement Pattern, the conjunctionCode for the precondition is set to AND (allTrue). In CDA, it is commonly understood to be AND (allTrue) and specified as such in the documentation. In fact, as for allTrue, the precondition should be fixed to be AND in this case, but simply wasn't when the standard was created.

      Delete
  2. Thanks Keith!
    Is it possible to change this to "OR"/"XOR"? or create an extension base on the HQMF as HQMF do use "OR"/"XOR"?

    PS. I am Asim@Philips and Continua Health Alliance. don't prefer to use my personal Google account here that's why asked anonymous question.

    ReplyDelete