get_mangled_object_vars()

Here is an implementation detail that you may or may not have wanted to know: how does PHP internally distinguish the private, protected, and public properties of an object from each other? The answer is: PHP does it using so-called name mangling.

For internal representation and storage, the name of a private property is prefixed with \0<C>\0 where \0 is the null byte and <C> is the name of the class that declares the private property. The name of a protected property is prefixed with \0*\0 and the name of a public property is not modified.

The new get_mangled_object_vars() function provides access to these mangled properties of an object:

class ParentClass
{
    public int $publicPropertyDeclaredInParentClass = 1;
    protected int $protectedPropertyDeclaredInParentClass = 2;
    private int $privatePropertyDeclaredInParentClass = 3;
}

class ChildClass extends ParentClass {
    public int $publicPropertyDeclaredInChildClass = 4;
    protected int $protectedPropertyDeclaredInChildClass = 5;
    private int $privatePropertyDeclaredInChildClass = 6;
}

$o = new ChildClass;

$o->dynamicProperty = 7;
$o->{'8'} = 8;


var_export(get_mangled_object_vars($o));

Executing the code shown above will print the output shown below:

array (
  'publicPropertyDeclaredInChildClass' => 4,
  '' . "\0" . '*' . "\0" . 'protectedPropertyDeclaredInChildClass' => 5,
  '' . "\0" . 'ChildClass' . "\0" . 'privatePropertyDeclaredInChildClass' => 6,
  'publicPropertyDeclaredInParentClass' => 1,
  '' . "\0" . '*' . "\0" . 'protectedPropertyDeclaredInParentClass' => 2,
  '' . "\0" . 'ParentClass' . "\0" . 'privatePropertyDeclaredInParentClass' => 3,
  'dynamicProperty' => 7,
  8 => 8,
)

Before the get_mangled_object_vars() function existed, accessing these mangled properties was only possible by casting the object to array using the (array) cast operator. This, however, was problematic when the object in question was created based on a class either provided by PHP itself or by a PHP extension and overloaded the array-case object handler. The ArrayObject class is a good example for such a problematic case. These problems can now be avoided by using get_mangled_object_vars().