--disable-experimental-aggregate and --disable-experimental-overload? Just in case we really want to make it optional and have new way for overloading/multiple inheritance. We can document these features as EXPETIMENTAL as long as we want, right?
-- Yasuo Ohgaki Kristian Koehntopp wrote: > I have several observations regarding the newly implemented > aggregate() und overload() extensions. Depending on the > correctness of these observations you may want to reconsider the > inclusion of these extensions in the current build of PHP. > > The following has not in its entirety verified in the source and > may be incorrect or incomplete. Please correct me. > > Situation: > > $obj = new Origclass; aggregate($obj, "Classname"); is a > function which adds all instance variables and methods from > class Classname to an object $obj of an original class > Origclass. There are variations of aggregate which allow you to > add instance variables and methods selectively by enumeration > and regex. > > Observation: > > aggreate and friends break the introspection in PHP, and may > interfere with serialization and sessions. This is, because > get_class($obj) returns Origclass, and no trace of Classname. > Also, $obj is_a() Origclass, but not is_a(Classname), leading to > serialization of $obj as a pure Origclass, and reinstantiation > as a pure Origclass with no methods from Classname at all. > > This is the situation of serialize() in PHP 3 at a slightly > elevated level. Reminder: In PHP 3, serialize() did not record > the class of an object on serialization, and unserialize() > consequently produced an object with no methods at all, which is > in fact quite useless. > > Also, because of the fine grained nature of the more advanced > variations of aggregate, there is no fast way to describe the > class or type of an object instance. The only way to completely > describe an object is to completely enumerate its instance > variables and instance methods. Essentially, get_class and > friends become meaningless. > > Alternative: > > aggregate is a badly designed way to introduce multiple > inheritance like functionality. There are at least two tested > ways to implement MI functionality. Statically typed languages > such as C++ set type == class and implement pure MI. Regarding > PHP, this would lead to > > class C extends A, B { ... } > > with the order of A and B being important. Also, > get_parent_class() would need to be modified to return > inheritance level information or inheritance graph information > together with class names in order to produce meaningful > information. Something like > > $v = get_parent_class($complicated_object); > > $v would be > > array("A" => "B", "B" => "C", "B" => "D"); > > for > > class A extends B ... > > class B extends C, D ... > > An alternative, possibly cleaner way would be the introduction > of interfaces and categories. In this scenario we keep single > inheritance. We introduce declarations of interfaces, which may > contain a number of instance variables and functions. Interfaces > are a simple declaration of these, there is no implementation at > all in an interface. > > A class may claim conformity with an interface. This means that > the class at least has all the instance variables the interface > demands and has at least implementations for all member > functions of the interface. The class may implement all this > independently or it may import a category. > > A category is class-subset, and always an implementation of an > interface (you cannot define a category for which no interface > definition is being known). > > Interfaces and Categories are found in some dynamically typed > languages, sometimes under slightly different names. They > separate type and class, and in order for them to function in > PHP we would need enumerative functions and predicates to > complement the new language constructs (get_defined_interfaces(), > get_defined_categories(), conforms_to($interface_name)). > > Recommendation: > > As-is aggregate() is a broken design, and will break existing > older functionality. It will create a number of support issues, > and later backward compatibility issues. It may inspire even > more broken "fixes" for these issues, effectively uglifying the > language itself or at least its object system. > > The best would be to remove aggregate() completely, and bury it. > It should be replaced by a proper MI system, probably one for a > dynamically typed language, as PHP is such a language. > > If aggregate() functionality is being used right now, and is > critical, it should be kept, properly documented, the drawbacks > spelled out in all its ugliness and its use strongly > discouraged. It should be clearly marked as obsolete from day 1, > and may be removed at any time. If someone uses this feature > despite the warning labels, this person deserves everything that > happens. > > > > Situation: > > The overload() extension allows userland code to intercept get, > set and call operations on the instance variables and instance > functions of an object. It does this by defining the special > fixed name functions __get, __set and __call in a class, which > are enabled by calling overload() on this class. > > It also allows, according to Sebastian Bergmann, and in spite of > the current documentation at > http://www.php.net/ref.overload.php, __get_x(), __set_y() and > __call_x() functions in order to intercept accesses and calls to > instance variable x and method y respectively. > > I haven't verified this in source, but Sebastian claims it > works. > > Observation: > > If this is NOT the case, I have no issue with overload(). It is > dangoerous, but it is an expert feature and the design is okay. > > If overload() allows for __get_x(), though, this is bad design. > The reason for this is that we get namespace pollution and, > again (*), automatically called callback functions with a > variable name. There will interoperate badly with inheritance, > with dynamically created, undeclared instance variables and with > aggregate(). > > Recommendation: > > If overload() indeed supports variably named callback functions > such as __get_x(), support for this should be removed in order > to avoid a number of possible inconsistencies and namespace > pollution. > > > End Rant, fire away... > > Kristian > > (*) We had them with PHP 3 constructor names, which were an > extremely bad idea in the first place. -- PHP Development Mailing List <http://www.php.net/> To unsubscribe, visit: http://www.php.net/unsub.php