_object, _member, _method, _executeclass and _attribute Statements

Purpose The _object statement is used to access an object whose name is derived at runtime.
The _member statement is used to access a member whose name is derived at runtime.
The _method statement is used to access a method whose name is derived at runtime.
The _executeclass statement is used to specify a class at runtime whose member/method is to be invoked.
The _attribute statement is used to access an attribute whose name is derived at runtime.
This is a handy tool to use for indirection and runtime resolution for objects, members, methods, execute classes and/or attributes.
Format _object({object path})

_member({member name})

_method({method name and parms})

_executeclass({execute class name})

_attribute({attribute name})

_object({object path})._member({member name})

_object({object path})._method({method name and parms})

_object({object path})._executeclass({execute class name})::_method({method name and parms})

_object({object path})._attribute({attribute name})

{object path} an expression that evaluates to the path expression for the object being accessed
{member name} an expression that evaluates to the name of the member being accessed
{method name and parms} an expression that evaluates to the name of the method being executed with the parameters
{execute class name} an expression that evaluates to the name of the class whose member/method will be executed
{attribute name} an expression that evaluates to the name of the attribute being accessed

Example #1 _object("MyNode")

An expression that will access the MyNode node.

Example #2 _object("MyNode")._attribute("the" + "Attr")

An expression that will access the theAttr attribute of the MyNode node.

Example #3 string s = "MyAttr";
_object("MyNode")._attribute(s)

An expression that will access the MyAttr attribute of the MyNode node. The value of s is evaluated and used as the attribute to be accessed.

Example #4 class XFarm {
   construct {
   public:
      <MyCow breed="Friesian">Bessie</MyCow>
   }
   public:
      int Add(int a, int b) {
         return a + b;
      };
};
node(XFarm) MyFarm;
xout("\r\nAdd 10 + 20 = " + _object("MyFarm")._method("Add", "a" = 10, "b" = 20));

The code above will instantiate an object called MyFarm which contains the MyCow object. The xout statement writes the following text to the output stream:

Add 10 + 20 = 30

Example #5 class XOxygen {
   public:
      string   GetName() {
         return "Oxygen";
      };
}
class XHydrogen {
   public:
      string   GetName() {
         return "Hydrogen";
      };
}

node(XHydrogen, XOxygen)   MyWater;

xout("\r\nXOxygen name using _object and _executeclass = " + _object("MyWater")._executeclass("XOxygen")::_method("GetName"));
xout("\r\nXHydrogen name using _object and _executeclass = " + _object("MyWater")._executeclass("XHydrogen")::_method("GetName"));

The code above will instantiate an object called MyWater which is derived from 2 classes: XOxygen and XHydrogen. Both of the classes implement the GetName() method differently. The xout statements contain invocations to the two implementations of GetName(). The implementation that is executed is determined by the _executeclass statement. The result is that the output stream looks like this:

XOxygen name using _object and _executeclass = Oxygen
XHydrogen name using _object and _executeclass = Hydrogen