Decided to put something together:https://github.com/joshbruce/external-project-proposals/blob/master/php-concepts/interact-with-instance-as-php.md
Hi Josh,
Reading through this, it seems to cover a few different concepts, which are certainly related, but not quite the same.
Firstly, we have interfaces such as Countable and Serializable, which don't make the object act like any particular primitive type, they just customise its interaction with particular functions. Iterators could potentially be included in that category, too, because it's fairly easy to imagine the language having multiple primitive types that can be iterated (e.g. separate "list" and "dictionary" types).
ArrayAccess feels more explicitly about making an object "act like" an array, but more precisely it overloads the [] operator - it doesn't allow the object to be used in other contexts where arrays are allowed. More general operator overloading was discussed recently, and the particular proposal put forward did not pass its RFC vote. [1]
__toString, on the other hand, only allows the object to be converted to a string, not act like one. You can't, for instance, influence the behaviour of the concatenation operator, and make "Hello" . $object . "!" return an object instead of a string, or a string that doesn't begin "Hello". An __toArray method was proposed recently, to mixed reaction. [2]
The other closely related topic is what is often discussed as "scalar methods" or "scalar objects" - the ability to call methods on non-object values, and possibly to define your own methods that can be called in this way. This would seem to fit your use case with Shoop quite well: rather than Shoop::array($array)->first()->unfold(), you would just call $array->first(). It's fairly high on a lot of people's wish lists, but there's a lot of details to get right in both design and implementation, so I strongly recommend searching for previous discussions and proofs of concept before diving in.
[1] https://wiki.php.net/rfc/userspace_operator_overloading
[2] https://externals.io/message/105589--
Rowan Tommins (né Collins)
[IMSoP]--
To unsubscribe, visit: https://www.php.net/unsub.php
All: Going to change threads now that I’m getting a better feel for the list environment and conventions, I think.
Someniatko: Saw the pipes RFC a while back and really appreciate. Think both could have their place and developed preference (switch and if-else, for example). Added reference to document. See link below.
Rowan: Thanks for the feedback and links!
PHP Internals is definitely not my wheelhouse and I find myself speaking mainly from the developer’s perspective because I don’t know enough to speak from the PHP perspective. Thanks for your patience there.
First takeaway is that I should drastically reduce scope and cut-short the background, lay of the land, sales pitch language I’ve seen in other RFCs and concepts.
Second, I should consider the audience more. Most of the people on this list probably (read most definitely) know more about this than I do (or ever will) and y’all don’t need long-winded explanations and background (could be wrong). So, thinking less text, more code.
Finally, as I see more of the landscape and given conversations are low-bandwidth (long form, text-only), trying to cover more than one thing would most likely distract at best and block at worst.
So, gonna go after defining a boolean return value for a class. (At least for now.)
Updated: https://bit.ly/php-0001
Thank you again for the feedback and links.
Cheers,
Josh
ps. The ability to call methods on non-object values is interesting and could definitely be helpful for Shoop. The main frustration for me when using Shoop is the inability to just drop the pointer into a condition and have it work. :)
pps. The operator overloading feels like Swift…nice feature...that would definitely be helpful. While it doesn’t do the array thing itself, I would be able to implement ArrayAccess and Iterator on it, yeah? At which point it could feel like an array (if I skimmed properly) - throw in __toString and we have the Pym primitive. :)