Introduction to Object-Relational Language

ORL Contents

ORL stands for Object-Relational Language. Respectively, it handles Objects and Relations in the sense that Objects are instances of Relations (being used in relational algebra). Put it in other way, Classes in ORL stands for Relations in relational algebra.

What is important here, ORL defines just syntax and conceptual idea for implementatin of language interpreter but it doesn't specify reserved words or set of commands. That is, one might develop ORL engine relying on basic terms like "object", "class" and "attribute" (like it happens to C++ ORL engine created at ProPro Group, Russia) while other can develop another ORL engine relying on "relationship" and "relation". For instance, Java ORL engine used in Webstructor relies on "thing" (like "class") and "property" (like "attribute").

Notable, that ORL doesn't make fundamental distinction between "class" (as abstract entity) and "object" (as specific instance). This is because while one might think about object "Bob" as intance of class "Man", another might think about "Angry Bob" and "Happy Bob" as about specific instances of class "Bob".

The latter feature makes it possible to use any object model relying on ORL to be expressible in terms of totally different object model relying on the same ORL. For example, object model built on "classes" and "attributes" may be expressed within another object model built with "things" and "properties". In turn, former may be used to describe some model consisting of "relationships".

You can look at ORL from the following perspectives. Essentially, it takes together the most powerful and convenient features of LISP, XML, SQL, Prolog and Smalltalk. Below we compare ORL with all of these languages.

 

1. ORL syntax makes code written in simple hierarchical structures as LISP does.

For example, here is the same code written in LISP and ORL.

 
        LISP:
        (if 
               (and 
                       (> x -1) 
                       (< x 1) 
                       (type x integer)) 
                (print "x is equal to 0"))
        ORL:
        if 
               condition 
                       type and; 
                       list
                               operation '>'; lvalue x; rvalue -1;, 
                               operation '<'; lvalue x; rvalue 1;, 
                               operation instaneof; lvalue x; rvalue integer;
                       ;
               ;
               function 
                       name print; 
                       arguments 
                               "x is equal to 0";
                       ;
               ;
        ;

There are three major diferences between ORL and LISP.

First, LISP keeps head of relation and arguments of relation in one bracketed list "(love,John,Mary)" while ORL keeps head of relation separately "love object John; subject Mary;;".

Second, LISP doesn't label arguments of relation while ORL does. That is, "(love,John,Mary)" and "(love,Mary,John)" have different meanings in LISP while "love object John; subject Mary;;" and "love subject Mary; object John;" are identical in ORL.

Third, LISP doesn't distinguish collections of attributes or arguments and collections of objects while ORL does. That is, in LISP you can describe a team as "(team (name 'Eagles') (members 'Tom' 'Bob' 'Jim' 'Tim'))" while in ORL you use different punctuation marks to distinguish sequence of labeled attributes from sequence of unlabeled elements.

 
        "team name 'Eagles'; members name Tom;, name Bob;, name Jim;, name Tim;;;"

 

2. ORL can easily describe complex and flexible data structures as XML does.

For example, here is the same data encoded in XML and ORL.

 
        XML:
        <team name='Eagles'>
               <coach>Ron</coach>
               <member>Tom</member>
               <member>Bob</member>
               <member>Jim</member>
               <member>Tim</member>
        </team>
        ORL:
        team 
               name 'Eagles'; 
               coach name Ron;;
               members 
                       name Tom;, 
                       name Bob;, 
                       name Jim;, 
                       name Tim;
               ;
        ;

There are four major distrinctions between ORL and XML.

