Last night I presented the Standard PHP Library at the PHP London User Group. The aim was to give an overview of the extension and to entice people into coming to TestFest, of which the London and Manchester incarnations will be focussing on SPL.
Thanks to all who attended! Here are the slides for those who couldn’t make it:
3 thoughts on “SPL Talk at PHP London”
Thanks for the great talk on the SPL class – Whats the point of the offsetGet function on the SPLFixedArray class? I benchmarked the  and the offsetGet function and found it to be 2.5x slower than accessing the array via .
SPLFixedArray implements the ArrayAccess interface, which provides the various offset*() methods.
When the engine encounters an indexed access (using the  notation) on an object, it will check to see whether that object implements ArrayAccess. If so, it will invoke the appropriate offset*() method. If not, you get an error like “Fatal error: Cannot use object of type C as array”.
In other words, it’s by implementing ArrayAccess that a class can provide custom behaviour when its instances are accessed with . Therefore, any class which does this must provide an implementation of the offset*() methods – SPLFixedArray included.
You performance observation is really interesting. My guess is that it highlights the overhead of PHP method lookup & invocation:
– When an indexed read () is encountered on an instance of a user-space class which implements ArrayAccess, the engine just looks up the offsetget() method and executes it. So there should be very little difference between reading with  and offsetget().
– However, extensions classes like SPLFixedArray (implemented in C) can bypass this behaviour. The  access can lead to a direct invocation of a C function which does the read – no need to lookup and invoke the PHP-space method… hence the performance improvement when using  instead of calling offsetGet() explicitly on an an SPLFixedArray.
For the details of how SPLFixedArray achieves this, see spl_fixedarray.c:
– In the class setup, we see that the standard read_dimension object handler (which would normally have done the slow lookup & invocation of offsetGet()) is replaced by spl_fixedarray_object_read_dimension.
– spl_fixedarray_object_read_dimension calls back into PHP-space only if we’re in a subclass of SPLFixedArray and offsetGet() has been overridden. Otherwise, it delegates to spl_fixedarray_object_read_dimension_helper. This is the fast path – no lookups, no call back into PHP-space.
I’m deducing this from looking at the code, so I may well be wrong… could be worth profiling to confirm. But method invocation is known to be quite expensive in PHP. I think there was some discussion on the internals list about improving this by caching invocation targets when the receiver type is sure not to change – I can’t find a reference right now but will let you know if I do.