core: Support lazy initialisation of properties
Creating several HashSets and HashMultiMaps for every Individual turns
out to be quite wasteful, especially when most of them will typically be
empty (as address books are generally quite sparse on properties) and never
accessed (since most clients don’t need local IDs or web service addresses).
This commit delays initialisation of various multi-valued Individual
properties to the first time they’re accessed, giving them a null value
before that time. It preserves the existing API for Individual, i.e. the
properties themselves remain non-nullable, and only the object members
backing them become nullable.
This does introduce a slight behaviour change, in that an Individual will
now emit change notifications for a non-initialised multi-valued property if
*any* of the Personas in the Individual emit a notification for that
property. This is because the Individual can’t compare the current value of
its property to the new one resulting from the change in the Persona’s
property value to determine if a change has really occurred. Therefore the
Individual makes a safe over-estimate and emits notifications which might
be false positives.
This shouldn’t be a problem: if a client is interested in the property,
they will have already queried it and caused it to be initialised.
Initialised properties have the same notification behaviour as before.
If a client isn’t interested in the property, it won’t be connected to the
property notifications anyway.
This change roughly quarters the number of GObjects being created when
opening folks-inspect with the Telepathy, key-file and EDS backends enabled
and ~115 personas in the system.