First, while XML may be self-described using special DTD tags, ORL self-describes itself using the same syntax it uses to describe data (as LISP does). In other words, while XML distinguishes data and meta-data, ORL doesn't.

 
               For example, consider the following XM code.
               <!DOCTYPE message [<!ELEMENT note    (from,to,subject,body)>
                       <!ELEMENT from    (#PCDATA)>
                       <!ELEMENT to      (#PCDATA)>
                       <!ELEMENT subject (#PCDATA)>
                       <!ELEMENT body    (#PCDATA)>]>
               <message>
                       <from>Anton</from>
                       <to>Yulia</to>
                       <subject>hi</subject>
                       <body>How are you?</body>
               </message> 

If you rewrite code in ORL, it will look like follows.

 
               class 
                       name message;
                       attributes
                               name from; TYPE STRING;,
                               name to; TYPE STRING;,
                               name subject; TYPE STRING;,
                               name body; TYPE STRING;
                       ;
               ;
               message
                       from Anton;
                       to Yulia;
                       subject hi;
                       body "How are you?";
               ; 

Second, ORL doesn't handle chunks of raw textual data the same way as XML does. In XML, there is distinction between "content" and "attribute" while in ORL "content" is just value of attribute. In other words, when you use XML to write something like <greeting language="French">Comment allez-vous?</greeting>, in ORL you always write it as follows

 
        greeting language French; text "Comment allez-vous?";; 

Respectively, you can not include chunk of some text intermixed with ORL statements into value of ORL attribute as you can do it with XML content. This is because ORL is not intended to handle hypertexts (as it happen to XML historically) but it is intended to handle hyperdata.

Third, ORL eliminats confustion between XML attribute and single element in XML tag content. In XML, there is always some sort of vagueness, whether to write

 
    <book title="Sandy Hook"/> 

or

 
    <book>&lttitle&gtSandy Hook</title></book>.

At the same time, second kind of notation nay lead to confusion between single value and list of values like in

    <book><author>John Crown</author><title>Sandy Hook</title><author>Mary Brown</author></book>.

In ORL, you always write this as follows.

 
        book
               title 'Sandy Hook';
               authors 
                       name 'John Crown';,
                       name 'Mary Brown';
               ;
        ;

Fourth, ORL enables you to desribe non-hierarchical and even recurrent structures which is hardly possible in XML. For example, you can easily describe mutual relationships beteen Wife and Husband as follows.

 
               Woman name Mary;;
               Man name Gary;;
               Woman(Mary) husband (Gary);;
               Man(Gary) wife (Mary);;

You can even add more complexity to this story sayng that

 
               Man name John; love (Mary); like (Gary);;
               Woman(Mary) like (Gary); love (John);;

That is easily done because ORL supports two differnt ways to access the object.

 
        - upon creation, like Woman name Mary;;
        - on query, like Woman(Mary);

Then, one can create (declare) object first and then reference this object by query from other objects. This is somewhat similar to "declaration versus definition" paradigm used in C/C++. First, you create an object with minimal set of attributes needed to identify it in a query. After that, you refer to this object and add more attributes and relationships to it.

 

3. As SQL, ORL supports complex structured queries.

For example, here is the same query written in SQL and ORL.

 
        SQL:
        UPDATE account 
               SET balance = balance - 99.99, last_date = '07/01/2001' 
               WHERE (number='34509045')
        ORL:
        account(number '34509045')     
               last_date '07/01/2001';
               balance -= 99.99;
        ;

Here are a few differences between SQL and ORL.

First, in ORL, there is no distinction like between SQL DDL and SQL DML. This is because ORL Class is just kind of ORL Object. That is, "CREATE TABLE customer" statement in SQL is more like "INSERT INTO tables (name) VALUES ('customer')". This is what essentially happens in SQL behind the scene. In ORL, this is explicit.

Second, there is no separate SELECT statement in ORL to return list of rows with columns filled in within each row. This is because ORL is intended for symmetric interaction between applications and not for client-server question-answer. For example, if one application wants to say something about love to another one, it submits kind of the following SQL UPDATE statement.

 
    "feeling(name 'love') isKindOf 'fun';;" 

In turn, other application may respond with another statement.

 
    "feeling(name 'love') isKindOf 'responsibility';;"

Still, there is nothing wrong to provide an ORL object with some DUMP method so it might be invoked by query.

 
        "account(balance<0,last_date>'07/01/2001') DUMP;"

Then, result would be equivalent to output of the following SQL query.

 
        "SELECT * FROM account WHERE balance<0 AND last_date>'07/01/2001'"

Third, ORL is somewhat much more Object-oriented than SQL because its syntax is intended to handle hierarchically enclosed objects like in the following example.

 
        ESTATE
               NAME "Maple Grove";
               PRICE 999999;
               OBJECTS
                       LAKE SQUARE 333;,
                       LAWN SQUARE 444;,
                       PARK SQUARE 555;
               ;
               BUILDINGS
                       NAME GARAGE;,
                       NAME HOWSE
                               FLOORS 2;
                               ROOMS
                                      TITLE Living; WINDOWS 4;,
                                      TITLE Dining; WINDOWS 3;,
                                      TITLE Kitchen; WINDOWS 1;,
                                      TITLE 'Master Bedroom'; WINDOWS 3;,
                                      TITLE Bedroom; WINDOWS 2;,
                                      TITLE 'Storage Area' WINDOWS 0;;
                               ;
                       ,
                       NAME 'SUMMER CABIN';
               ;
        ;

 

4. Like PROLOG, ORL may handle predicates as long as you can think about any ORL object as about predicate.

For example, you might define the following objects in ORL.

 
        PARENT_CHILD
               PARENT PAM; CHILD BOB;,
               PARENT TOM; CHILD BOB;,
               PARENT TOM; CHILD LIZ;,
               PARENT BOB; CHILD ANN;,
               PARENT BOB; CHILD PAT;,
               PARENT PAT; CHILD JIM;
        ;

Then, you might make the following queries to the ORL engine and get respective responses.

 
        Who are BOB's kids?
               PARENT_CHILD( PARENT BOB ).CHILD;
               Result: ANN, PAT
 
        Is BOB parent of PAT?
               PARENT_CHILD( PARENT BOB, CHILD PAT );
               Result: TRUE
 
        Is LIZ parent of PAT?
               PARENT_CHILD( PARENT LIZ, CHILD PAT );
               Result: NO
 
        Who are parents of PAM's child?
               PARENT_CHILD( CHILD (CHILD PAM).PARENT ).PARENT;
               Result: PAM, TOM

 

5. Like in Smalltalk (and Unlike C++ or Java), object-orientation in ORL is completly dynamic.

That is, there is nothing to define on compilation time because there is no compilation. What makes ORL different, is that you can use SQL-alike queries consistenly with OO-style access to object member attributes and functions. For example, you can access certain instance of ESTATE object and recursively refer to attribute of some of its attributes as follows.

 
        N_BEDROOM_WINDOWS = ESTATE("Maple Grove").BUILDINGS(NAME HOWSE).ROOMS(TITLE Bedroom).WINDOWS;

ORL Contents

(C) Copyright 1988-1998,2001 Anton Kolonin