Easy Reference Comparison of Objects & Collections

Objects have become an essential part of the 4D language and of Qodly.

But when you declare a variable of this type, you define a reference. So, how do you know if two objects are, in fact, just one and share the same reference?

Starting with 4D 20 R6, comparing object references is simple: enter the = and # operators!

This blog post explores these operators and how they help determine if objects share the same reference. Let’s find out more!

Equal, different…

When talking about objects, it is essential to distinguish between their content and their reference. The comparison using equal (=) and not equal (#), as well as other possibilities like searching and counting in arrays, etc., concerns references.

The same applies to collections. When a collection is declared as a variable, it is actually a reference that is declared. The examples below will help to clarify this.

Ex1: Two objects are declared and share the same reference.
var $o1; $o2 : Object
$o1:={a: 1}
$o2:=$o1  // Same reference, $o2 is NOT a copy of $o1

$result:=($o1=$o2)  // True
$result:=($o1#$o2)  // False
Ex2: Two collections are declared and share the same reference.
var $c1; $c2 : Collection
$c1:=["a"]
$c2:=$c1   // Same reference, $c2 is NOT a copy of $c1

$result:=($c1=$c2)  // True
$result:=($c1#$c2)  // False
Ex3: This time, two objects and two collections have the same content. In both cases, they are two distinct objects and two distinct collections!
$o1:={a: 1}
$o2={a: 1}
$result:=($o1=$o2)  // False (objects are distinct!)
$result:=($o1#$o2)  // True

$c1:=["a"]
$c2:=["a"]
$result:=($c1=$c2)  // False (collections are distinct!)
$result:=($c1#$c2)  // True

Arrays and array functions

Find in array and Count in array.

Until now, functions such as Find in array and Count in array could not be used with arrays of objects. Now they can!

$o1:={a: 1}
$objects{20}:=$o1
$position:=Find in array($objects; $o1)  // returns20 !
$o1:={a: 1}
$objects{10}:=$o1
$objects{20}:=$o1
$objects{30}:=$o1

$count:=Count in array($objects; $o1) // -> Returns 3

Sort array, find in sorted array and multisort array

If your object arrays contain many elements and these are sorted, the Find in sorted array command will be much faster than Find in the array. That’s why we’ve also improved the SORT ARRAY command so that it can also sort objects! The sort order is a purely technical internal order, but it is essential to allow the complementary Find in sorted array command to be used later.

Objects and collections inside collections

The query() function can also be used to search for object or collection references… within a collection!

The code examples below are now valid.

For example, an object inside a collection

$o1:={a: 1}
$c1:=[{o: $o1}]
$c2:=$c1.query("o = :v"; {parameters: {v: $o1}})

Example with a collection inside a collection

$col1:=[1; 2; 3]
$c1:=[{c: $col1}]
$c2:=$c1.query("c = :v"; {parameters: {v: $col1}})

Entities and entity selections

According to ORDA principles, the same applies to entities and entity selections. Even if one entity references a database element, another entity referencing the same element will still be different (not equal).

$e1:=ds.Table.all().first()
$e2:=$e1
$result:=($e1=$e2) // True

$e1:=ds.Table.all().first()
$e2:=ds.Table.all().first()
$result:=($e1=$e2) // False

The same applies to two entity selections. This one might be easier to understand. In the second case, in the time laps between $es1 and $es2 are created, the content of the table might have changed. But even if it’s not the case, $es1 and $es2 will always be distinct entity selections!

$es1:=ds.T1.all()
$es2:=$es1
$result:=($es1=$es2) // True

$es1:=ds.T1.all()
$es2:=ds.T1.all()
$result:=($es1=$es2) // False

Conclusion

You now have the same possibilities for comparing and searching for objects as you had with strings, numbers, dates, and times. We hope these changes to conform with the other variable types will make your development easier.

Don’t hesitate to let us know what you think on the forum!

Roland Lannuzel
• Product Owner & 4D Expert •After studying electronics, Roland went into industrial IT as a developer and consultant, building solutions for customers with a variety of databases and technologies. In the late 80’s he fell in love with 4D and has used it in writing business applications that include accounting, billing and email systems.Eventually joining the company in 1997, Roland’s valuable contributions include designing specifications, testing tools, demos as well as training and speaking to the 4D community at many conferences. He continues to actively shape the future of 4D by defining new features and database development tools.