When creating an object method that overloads one of IDL’s standard operators, you might want to return an object instance that replaces the value on the left-hand side of the equals sign. In this situation, you have two options for coding your method: creating and returning a new object instance, or modifying the original object instance and returning it.

Approach 1: Create a New Object Instance


For example, if you have overloaded the “+” operator, you might choose to return a new object instance when the operator is called like this:

newVariable = myObject + value

This is relatively straightforward; your _overloadPlus method would create a new object instance that contains the correct member data and return the object reference. The code might look something like this:

FUNCTION myClass::_overloadPlus, Left, Right
 
   Left->GetProperty, DATAVALUE=value
   newValue = value + Right
   newObject = OBJ_NEW('myClass')
   newObject->SetProperty, DATAVALUE=newValue
 
RETURN, newObject

In practice, you might want your method to be more robust about checking the data types of the Left and Right variables and behaving appropriately; your method might also modify the other member data values in the returned object. The basic idea, however, is simple: your method creates a new object instance and returns the reference.

Notice that with this approach, any additional references to a modified object instance remain unchanged when the same object appears on both sides of the equals sign. For example, if you were to create two references to the same object instance:

myObject1 = OBJ_NEW('myClass')
myObject2 = myObject1

and then modify one of the references by including it on both sides of the equals sign:

myObject1 = myObject1 + 3

the original myObject1 reference would be lost (since the _overloadPlus method returns a new object instance), but the myObject2 reference would still contain the original value. (That is, myObject1 and myObject2 are no longer references to the same object instance.)

Approach 2: Modify the Original Object Instance


The result of an assignment statement like the one shown above is not always a new variable; however, the variable to the left of the equals sign can also appear to the right of the equals sign. For example, you might want your overloaded “+” operator to handle the following:

myObject = myObject + 3

by adding three to the value of a property of the existing object rather than creating a new object instance. Note that the above statement can also be written as:

myObject += 3

Code for this scenario might look something like this:

FUNCTION myClass::_overloadPlus, Left, Right
 
   self->GetProperty, DATAVALUE=value
   newValue = value + Right
   self->SetProperty, DATAVALUE=newValue
 
RETURN, self

In this example, we modify the value of myObject directly (using the method’s implicit self argument) rather than creating a new object instance. This technique avoids the overhead of creating and populating a new object instance, at the cost of losing the original data value of myObject.

Notice that with this approach, any additional references to the modified object instance are also modified when the same object appears on both sides of the equals sign. For example, if you were to create two references to the same object instance:

myObject1 = OBJ_NEW('myClass')
myObject2 = myObject1

and then modify one of the references by including it on both sides of the equals sign:

myObject1 = myObject1 + 3

the original myObject1 reference would contain the new data value, and the data value of the myObject2 reference would change as well. (That is, myObject1 and myObject2 are still references to the same object instance.)

Choosing an Approach


Creating and returning a new object instance, or modifying the value of an existing object instance can be considered the correct approach under certain circumstances. Neither approach is perfectly general, however. The trade-offs are as follows:

  • If your method creates and returns a new object instance, it will preserve the value of the original object instance, but can lose the reference to the original object if it appears on both sides of the equals sign. Creating a new object instance also requires that your method create the correct type of object and populate its member data appropriately; this task may be complex or computationally expensive.
  • If your method modifies the original object instance and returns it, all references to the original object will remain valid, and you avoid the overhead of creating a new object. Choosing this approach means that the original data values within your object will be lost, however, and may cause unexpected behavior when the original object does not appear on both sides of the equals sign.

Note: The problem of losing the reference to an object is mitigated if Automatic Garbage Collection is enabled, as it is by default.

The following table summarizes the advantages and disadvantages of each approach.

Approach

Advantages

Disadvantages

Create and return a new object instance

Does not modify value of original object

Returns a new object instance

Can lose the reference to the original object

Requires creation of a new object instance

Modify the self object reference and return it

Does not require creation of a new object instance

Preserves references to the original object

No way to store the value of the operation in a new object instance

Loses the data values within the original object

If you are familiar with the context in which your overloaded operator method will be used, you can make an informed decision about which approach suits the situation best. In more general cases (or if you don’t know how the overloaded operator will be used) it is safest to return a new object instance from your overloaded operator method.