Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 5 December 2010 16:47, presid...@basnetworks.net wrote: If I have an object called PiggyBank, with the property dollars set to 5, dimes set to 4 and nickles set to 1, then I get the contents of the property Total, I can predict it will give me the value 5.45. That is what properties are really for. To me, the balance on my piggy bank is a readonly, dynamic attribute/property. OK. Piggy bank is too small an entity. My kids' piggy banks have only 1 user per bank. The balance changes rarely 'cause they don't do a lot of housework. Yet. But for a larger entity, something with many people altering data via an instrument of change (a term I got from Sage Accounting a long time ago), then the balance on an account will change in unknown ways. And a synthetic property like AvailableBalance will certainly look like a random value, whilst orders are taken during the day and invoices raised and payments allocated. All in real time. A real world process. What I'm confused by is what you would consider a property? Why does predictability matter? Not all properties of an entity are predictable. My kids have an attribute of mood. They sure as hell aren't predictable. If you have a clock object, the time is a readonly, dynamic property/attribute of a clock. Makes sense? You would want $clock-time as a property. Not $clock-getTime(). Well. OK. You _COULD_ and it would solve all the issues you have with dynamic, readonlys, but time is a property. What would you expect to be the natural behaviour of unset($clock-time); ? If I have to call getTime(), then I've just got setters/getters (__magic will do). Suddenly time is no longer a property of a clock. I can see we have very different opinions about the implementation and the possible use of properties. I'm quite happy with that. Either way, I think the basic proposal is very good. I've always wanted setters/getters in PHP specifically to implement readonly/writeonly attributes when I went from Delphi to PHP. The concept of grouping these together into a property (like C#), rather than having actual set and get methods (like Delphi) certainly does keep things together. I think being able to call the getter/setter as part of fluid interface would be useful. For each property, there would be getxxx, set, isset, unset. That may look useful and I think for those that build classes like ORM systems, then probably of no issue and would be a major feature. But maybe too much for others not using that level of technology. As you can see, I'm not happy with having to keep with a method to update what I would consider a property (semantics and all that). I'm not happy with isset() calling the getter. But I'll adapt. I don't have the core knowledge or experience to argue much beyond what I've already said. The only thing I can think of though is __get can return a seemingly random value for an undefined property. In keeping with that, why couldn't a real property? In PHP's terms (not C#), what's the difference? Richard. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 5 December 2010 16:47, presid...@basnetworks.net wrote: If I have an object called PiggyBank, with the property dollars set to 5, dimes set to 4 and nickles set to 1, then I get the contents of the property Total, I can predict it will give me the value 5.45. Â That is what properties are really for. To me, the balance on my piggy bank is a readonly, dynamic attribute/property. OK. Piggy bank is too small an entity. My kids' piggy banks have only 1 user per bank. The balance changes rarely 'cause they don't do a lot of housework. Yet. But for a larger entity, something with many people altering data via an instrument of change (a term I got from Sage Accounting a long time ago), then the balance on an account will change in unknown ways. Sure, the balance is updated all the time in the database or whatever external data source it is stored in. But you are only loading from that database a single time in a page load. If you are loading it more than once, as per the C# guidelines, you should be doing it in a method, in order to signify that it is a resource intensive operation (makes a call to the data store every time its accessed... that is too intensive for a property, at least as agreed by the C# folks). Besides, this is not a common scenario. For the most part, if people are loading from a datastore, they will only load the data once per page, then cache it within the object instance. What I'm confused by is what you would consider a property? Why does predictability matter? Not all properties of an entity are predictable. My kids have an attribute of mood. They sure as hell aren't predictable. If you have a clock object, the time is a readonly, dynamic property/attribute of a clock. Makes sense? You would want $clock-time as a property. Not $clock-getTime(). Well. OK. You _COULD_ and it would solve all the issues you have with dynamic, readonlys, but time is a property. Yes, you would want it as a property. It is very predictable, as it gives you the current time of the clock. Lets say you call $clock-addHours(1), when you call $clock-time, you can expect it to be an hour further forward. If the clock is currently running, you can expect it to be one second higher for every second that passes. If $clock-time is being loaded from a datastore once per second where it could get modified, that is not predictable. Instead you should have $clock-syncTimeFromDataStore() or some such. Once you call that method, you know $clock-time is going to be modified. What would you expect to be the natural behaviour of unset($clock-time);? I would guess that it just would not do anything. Either that or throw a non-fatal error. The user would have to know that the property is readonly, which they can do by looking at the documentation or the class definition. I think you mention this in the interest of the interchangeability of properties and variables. I suppose we cannot have full 100% interchangeability if we still want separate visibility levels (public,protected,private) on the get/set, and the possibility of readonly/writeonly. I think that the interchangeability of the two would be like so: - A property can always be replaced with a variable, even if the new property has separate visibility levels (or final, abstract) on its get and set methods, and will continue to work. - A variable can be replaced by a property and be guaranteed to work as long as the new property does not have separate visibility levels (or final, abstract) on its get and set methods. I can see we have very different opinions about the implementation and the possible use of properties. I'm quite happy with that. Either way, I think the basic proposal is very good. I've always wanted setters/getters in PHP specifically to implement readonly/writeonly attributes when I went from Delphi to PHP. The concept of grouping these together into a property (like C#), rather than having actual set and get methods (like Delphi) certainly does keep things together. I think being able to call the getter/setter as part of fluid interface would be useful. For each property, there would be getxxx, set, isset, unset. That may look useful and I think for those that build classes like ORM systems, then probably of no issue and would be a major feature. But maybe too much for others not using that level of technology. As you can see, I'm not happy with having to keep with a method to update what I would consider a property (semantics and all that). I'm not happy with isset() calling the getter. But I'll adapt. I don't have the core knowledge or experience to argue much beyond what I've already said. The only thing I can think of though is __get can return a seemingly random value for an undefined property. In keeping with that, why couldn't a real property? In PHP's terms (not C#), what's the difference? A property certainly could return a random value, and it is
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
The original purpose being, specifically, smarter class members, correct? (The internal syntax to define them we can bikeshed later; determining the external syntax and semantics has to come first.) Well when saying original purpose I was referring to exactly this: The basic Idea of a property, is making a getFoo() / setFoo($value) pair of methods look and act like a variable from the outside, and have an easily identifiable and simple to use syntax on the inside. But I suppose you could just boil that down to smarter class members ;) - Dennis Well, there's a very subtle difference in those two statements. :-) That's what I'm saying. If the goal of properties is to allow a developer to bind arbitrarily complex behavior to what would otherwise look like a class member, that's fine and useful and I support it. But there are, technically, multiple very different ways that could be implemented. An inline set of get/set methods is one way. Creating a property as a reuable free-standing entity alongside traits and classes would also accomplish that goal. Creating a free-standing super-variable dojobby would work, too. Technically __get/__set also accomplish that goal now (although in a sub-optimal way). I'm trying to draw a very clear line between the syntactic interface and goal, and the implementation. That's important for us to keep the design clean. And I think I'm done harping on this point now, I hope... :-) Ah, I see. In that case, to use your words, I would say An inline set of get/set methods was my intention. This also leaves open the door to allow properties to be added to a trait definition which will also support re-usability. The supervariable thing I am not too keen on though. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
In a multi-user system, any of these values could be different from one moment to the next. class Account{ public property $AvailableBalance{ get{ return $this-CreditLimit - ($this-AccountBalance - $this-OnOrder); } } } This hides the mechanics away and tells any user that the account for this order has a realtime $CreditLimit, $AccountBalance, $OnOrder and an accurate $AvailableBalance. At the beginning and end of the order entry and maybe as each line is being entered, the AvailableBalance is accessed to see if it the current order can be met financially. The Account's properties are all read-only in this scenario (I'd have 2 Account classes, one for the Sales Ledger and a subclass for everywhere else. The ability to essentially remove the setter() in a subclass would turn a read/write property into a readonly property). So, based upon this fairly simple scenario, isset() would clearly alter the value of the account's properties if it had to call the getter()s. I am not sure I follow, your example is complex to read and understand. Loading the value of a property from a cache, or from a DB is fine, although I see no benefit of doing it multiple times in the same page load. Besides, I think you mis-interpreted what I was saying. Please read again: The major issue I see here, is that a property should not be generating a value in an unpredictable way. In the example above, you indicate that the value could change just by calling the get method. While it is possible to write a property that does such a thing, this is completely incorrect and should not be actively supported by the language in any way. The value of a property (as viewed from the outside of the class) should never, ever change solely by a call to a getter method. Specifically the part a property should not be generating a value in an unpredictable way. is what I was talking about. I think you took things I wrote after that out of context. Changing the value that comes out a property dynamically is fine, that is what they are for, however, it should be predictable. A random value is not predictable, and should not be in a getter. If I have an object called PiggyBank, with the property dollars set to 5, dimes set to 4 and nickles set to 1, then I get the contents of the property Total, I can predict it will give me the value 5.45. That is what properties are really for. If you are loading a value from a database several times on the same page load, it could be modified by some other process, and therefore that is not very predictable. That should likely be a regular method (CheckDBValue() or some such). You say While it is possible to write a property that does such a thing, this is completely incorrect and should not be actively supported by the language in any way.. How are you going to stop me from writing code that DOES generate a new and appropriate value in response to a getter() request. First, as noted above, this was taken out of context. Secondly, I never said it should be prevented, but rather not supported. Those are very different concepts. Surely that's the exact job of a getter()? To generate and supply a potentially new and accurate value. Not to supply some pre-hashed value which is accessible via __get() or by directly accessing a public variable (as seen in the EmployeeRecord on the MSDN link you gave - completely pointless). Yes, that is one of the many jobs as a getter. Just for the record, passing a value purely through a property without changing it is far from pointless. First of all, it allows you to independently create get or set methods, creating implicit readonly or writeonly properties. By defining a property you can also set each get/set methods visibility separately, or set either one final or abstract. In the case of creating a property that does not do any of this special functionality, and just passes through a value, there are still arguments for it. For one, it creates code uniformity. If 90% of the rest of a classes public members are properties, then converting the last few public variables to properties makes sense and is easier to read. Additionally, if you define all public members as properties right off the bat, it is easy to add additional functionality and validation checks as you go, instead of stopping to convert the member to a property. These scenarios are definitely supported in C#. For example, in more recent versions of C#, you can now create a property like this: public string MyString { get; set } That right there, when compiled, is the exact same thing as this: public class MyClass { private string someString; public string MyString { get { return someString; } set { someString = value; } } } So as you can see, this scenario is heavily supported in C#, and is considered good practice. Creating all public members as properties gives you the most flexibility when
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Its a defacto standard. Of course there is nothing stopping PHP from implementing properties that way, but by going against the standard set by the rest of the industry, it is very confusing for programmers coming from other languages to learn PHP. A good example is how == works differently in PHP than in other languages. In PHP, === works like == does everywhere else. (string)'0' == (int)0, for example is true in PHP, but false in most other languages. I have had countless conversations with PHP developers who claim the language is broken, because == does not work like they expect it to, after which I have to explain === to them. This is because PHP goes against the defacto standard. Maybe it would have been better if == and === had the opposite meaning, as to not squash the standard? You have got me there. = is assign == is equal value === is equal type and value At least on all the languages I've been using recently ... where is this a problem? In any language that does not have === it is like this: = is assign == is equal type and value That is where the confusion comes from. People do not expect 0 and 0 to be equal, because they are different types. javascript and C++ both do implicit type conversion (coercion) the same as PHP. You will have to prove that this is NOT the norm. There was a big debate a long time back on stopping implicit type conversion in C++ ... it did not get anywhere. What I am probably asking simply because I don't know is what language are you referring to as I've not come across any. If it's C# then that would explain it ... THAT was created by people who did not accept the consensus agreement in C/C++ ;) Ah well you are right about implicit type conversion... that DOES exist in C#, but its not the same as how it works in PHP AFAIK. I am fairly certain that 0 == 0 in C/C++/C# would always be false, or am I incorrect? 0.0 == 0 in C# DOES return true, for the record, I suppose I forgot about that. Sorry. My brain is on overload right now :) - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
How does one get a reference to a property, if a property is just a collection of methods with fancy behavior? That makes properties a first class entity, which is an entirely different bit of brain bending. Its the same concept as having a reference to a function, where you can invoke the reference and it invokes the function. I say that as a programming concept, not a PHP concept, because I am a bit fuzzy in the function reference department of PHP. I don't believe PHP has function references per se. It has the ability to call functions dynamically by either: $function = 'foo'; $function(); // or call_user_func[_array]('foo'); (The former is faster so preferred if you have a fixed number of variables.) Right, that is what I thought. Functions are not first-class entities in PHP the way they are in, say, Javascript so you can't pass them around, nor do you have function pointers as you do in C. (My god those are a nightmare to code...) PHP 5.3 introduced anonymous functions/closures, which seem at first blush to be sort of like that. However, I believe the internal implementation is done using objects and you can mimic that behavior on an object using an interface, so really functions still don't have a first-class status but are emulated using objects. (I'm sure one of the compiler people can correct me if that's not entirely accurate.) Ah that is interesting then. So is the solution then to make the set method return by reference? Or does that just create more problems? I'm not sure. I'm just pointing out that behaves like class members is a substantially more complex scenario than it seems at first blush, and we need to think through the implications of that and just how closely we can emulate properties. I completely agree. The basic Idea of a property, is making a getFoo() / setFoo($value) pair of methods look and act like a variable from the outside, and have an easily identifiable and simple to use syntax on the inside. The reason I originally focused so much around methods, is because properties literally are a pair of methods in C# (thats what they are compiled into). But PHP is another beast, and the challenges are different. As long as the original purpose of properties is not loss, whatever way we figure out is best to implement them is fine with me. The original purpose being, specifically, smarter class members, correct? (The internal syntax to define them we can bikeshed later; determining the external syntax and semantics has to come first.) Well when saying original purpose I was referring to exactly this: The basic Idea of a property, is making a getFoo() / setFoo($value) pair of methods look and act like a variable from the outside, and have an easily identifiable and simple to use syntax on the inside. But I suppose you could just boil that down to smarter class members ;) - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Chad, Having thought a bit about this, there are a couple of initial problems I see, and, more importantly, I'm not convinced that the stated problem (encapsulation) requires the addition of a new language construct (i.e. a property as distinct from a class member). In fact, I think it is better implemented in another way (see below). First of all from a confusion point of view, PHP already has defined property in a way that opposes your RFC's definition: property_exists() checks for the existence of what you call a class member. So, at least, it seems to me you would have to find new terminology if you wanted to pursue this avenue of a new construct. In my opinion, however, there should not be a new construct, and property and class member should remain interchangeable descriptions of the same class construct. I think we can do this and still fix the encapsulation problem. (Note: this is a long e-mail, and probably best represented in a new RFC. I have also written this up more completely in the form of an RFC, but I don't want to clutter up the wiki's RFC page unless other people like this idea as well, so I'll add the RFC if it looks like it will be useful). For example, we could do: class Time { protected $time; // note that $seconds, $minutes, and $hours are, in this // implementation, dummies, since they will never hold // a value, because their set functions only set the $time // class member. public $seconds; public $minutes; public $hours; public function issetTime($name) isset($hours,$minutes,$seconds) { return isset($this-time); } public function unsetTime($name) unset($hours,$minutes,$seconds) { unset($this-time); } public function setTime($name, $value) set($hours,$minutes,$seconds) { switch($name) { case 'hours': $this-time = $value * 3600; break; case 'minutes': $this-time = $value * 60; break; case 'seconds': $this-time = $value; break; } $this-seconds = $seconds; } public function getTime($name) get($hours,$minutes,$seconds) { switch($name) { case 'hours': return $this-time / 3600; break; case 'minutes': return $this-time / 60; break; case 'seconds': return $this-time; break; } } } with this syntax, you could group the properties like above or, if you preferred, you could have a different function for each property. for read only (similar for write only), including the possibility of asymmetry: class Time { protected $time; public $seconds; public $minutes; public $hours; // ... // now Time::$hours can only be set from inside the class / descendents protected function setHours($name, $value) set($hours) { $this-time = $value * 3600; } // but Time::$hours can still be retrieved from outside the class public function getHours($name) get($hours) { return $this-time / 3600; } } for interfaces: interface TimeClass { public function setHours($name, $value) set($hours); } This has a number of benefits: 1. This acts like PHP, and also brings along features out of the box (a) The new syntax mimics the form of the syntax of closures ($x = function() use($a, $b) { // ... };), so it is somewhat familiar. (b) The arguments of the isset, unset, getters and setters is analogous to that in the __get and __set methods, so userland implementation will be familiar. (c) The getters and setters are still regular class methods, so they can be called as methods as usual (subject to visibility, of course) (d) Adds shades to the read-only and write-only concepts via visibility modifiers! (e) Isset / unset make sense now! E.g. that when unsetting $hours, we actually want to unset the time in general. In fact, this is preferred, because in the examples we've been looking at, the magic is in grouping the three class members (seconds, minutes, hours), and this implementation of isset and unset allow you to do just that grouping, without having to write 3 isset and 3 unset functions, as you would have to in the property definition. (f) This allows for much more compact class definitions, as you don't have to define getHours(), getMinutes(), getSeconds() individually if you don't want to (although it allows you the flexibility to do that if it's what you want). (g) Inheritance works out of the box. (h) Final keyword works out of the box. (i) Documentation works out of the box (just do it as you do it now, on the class members and the methods). (j) Interfaces work. (k) In the example above, the class could go ahead and set the Time::$time class member directly
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Dennis 2010/12/5 presid...@basnetworks.net: Interesting. So you are saying that once a word is a keyword in PHP, it cannot be used as a name, anywhere? So for example, you are saying I cannot create a variable called $function? If that is the case, that is extremely odd. I would expect that get/set could be keywords when used in the right location (inside a property definition, but outside of the property body), but anywhere else they should be able to be used as a regular name... Is there some way that could be possible? A keyword in PHP means that it cannot be used as a name for something like a class/method/function etc. but of course still allowed in variable and constants (defined using define() -- not const as its compile time). class global { } /* fatal error */ function default() { } /* fatal error */ -- regards, Kalle Sommer Nielsen ka...@php.net -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Sunday, December 05, 2010 11:07:49 am presid...@basnetworks.net wrote: The original purpose being, specifically, smarter class members, correct? (The internal syntax to define them we can bikeshed later; determining the external syntax and semantics has to come first.) Well when saying original purpose I was referring to exactly this: The basic Idea of a property, is making a getFoo() / setFoo($value) pair of methods look and act like a variable from the outside, and have an easily identifiable and simple to use syntax on the inside. But I suppose you could just boil that down to smarter class members ;) - Dennis Well, there's a very subtle difference in those two statements. :-) That's what I'm saying. If the goal of properties is to allow a developer to bind arbitrarily complex behavior to what would otherwise look like a class member, that's fine and useful and I support it. But there are, technically, multiple very different ways that could be implemented. An inline set of get/set methods is one way. Creating a property as a reuable free-standing entity alongside traits and classes would also accomplish that goal. Creating a free-standing super-variable dojobby would work, too. Technically __get/__set also accomplish that goal now (although in a sub-optimal way). I'm trying to draw a very clear line between the syntactic interface and goal, and the implementation. That's important for us to keep the design clean. And I think I'm done harping on this point now, I hope... :-) --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Interesting. So you are saying that once a word is a keyword in PHP, it cannot be used as a name, anywhere? So for example, you are saying I cannot create a variable called $function? If that is the case, that is extremely odd. I would expect that get/set could be keywords when used in the right location (inside a property definition, but outside of the property body), but anywhere else they should be able to be used as a regular name... Is there some way that could be possible? A keyword in PHP means that it cannot be used as a name for something like a class/method/function etc. but of course still allowed in variable and constants (defined using define() -- not const as its compile time). class global { } /* fatal error */ function default() { } /* fatal error */ Thanks for explaining that Kalle. I believe there is a way around this. You mentioned using type-hinting syntax in an earlier email: You might also want to note in the RFC that get and set (which are very commonly used in userland code) will become keywords, unless you wish to take the same approach as with the current type hinting syntax we have in php-trunk that only makes type names have a meaning if they are in a prototype. Could this easily be used (and would it make sense to use them) in this situation? I think the best solution is for get/set to be keywords, but only in the context of a property definition. Will this accomplish the task? - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Dennis 2010/12/6 presid...@basnetworks.net: Could this easily be used (and would it make sense to use them) in this situation? I think the best solution is for get/set to be keywords, but only in the context of a property definition. Will this accomplish the task? I'm sure it can be done, but I'm not sure how good it would be and if it requires hacks to the parser. Someone with more in-depth knowledge of ZE might be able to answer this ;-) -- regards, Kalle Sommer Nielsen ka...@php.net -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
RE: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Thu Dec 2 02:11 AM, Larry Garfield wrote: See, here's the fundamental problem we're running into. There's three different definitions of what a property is that we keep bouncing between, each of which will dictate both syntax and semantics: 1) Properties are a smart masking layer over class members, like a smarter __get/__set, designed to make it possible to swap out in place of class members at will. In this case, both the syntax and semantics of properties should mirror class members as close as possible. 2) Properties are a short-hand for getFoo()/setFoo() methods (which in the general sense should *not* be understood to always map to class members, as discussed), designed to make typing $o-getFoo() and $o- setFoo() shorter/easier. In this case the syntax and semantics should make that clear and not confuse the user with class-member-like syntax. Right, for example: $tp = new TimePeriod; $tp-hours = 2; foreach($tp as $prop = $val) Would this be an empty loop? That seems to be what the RFC proposes (2) layer of syntactic sugar over a pair of methods. If a property is to provide the (1) illusion of a variable (~class member), IMHO it provides a clear benefit over the __get(), __set() methods. In the spirit of (1): class Audit_Entry { public $info; public $timeAdded { // illusion of a variable, removed 'public property' to avoid confusion get { return $this-_timeAdded; } isset { return isset($this-_timeAdded); } }; protected $_timeAdded; // Datetime function __get($prop) { // virtual properties, these are not class members } } In the spirit of (2), it seems like we would have two ways of doing the same thing. It would probably be a good idea to deprecate __get(), __set()... in favor of the C# style -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Why change the expected behavior of isset? If a property has not been set then isset must return false, and that includes $foo-name = NULL. Regards. Say the property is write-only. How can isset() operate on that? If the property is read-only, how can you unset() it? If the property is write-only, I would imagine isset would return false, because there is no value to read. I think when you call isset(), you are asking, is there something for me to read?, so this would make sense. If the property is read-only, then unset would have no effect. Unsetting is a write action (like deleting a file), so if its read-only, it cannot be unset. It could possibly throw a non-fatal error too I suppose. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
So we have one set of properties where get and isset use different methods and another set of properties where get and isset use same method but with parameter. I think it's not the best way to go. It's better to ignore isset altogether than this. No. The prototype of all setters would be the same. As would the prototype of all getters. The prototype would be ... [public|protected|private] property $property { [public|protected|private] mixed|bool get([bool $isset = false]) { // mixed result for get, bool result for isset }, [public|protected|private] mixed|void set(mixed $value [, bool $unset = false]) { // mixed result for set, void result for unset }, }; From a user's perspective ... echo isset($instance-property) ? 'isset to ' . $instance-property : 'not isset'; This would result in 2 calls ... property-get(true) // Let the getter that an attempt is being made to see if the property has been set. and property-get(false) // Let the getter know that the getter is expected to return the properties value. Similarly for the setter. $instance-property = 'foo'; unset($instance-property); would result in 2 calls ... property-set('foo', false) // Let the setter know that it should be setting the value of the property to 'foo'. and property-set(null, true) // Let the setter know that an attempt to unset the property has taken place. Maybe the proposal should be changed to ... [public|protected|private] property $property { [public|protected|private] mixed get() { }, [public|protected|private] mixed set(mixed $value) { }, [public|protected|private] bool isset() { }, [public|protected|private] void unset() { }, }; (NOTE: Add in abstract and final as appropriate). This last syntax makes far more sense than adding parameters to the get/set methods. The problem however, is what does isset and unset do/return if they are not defined? What if I only want to define the get/set and I do not define the isset/unset? If they are required, properties are far too complex to be useful. But if they are optional, we are back to the same problem of what isset() and unset() are supposed to do... - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hello Stas, In PHP, of course, class properties are dynamic, so you can add and delete them at will. It is a standard feature of dynamic languages. For a person coming from strict compiled language like C# it might be unusual, but that's how dynamic languages work. No not unusual at all. You can dynamically add properties to class instances in C# as well. My point was that methods cannot dynamically be added or removed from class instances, even though variables can. I think what it comes down to, is it wont be possible to remove the actual property definition from the instance, but just be able to hide it, or make it appear like it is missing, to be consistent with the behaviour of standard variables. This makes for another issue though. If I unset() the property $foo, and then (because its gone), attempt to set $foo to something else, this is going to activate the property definitions set method, when I only expected a variable to be created. This is because the property definition still exists, but is just hiding (returning false from its isset handler). How should this situation be handled? - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Stefan, Unfortunately I find that to be one of the major downfalls of PHP. It sometimes disregards defacto standards that are set across the entire industry, which causes a lot of frustration for new programmers. Sometimes the functionality PHP adds by going its own way is worth it, but often it is just a confusing mess. Thats just my opinion though, YMMV. Still, if it is not consistent in itself it is worse than not following certain designs which make sense for other languages only. Yes, I would agree with that. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. From the docu: isset Determine if a variable is set and is not NULL There is nothing confusing about isset($this-Hours) == FALSE in your example if isset($this-seconds) == FALSE. Right, I understand how it would work, and the reasons why it would make sense, but it just feels wrong to me. When you unset() a variable in a class, that whole variable is gone. Its not just hiding somewhere, its completely gone. If a property were to pretend it is not set, with an isset method, it would still be there - just hiding. That is why it does not make sense to me. The main problem here is that unset and isset are not symmetric. isset() basically means there is a value. Where unset() destroys the _holder_ of the value. In that sense, unset is special since it works on another level, on the same level as property_exists(). There are several possible approaches, but the main point here is that at least isset() still makes sense. property_exists() and unset() should be dealt with carefully in another way. Ok. Well isset() could just run the get handler for the property, and if it is null, return false, and otherwise return true. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Lester, Its a defacto standard. Of course there is nothing stopping PHP from implementing properties that way, but by going against the standard set by the rest of the industry, it is very confusing for programmers coming from other languages to learn PHP. A good example is how == works differently in PHP than in other languages. In PHP, === works like == does everywhere else. (string)'0' == (int)0, for example is true in PHP, but false in most other languages. I have had countless conversations with PHP developers who claim the language is broken, because == does not work like they expect it to, after which I have to explain === to them. This is because PHP goes against the defacto standard. Maybe it would have been better if == and === had the opposite meaning, as to not squash the standard? You have got me there. = is assign == is equal value === is equal type and value At least on all the languages I've been using recently ... where is this a problem? In any language that does not have === it is like this: = is assign == is equal type and value That is where the confusion comes from. People do not expect 0 and 0 to be equal, because they are different types. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Derick, Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax -1 Derick Care to elaborate? I'm not sure much consideration will be taken of your opinion unless you put some words behind it. I am curious to know why you did not like the RFC? Regards, - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
2010/12/1 Richard Quadling rquadl...@gmail.com On 1 December 2010 09:22, Stas Malyshev smalys...@sugarcrm.com wrote: Hi! Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set Meant by whom? Is there some law of universe that prevents us from implementing the feature? of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. If you need methods, why not use methods? If you mimick object properties, however, it makes sense to make them work exactly like property, otherwise you have to explain why they don't work this way. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Sorry, from your answer I don't understand - what happens when you call isset($foo-property) and unset($foo-property)? If we think of properties as this new entity for the language (rather than somehow massaging existing entities to fit a new usage scenario), then isset($instance-property) will always return true for any defined property. Even if the getter would return null. This is new behaviour and can be easily documented. isset() for a property is more like method_exists() than isset() on a variable. With regard to unset($instance-property), from the manual ... ... Why change the expected behavior of isset? If a property has not been set then isset must return false, and that includes $foo-name = NULL. Thats simple then, when isset is invoked, call the get method, and if it returns null then isset() returns false, but otherwise returns true. That was likely just a small oversight on Richard's part. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
presid...@basnetworks.net wrote: I feel that the downfall of this syntax, is that the get and set methods can easily be scattered at either end of a class definition. With the syntaxes I provided, it is easy to tell which of the methods a property has defined at a quick glance, because everything is in on spot. Additionally, public/private/protected/final/abstract/etc only has to be specified once on the property (but can be specified separately! - see the RFC). This means less to read, and clearer, cleaner syntax. Lastly, I think that grouping the two methods just makes sense, because a property is one conceptual object, not two. Separating the two methods makes as much sense logically as does separating a class definition into two parts. - Dennis Grouping the get and set is a good convention. But grouping all the gets (doing pretty similar things) and all the sets can be as good as it. You would need to enter into each class/project to see which convention fits better. Grouping all the gets and all the sets can already be done using __get and __set. That is great when dealing with collections of data, but not good at all for dealing with individual properties. They are both meant for different situations, and I think would live quite happily along side each other. Because of that, I think grouping the get/set of an individual property is the best approach possible. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
See, here's the fundamental problem we're running into. There's three different definitions of what a property is that we keep bouncing between, each of which will dictate both syntax and semantics: 1) Properties are a smart masking layer over class members, like a smarter __get/__set, designed to make it possible to swap out in place of class members at will. In this case, both the syntax and semantics of properties should mirror class members as close as possible. 2) Properties are a short-hand for getFoo()/setFoo() methods (which in the general sense should *not* be understood to always map to class members, as discussed), designed to make typing $o-getFoo() and $o-setFoo() shorter/easier. In this case the syntax and semantics should make that clear and not confuse the user with class-member-like syntax. 3) Properties are a completely different animal, neither methods nor class members but a totally different concept. In this case the syntax should not be confusing with either methods or class members, and the semantics should probably then be taken from the most common/popular existing implementation feasible. We cannot mix #1 and #2 and expect to get something usable out the other end, nor can we defend doing so on the grounds of #3. The discussion of the proposal is doing exactly that, however, which I think is a fatal flaw. Personally, if we follow approach #1 (make them look and smell as much like class members as possible) then I'm all for it in concept. It might even simplify many of the regular arguments I have about public properties and good architecture. :-) But only if we can cleanly stick to one definition of purpose, syntax, and semantics. Treating properties as a method implementation that can work like class members if you look at them from the right angle even though they're not class members and don't really work like them is a sure-fire way to confuse the hell out of people. PHP is complicated enough without introducing wave/particle duality. I agree Larry, the discussion is all over the place, but I think it is good because a lot of great ideas are coming up, and most of the bad ideas are getting flushed out. I think everyone needs to work through all of the possibilities before we come to a consensus on what is best. The basic Idea of a property, is making a getFoo() / setFoo($value) pair of methods look and act like a variable from the outside, and have an easily identifiable and simple to use syntax on the inside. The reason I originally focused so much around methods, is because properties literally are a pair of methods in C# (thats what they are compiled into). But PHP is another beast, and the challenges are different. As long as the original purpose of properties is not loss, whatever way we figure out is best to implement them is fine with me. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Larry, Hmm, I would have programmed it liked this: if ($account-beneficiary != null) { print $account-beneficiary-name; } To me, if a property is not set, it means it does not exist and will not be a valid property at any point in the object's lifetime. Null means that it is a valid *possible* property, but does not currently hold any value. This thinking is consistent with other languages. (I move between languages on a daily basis, so consistency is key to keeping my sanity!) One certainly could implement it that way, but that would throw an E_NOTICE if you're using class members and $account-beneficiary is not set. So that makes properties an incomplete drop-in for class members. Hmm, I will have to contemplate that some more. Thinking about properties further, actually, there's two other (related) considerations that always give me grief when dealing with __get: Reference returns and complex member variables. If I want a reference to a class member, I can very easily do this: $foo = $bar-baz; If -baz is accessed via __get(), then that only works if __get() is defined as function __get($var) to start with. That's another encapsulation break. If baz is a property, I would imagine: $foo = $bar-baz; would get a reference to the property itself, not a reference to the return value of the set method. Therefore each call to the new reference would call either the get or set method, and would not operate on the return value of the get. Just a note, C# does not support references to properties, and yes, they break compatibility with variables by doing that. How does one get a reference to a property, if a property is just a collection of methods with fancy behavior? That makes properties a first class entity, which is an entirely different bit of brain bending. Its the same concept as having a reference to a function, where you can invoke the reference and it invokes the function. I say that as a programming concept, not a PHP concept, because I am a bit fuzzy in the function reference department of PHP. (Making properties a free-form super-variable that are not bound to a class is a cool concept, but not at all what we're discussing here AFAIK.) Right, that is not what this RFC is looking to achieve. I imagine to get a reference to the return value of a property, you would do something like this: $foo = ($bar-baz); Similarly, the following does exactly what you'd expect with a normal class member: $foo-bar['baz']-narf = 'poink'; If $foo-bar is returned via __get(), though, then the above statement executes but does not actually save anything... *unless* __get() was defined to return by reference as above. Ok I think I understand what you are saying. In this case, $foo-bar is returning an array. You then access ['baz']-narf from that array. Arrays are always passed by reference, are they not? If so, than the above would work fine, no? Because $foo-bar would just be returning a reference to some array, which you then modify. Actually that's subtly wrong, which is the point I'm making. :-) If $foo-bar is a class member, then $foo-bar['baz'] dereferences from $foo to bar, does an array key lookup, finds an object, dereferences to the narf class member, and assigns poink to that. No new variables are ever created. If $foo-bar is accessed via __get(), then $foo-bar *returns* an array by value; the ['bar'] index of that new array is then accessed, we find an object there,that gets dereferenced to narf, and we assign 'poink' to that, in the new array. So is the solution then to make the set method return by reference? Or does that just create more problems? My question regarding properties here would be: There are subtle and irritating differences between class members as __get() that make the latter not a true replacement for the former, especially when dealing with arrays as I've not found a way to work around those yet. What subtle and irritating differences between class members and properties would we introduce, and would they be the same subtle and irritating inconsistencies or an entirely new set of subtle and irritating inconsistencies to have to deal with? I would say, try our best to resolve all of the inconsistencies, and if we cannot, then make sure they are the same inconsistencies that __get and __set have, to be as least confusing as possible. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
presid...@basnetworks.net wrote: Its a defacto standard. Of course there is nothing stopping PHP from implementing properties that way, but by going against the standard set by the rest of the industry, it is very confusing for programmers coming from other languages to learn PHP. A good example is how == works differently in PHP than in other languages. In PHP, === works like == does everywhere else. (string)'0' == (int)0, for example is true in PHP, but false in most other languages. I have had countless conversations with PHP developers who claim the language is broken, because == does not work like they expect it to, after which I have to explain === to them. This is because PHP goes against the defacto standard. Maybe it would have been better if == and === had the opposite meaning, as to not squash the standard? You have got me there. = is assign == is equal value === is equal type and value At least on all the languages I've been using recently ... where is this a problem? In any language that does not have === it is like this: = is assign == is equal type and value That is where the confusion comes from. People do not expect 0 and 0 to be equal, because they are different types. javascript and C++ both do implicit type conversion (coercion) the same as PHP. You will have to prove that this is NOT the norm. There was a big debate a long time back on stopping implicit type conversion in C++ ... it did not get anywhere. What I am probably asking simply because I don't know is what language are you referring to as I've not come across any. If it's C# then that would explain it ... THAT was created by people who did not accept the consensus agreement in C/C++ ;) -- Lester Caine - G8HFL - Contact - http://lsces.co.uk/wiki/?page=contact L.S.Caine Electronic Services - http://lsces.co.uk EnquirySolve - http://enquirysolve.com/ Model Engineers Digital Workshop - http://medw.co.uk// Firebird - http://www.firebirdsql.org/index.php -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 2 December 2010 13:51, presid...@basnetworks.net wrote: 2010/12/1 Richard Quadling rquadl...@gmail.com On 1 December 2010 09:22, Stas Malyshev smalys...@sugarcrm.com wrote: ... Why change the expected behavior of isset? If a property has not been set then isset must return false, and that includes $foo-name = NULL. Thats simple then, when isset is invoked, call the get method, and if it returns null then isset() returns false, but otherwise returns true. That was likely just a small oversight on Richard's part. No, it was not an oversight. Calling the getter() in response to isset() will probably result in a change to the value of the property. For a property, isset() can and only be interested in the last value of the property, not the next value. As I understand things, isset() performs 2 tests. First a check to see if the variable exists and then to see if it has a value assigned. For a property, the first part of that equation is fairly simple - the property has to exist or not. The second part though is not easy. A variable will not change value in response to isset(), but, if isset() calls the getter(), then it could and probably would. Calling isset() shouldn't alter anything. Having isset() call the getter() and unset() call the setter() is fine as long as the getter() and setter() know why they are being called. If the developer needs to supply the last value - their choice - then this could be implemented by caching the last value in a local scope static. Completely encapsulated. get($isset = false){ static $lastValue; if (!$isset) { // Generate the new value and assign it to $lastValue } return $lastValue; } Richard. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 12/2/10 8:42 AM, presid...@basnetworks.net wrote: How does one get a reference to a property, if a property is just a collection of methods with fancy behavior? That makes properties a first class entity, which is an entirely different bit of brain bending. Its the same concept as having a reference to a function, where you can invoke the reference and it invokes the function. I say that as a programming concept, not a PHP concept, because I am a bit fuzzy in the function reference department of PHP. I don't believe PHP has function references per se. It has the ability to call functions dynamically by either: $function = 'foo'; $function(); // or call_user_func[_array]('foo'); (The former is faster so preferred if you have a fixed number of variables.) Functions are not first-class entities in PHP the way they are in, say, Javascript so you can't pass them around, nor do you have function pointers as you do in C. (My god those are a nightmare to code...) PHP 5.3 introduced anonymous functions/closures, which seem at first blush to be sort of like that. However, I believe the internal implementation is done using objects and you can mimic that behavior on an object using an interface, so really functions still don't have a first-class status but are emulated using objects. (I'm sure one of the compiler people can correct me if that's not entirely accurate.) /tangent Actually that's subtly wrong, which is the point I'm making. :-) If $foo-bar is a class member, then $foo-bar['baz'] dereferences from $foo to bar, does an array key lookup, finds an object, dereferences to the narf class member, and assigns poink to that. No new variables are ever created. If $foo-bar is accessed via __get(), then $foo-bar *returns* an array by value; the ['bar'] index of that new array is then accessed, we find an object there,that gets dereferenced to narf, and we assign 'poink' to that, in the new array. So is the solution then to make the set method return by reference? Or does that just create more problems? I'm not sure. I'm just pointing out that behaves like class members is a substantially more complex scenario than it seems at first blush, and we need to think through the implications of that and just how closely we can emulate properties. My question regarding properties here would be: There are subtle and irritating differences between class members as __get() that make the latter not a true replacement for the former, especially when dealing with arrays as I've not found a way to work around those yet. What subtle and irritating differences between class members and properties would we introduce, and would they be the same subtle and irritating inconsistencies or an entirely new set of subtle and irritating inconsistencies to have to deal with? I would say, try our best to resolve all of the inconsistencies, and if we cannot, then make sure they are the same inconsistencies that __get and __set have, to be as least confusing as possible. - Dennis I agree that is a good guideline to follow. It also provides a natural answer to the isset/unset question: If you try to isset/unset a class member that doen't exist but __get() does, what happens? (That may not always be the right answer, but it's a comparison we should make.) From another reply: The basic Idea of a property, is making a getFoo() / setFoo($value) pair of methods look and act like a variable from the outside, and have an easily identifiable and simple to use syntax on the inside. The reason I originally focused so much around methods, is because properties literally are a pair of methods in C# (thats what they are compiled into). But PHP is another beast, and the challenges are different. As long as the original purpose of properties is not loss, whatever way we figure out is best to implement them is fine with me. The original purpose being, specifically, smarter class members, correct? (The internal syntax to define them we can bikeshed later; determining the external syntax and semantics has to come first.) --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Having thought a bit about this, there are a couple of initial problems I see, and, more importantly, I'm not convinced that the stated problem (encapsulation) requires the addition of a new language construct (i.e. a property as distinct from a class member). In fact, I think it is better implemented in another way (see below). First of all from a confusion point of view, PHP already has defined property in a way that opposes your RFC's definition: property_exists() checks for the existence of what you call a class member. So, at least, it seems to me you would have to find new terminology if you wanted to pursue this avenue of a new construct. In my opinion, however, there should not be a new construct, and property and class member should remain interchangeable descriptions of the same class construct. I think we can do this and still fix the encapsulation problem. (Note: this is a long e-mail, and probably best represented in a new RFC. I have also written this up more completely in the form of an RFC, but I don't want to clutter up the wiki's RFC page unless other people like this idea as well, so I'll add the RFC if it looks like it will be useful). For example, we could do: class Time { protected $time; // note that $seconds, $minutes, and $hours are, in this // implementation, dummies, since they will never hold // a value, because their set functions only set the $time // class member. public $seconds; public $minutes; public $hours; public function issetTime($name) isset($hours,$minutes,$seconds) { return isset($this-time); } public function unsetTime($name) unset($hours,$minutes,$seconds) { unset($this-time); } public function setTime($name, $value) set($hours,$minutes,$seconds) { switch($name) { case 'hours': $this-time = $value * 3600; break; case 'minutes': $this-time = $value * 60; break; case 'seconds': $this-time = $value; break; } $this-seconds = $seconds; } public function getTime($name) get($hours,$minutes,$seconds) { switch($name) { case 'hours': return $this-time / 3600; break; case 'minutes': return $this-time / 60; break; case 'seconds': return $this-time; break; } } } with this syntax, you could group the properties like above or, if you preferred, you could have a different function for each property. for read only (similar for write only), including the possibility of asymmetry: class Time { protected $time; public $seconds; public $minutes; public $hours; // ... // now Time::$hours can only be set from inside the class / descendents protected function setHours($name, $value) set($hours) { $this-time = $value * 3600; } // but Time::$hours can still be retrieved from outside the class public function getHours($name) get($hours) { return $this-time / 3600; } } for interfaces: interface TimeClass { public function setHours($name, $value) set($hours); } This has a number of benefits: 1. This acts like PHP, and also brings along features out of the box (a) The new syntax mimics the form of the syntax of closures ($x = function() use($a, $b) { // ... };), so it is somewhat familiar. (b) The arguments of the isset, unset, getters and setters is analogous to that in the __get and __set methods, so userland implementation will be familiar. (c) The getters and setters are still regular class methods, so they can be called as methods as usual (subject to visibility, of course) (d) Adds shades to the read-only and write-only concepts via visibility modifiers! (e) Isset / unset make sense now! E.g. that when unsetting $hours, we actually want to unset the time in general. In fact, this is preferred, because in the examples we've been looking at, the magic is in grouping the three class members (seconds, minutes, hours), and this implementation of isset and unset allow you to do just that grouping, without having to write 3 isset and 3 unset functions, as you would have to in the property definition. (f) This allows for much more compact class definitions, as you don't have to define getHours(), getMinutes(), getSeconds() individually if you don't want to (although it allows you the flexibility to do that if it's what you want). (g) Inheritance works out of the box. (h) Final keyword works out of the box. (i) Documentation works out of the box (just do it as you do it now, on the class members and the methods). (j) Interfaces work. (k) In the example above, the class could go ahead and set the Time::$time class member directly without incurring the overhead of the getter / setter functions! 2. Fixes the stated problems (a) Adds the syntactic sugar to
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi: On 01 Dec 2010, at 01:31, presid...@basnetworks.net wrote: That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. This is also true for object properties - see magic methods. I don't see why you shouldn't be able to unset them - you can do that with regular properties... So what you imagine would happen if you call unset($foo-property) or isset($foo-property)? Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. I tend to disagree. The need to be consistent inside of PHP has precedence over being consistent with other languages. You need to think of a property as a set of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. I think, it really is the other way around. Properties are meant to give the programmer the illusion that she is just having a field. That is abstraction. She does not care about implementation details. And that is the power of properties. isset() and unset() are perfectly fine in that context. And I do not see a problem to provide the standard semantics for them automatically, and let the programmer add isset/unset methods to the property as needed in exactly the same style as get/set. There is a good usecase for asking whether a property has been set, for instance to verify initialization. And, of course unset has also a useful meaning. It is about the value, and even so there are methods around a value, properties are meant to be values. There are definitely use-cases where that does not hold, but that is application specific. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. From the docu: isset — Determine if a variable is set and is not NULL There is nothing confusing about isset($this-Hours) == FALSE in your example if isset($this-seconds) == FALSE. Best regards Stefan -- Stefan Marr Software Languages Lab Vrije Universiteit Brussel Pleinlaan 2 / B-1050 Brussels / Belgium http://soft.vub.ac.be/~smarr Phone: +32 2 629 2974 Fax: +32 2 629 3525 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Tue, 2010-11-30 at 19:31 -0500, presid...@basnetworks.net wrote: isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Even when a property does exist physically (by these methods) it might not exist logically. Missing that functionality is inconsistent with the languages. such an inconsistency would be enough reason for a -1000 vote :-) johannes -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set Meant by whom? Is there some law of universe that prevents us from implementing the feature? of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. If you need methods, why not use methods? If you mimick object properties, however, it makes sense to make them work exactly like property, otherwise you have to explain why they don't work this way. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Sorry, from your answer I don't understand - what happens when you call isset($foo-property) and unset($foo-property)? -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! Just to chime in on the subject of performance, here is how C# handles properties: PHP is not a compiled language and as such handling of properties, in particular, is radically different in PHP. For example, the property name in expression like $foo-$bar is known only in runtime. -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 1 December 2010 09:22, Stas Malyshev smalys...@sugarcrm.com wrote: Hi! Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set Meant by whom? Is there some law of universe that prevents us from implementing the feature? of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. If you need methods, why not use methods? If you mimick object properties, however, it makes sense to make them work exactly like property, otherwise you have to explain why they don't work this way. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Sorry, from your answer I don't understand - what happens when you call isset($foo-property) and unset($foo-property)? If we think of properties as this new entity for the language (rather than somehow massaging existing entities to fit a new usage scenario), then isset($instance-property) will always return true for any defined property. Even if the getter would return null. This is new behaviour and can be easily documented. isset() for a property is more like method_exists() than isset() on a variable. With regard to unset($instance-property), from the manual ... The behavior of unset() inside of a function can vary depending on what type of variable you are attempting to destroy. So, we already have differing behaviour based upon context. Attempting to destroy a property should through a non fatal error. One idea I had was to keep just the get/set property methods and add to them an additional parameter ... ?php public $seconds { public set($value, $unset = False) { if ($unset) { // unset() has been called on the property. // In this instance $value will be Null. } else { // set the property using the supplied $value. } }, public get($isset = False) { if ($isset) { // isset() has been called on the property. // If the value is a non-destructive calculation then maybe returning the comparison of the result of the calculation to null. } else { // return the value for this property. } } }; So, isset($instance-property) would call $instance-property-get(True); unset($instance-property) would call $instance-property-set(Null, True); This keeps just the 2 property methods. It still allows isset/unset and allows the developer the option of handling them. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
2010/12/1 Eloy Bote Falcon eloyb...@gmail.com 2010/12/1 Richard Quadling rquadl...@gmail.com On 1 December 2010 09:22, Stas Malyshev smalys...@sugarcrm.com wrote: Hi! Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set Meant by whom? Is there some law of universe that prevents us from implementing the feature? of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. If you need methods, why not use methods? If you mimick object properties, however, it makes sense to make them work exactly like property, otherwise you have to explain why they don't work this way. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Sorry, from your answer I don't understand - what happens when you call isset($foo-property) and unset($foo-property)? If we think of properties as this new entity for the language (rather than somehow massaging existing entities to fit a new usage scenario), then isset($instance-property) will always return true for any defined property. Even if the getter would return null. This is new behaviour and can be easily documented. isset() for a property is more like method_exists() than isset() on a variable. With regard to unset($instance-property), from the manual ... The behavior of unset() inside of a function can vary depending on what type of variable you are attempting to destroy. So, we already have differing behaviour based upon context. Attempting to destroy a property should through a non fatal error. One idea I had was to keep just the get/set property methods and add to them an additional parameter ... ?php public $seconds { public set($value, $unset = False) { if ($unset) { // unset() has been called on the property. // In this instance $value will be Null. } else { // set the property using the supplied $value. } }, public get($isset = False) { if ($isset) { // isset() has been called on the property. // If the value is a non-destructive calculation then maybe returning the comparison of the result of the calculation to null. } else { // return the value for this property. } } }; So, isset($instance-property) would call $instance-property-get(True); unset($instance-property) would call $instance-property-set(Null, True); This keeps just the 2 property methods. It still allows isset/unset and allows the developer the option of handling them. -- Richard Quadling Twitter : EE : Zend -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php Why change the expected behavior of isset? If a property has not been set then isset must return false, and that includes $foo-name = NULL. Regards. Oops, the mail has been marked has spam because of some URI. Regards.
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! If we think of properties as this new entity for the language (rather than somehow massaging existing entities to fit a new usage scenario), then I think the idea of new entity of the language looking exactly like old entity of the language but having different rules is kind of non-starter. One idea I had was to keep just the get/set property methods and add to them an additional parameter ... So we have one set of properties where get and isset use different methods and another set of properties where get and isset use same method but with parameter. I think it's not the best way to go. It's better to ignore isset altogether than this. -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Richard: On 01 Dec 2010, at 10:57, Richard Quadling wrote: If we think of properties as this new entity for the language (rather than somehow massaging existing entities to fit a new usage scenario), then isset($instance-property) will always return true for any defined property. Even if the getter would return null. This is new behaviour and can be easily documented. isset() for a property is more like method_exists() than isset() on a variable. I tend to see that rather different. Properties are not about methods, properties as in C# are about abstracting from the actual realization of how the state is represented internally that is exposed by a property. Thus, properties like proposed here should be used to provide the illusion of having normal class variables. And in that scenario it makes sense to talk about the value the property represents and not the fact that there are methods. So, from my point of view isset/unset have perfectly valid semantics on many of the usual cases. Even so, I agree, there are cases where that is not so, but in those cases isset/unset could be specialize like set/get. Best regards Stefan -- Stefan Marr Software Languages Lab Vrije Universiteit Brussel Pleinlaan 2 / B-1050 Brussels / Belgium http://soft.vub.ac.be/~smarr Phone: +32 2 629 2974 Fax: +32 2 629 3525 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 1 December 2010 10:23, Eloy Bote Falcon eloyb...@gmail.com wrote: 2010/12/1 Richard Quadling rquadl...@gmail.com On 1 December 2010 09:22, Stas Malyshev smalys...@sugarcrm.com wrote: Hi! Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set Meant by whom? Is there some law of universe that prevents us from implementing the feature? of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. If you need methods, why not use methods? If you mimick object properties, however, it makes sense to make them work exactly like property, otherwise you have to explain why they don't work this way. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Sorry, from your answer I don't understand - what happens when you call isset($foo-property) and unset($foo-property)? If we think of properties as this new entity for the language (rather than somehow massaging existing entities to fit a new usage scenario), then isset($instance-property) will always return true for any defined property. Even if the getter would return null. This is new behaviour and can be easily documented. isset() for a property is more like method_exists() than isset() on a variable. With regard to unset($instance-property), from the manual ... The behavior of unset() inside of a function can vary depending on what type of variable you are attempting to destroy. So, we already have differing behaviour based upon context. Attempting to destroy a property should through a non fatal error. One idea I had was to keep just the get/set property methods and add to them an additional parameter ... ?php public $seconds { public set($value, $unset = False) { if ($unset) { // unset() has been called on the property. // In this instance $value will be Null. } else { // set the property using the supplied $value. } }, public get($isset = False) { if ($isset) { // isset() has been called on the property. // If the value is a non-destructive calculation then maybe returning the comparison of the result of the calculation to null. } else { // return the value for this property. } } }; So, isset($instance-property) would call $instance-property-get(True); unset($instance-property) would call $instance-property-set(Null, True); This keeps just the 2 property methods. It still allows isset/unset and allows the developer the option of handling them. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php Why change the expected behavior of isset? If a property has not been set then isset must return false, and that includes $foo-name = NULL. Regards. Say the property is write-only. How can isset() operate on that? If the property is read-only, how can you unset() it? If properties are abstractions to methods, then they don't serve a purpose. If properties are wrappers for locally cached values then they isset/unset is feasible. If properties are to ... provide the illusion of having normal class variables ... ... then it is undefined if there is a real value held anywhere. You do not want isset() to have to get() the value of the property as the getter may be getting the data from (for example) a DB, SOAP request, etc. Getting the data is not as simple as just returning a local value. I think isset() and unset() for properties is different to that for variables. Either isset() and unset() generate errors when called on properties, or, with an amendment to the syntax, isset() and unset() are passed to the setter and getter (if they exist) to allow the developer of the property to decide what to return. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 1 December 2010 10:38, Stas Malyshev smalys...@sugarcrm.com wrote: So we have one set of properties where get and isset use different methods and another set of properties where get and isset use same method but with parameter. I think it's not the best way to go. It's better to ignore isset altogether than this. No. The prototype of all setters would be the same. As would the prototype of all getters. The prototype would be ... [public|protected|private] property $property { [public|protected|private] mixed|bool get([bool $isset = false]) { // mixed result for get, bool result for isset }, [public|protected|private] mixed|void set(mixed $value [, bool $unset = false]) { // mixed result for set, void result for unset }, }; From a user's perspective ... echo isset($instance-property) ? 'isset to ' . $instance-property : 'not isset'; This would result in 2 calls ... property-get(true) // Let the getter that an attempt is being made to see if the property has been set. and property-get(false) // Let the getter know that the getter is expected to return the properties value. Similarly for the setter. $instance-property = 'foo'; unset($instance-property); would result in 2 calls ... property-set('foo', false) // Let the setter know that it should be setting the value of the property to 'foo'. and property-set(null, true) // Let the setter know that an attempt to unset the property has taken place. Maybe the proposal should be changed to ... [public|protected|private] property $property { [public|protected|private] mixed get() { }, [public|protected|private] mixed set(mixed $value) { }, [public|protected|private] bool isset() { }, [public|protected|private] void unset() { }, }; (NOTE: Add in abstract and final as appropriate). -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! No. The prototype of all setters would be the same. As would the prototype of all getters. But we'd have two sets of properties - one handled by __get/__isset, another - by get($isset). Not a good idea. -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 1 December 2010 12:30, Stas Malyshev smalys...@sugarcrm.com wrote: Hi! No. The prototype of all setters would be the same. As would the prototype of all getters. But we'd have two sets of properties - one handled by __get/__isset, another - by get($isset). Not a good idea. So, should properties isset/unset go via the magic methods? With properties, there would be the duplication anyway (__get()/get() and __set()/set()). Either way, only the property knows what should happen when an isset() or unset() is called against it. It is for that reason that I think the property should handle it. __get, __set, __isset and __unset are for undefined class members. Not properties. From the user of the class, completely invisible. Having more than 1 way to skin the cat is pretty much de rigueur for PHP. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Davey, Object properties (or members, classic -var, not this proposed syntax) CURRENTLY, work this way: php -r 'class foo { public $bar; } $foo = new foo(); var_dump(isset($foo-bar));' bool(false) This is because you are confusing PHP's isset() with a property_exists(). Is set. Is the variable (or member/property) set to a value? I did not know of property_exists(), very interesting! In this case, both isset() and unset() work with the property get/set you are proposing. Imagine: $results = $db-query('SELECT SQL_CALC_FOUND_ROWS * FROM some_table WHERE foo = 'bar'); if (isset($results-count)) { foreach ($results-getResult() as $result) { // Do something } } where isset() would hit: protected property count { isset { $result = $this-execute('SELECT FOUND_ROWS()'); $this-count = $result-getColumn(); if ($this-count == 0) { return false; } return false; } } Not an ideal example, but it gives you an IDEA off the top of my head of a way to take advantage of it Well, I understand the concept and how it would work, but I just don't think its logical. In my mind, being able to make a property appear to disappear makes as much sense as making a class method appear to disappear. This is absolutely no good for inheritance for one thing. The __isset method makes perfect sense, because all variables handled with __get and __set don't truly exist. They are not actually defined in the class, they are just fake class members, whose data comes from somewhere else - maybe an array. So __isset is there to say which fake member names do and don't exist. But when defined, a property, like a method, shouldn't be able to just disappear. It is a specific definition and should never appear to be missing. If you need a class member that can be unset, you should be using __isset __get and __set, because that is exactly what those are meant for. My feelings are that a property foo should behave exactly like a getFoo() and setFoo($value) pair of methods. You can always call these methods, and never worry that you will get a method not set error. When you call getFoo() you are always guaranteed to get something, even if it is simply NULL. Maybe I am missing your point? But it does not make logical sense to me, the way you suggest. Also, would adding isset not make properties much slower? Calling $object-foo would first have to call and process the isset method to determine if it is set, then after getting true from isset, it would be able to call get. And what happens if there is no isset? Is it just always guaranteed to be set then? - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. This is also true for object properties - see magic methods. I don't see why you shouldn't be able to unset them - you can do that with regular properties... So what you imagine would happen if you call unset($foo-property) or isset($foo-property)? Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. I tend to disagree. The need to be consistent inside of PHP has precedence over being consistent with other languages. Unfortunately I find that to be one of the major downfalls of PHP. It sometimes disregards defacto standards that are set across the entire industry, which causes a lot of frustration for new programmers. Sometimes the functionality PHP adds by going its own way is worth it, but often it is just a confusing mess. Thats just my opinion though, YMMV. You need to think of a property as a set of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. I think, it really is the other way around. Properties are meant to give the programmer the illusion that she is just having a field. That is abstraction. She does not care about implementation details. And that is the power of properties. isset() and unset() are perfectly fine in that context. And I do not see a problem to provide the standard semantics for them automatically, and let the programmer add isset/unset methods to the property as needed in exactly the same style as get/set. There is a good usecase for asking whether a property has been set, for instance to verify initialization. And, of course unset has also a useful meaning. It is about the value, and even so there are methods around a value, properties are meant to be values. There are definitely use-cases where that does not hold, but that is application specific. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. From the docu: isset Determine if a variable is set and is not NULL There is nothing confusing about isset($this-Hours) == FALSE in your example if isset($this-seconds) == FALSE. Right, I understand how it would work, and the reasons why it would make sense, but it just feels wrong to me. When you unset() a variable in a class, that whole variable is gone. Its not just hiding somewhere, its completely gone. If a property were to pretend it is not set, with an isset method, it would still be there - just hiding. That is why it does not make sense to me. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set Meant by whom? Is there some law of universe that prevents us from implementing the feature? Its a defacto standard. Of course there is nothing stopping PHP from implementing properties that way, but by going against the standard set by the rest of the industry, it is very confusing for programmers coming from other languages to learn PHP. A good example is how == works differently in PHP than in other languages. In PHP, === works like == does everywhere else. (string)'0' == (int)0, for example is true in PHP, but false in most other languages. I have had countless conversations with PHP developers who claim the language is broken, because == does not work like they expect it to, after which I have to explain === to them. This is because PHP goes against the defacto standard. Maybe it would have been better if == and === had the opposite meaning, as to not squash the standard? of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. If you need methods, why not use methods? Because properties are only meant to be a pretty syntax for a get/set method. Thats it! I don't know of any other special behaviour in any other language that lets you hide properties or anything else like that. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Sorry, from your answer I don't understand - what happens when you call isset($foo-property) and unset($foo-property)? You make a good point. If we can't unset a property, than we lose consistency with regular variables which I guess ruins the point of properties. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Just to chime in on the subject of performance, here is how C# handles properties: PHP is not a compiled language and as such handling of properties, in particular, is radically different in PHP. For example, the property name in expression like $foo-$bar is known only in runtime. Yes, of course. Like I say, that is just how it works in C#, I make no claims about how it would or should work in PHP. I was just hoping that comparisons to C# would help to inform the discussion. However, I would imagine that the get/set within a property would be interpreted as methods in PHP irregardless, so apart from checking to see if a class member is a property, and finding its get/set method to call, would the performance not be exactly that of a method call? - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
public property Hours read getHours write setHours; I actually like that, though I think we should support the whole existing semantics, i.e. get/set/isset/unset. And probably keep the names, so we don't call the same thing both read and get. This doesn't make sense. To call isset() on a property, would be to ask if the property itself exists. But once defined, a property always exists (think of methods, for example). (Sorry for sending again Stas, I forgot to reply all) - Dennis True, but if part of the intent (as noted in a previous email) is to provide a mechanism that looks to the outside world like a class member, and therefore one can switch between the two without breaking an API, then isset/unset should have some sort of useful meaning. This is the exact issue Stas touched upon earlier, and you are both absolutely right. If isset/unset are not supported, than class variables and properties cannot truly be interchangeable. However, my issue is this: If get/set/isset/unset are all supported as methods in a property, I do not think it wise to require isset/unset to be created - they should be optional, for the few times that they would be useful. However, the question is, if you do not define isset/unset, then what do they do? isset could always return true, but what about unset? Does it just do nothing? That does not make sense from the perspective of a user of the class. Maybe if you call unset, than isset now returns false. Then once you call set again, isset now returns true? That would be consistent with how variables work... - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! the rest of the industry, it is very confusing for programmers coming from other languages to learn PHP. A good example is how == works differently in PHP than in other languages. In PHP, === works like == does everywhere else. (string)'0' == (int)0, for example is true in Not everywhere. Perl has the same rules, for example. explain === to them. This is because PHP goes against the defacto standard. Maybe it would have been better if == and === had the opposite meaning, as to not squash the standard? There's no such standard. PHP works differently than the language you knew before, that's it. If it worked the same, it would be the same language. Because properties are only meant to be a pretty syntax for a get/set method. Thats it! I don't know of any other special behaviour in any other language that lets you hide properties or anything else like that. If that's it, we probably don't need them. They would just hide what happens in the code and confuse the user, which would not know what $a-foo means - would it work according to class attribute rules or class method rules? I think, however, this syntax might be useful - for example, Zend Framework does a lot of property/method linking, some other frameworks do that too, and individual methods might be better than catch-all in this case. But that requires consistency. In PHP, of course, class properties are dynamic, so you can add and delete them at will. It is a standard feature of dynamic languages. For a person coming from strict compiled language like C# it might be unusual, but that's how dynamic languages work. You make a good point. If we can't unset a property, than we lose consistency with regular variables which I guess ruins the point of properties. It doesn't have to - if we can find a consistent concept of how to do it. But we need to think about it. -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 01 Dec 2010, at 14:10, presid...@basnetworks.net wrote: Unfortunately I find that to be one of the major downfalls of PHP. It sometimes disregards defacto standards that are set across the entire industry, which causes a lot of frustration for new programmers. Sometimes the functionality PHP adds by going its own way is worth it, but often it is just a confusing mess. Thats just my opinion though, YMMV. Still, if it is not consistent in itself it is worse than not following certain designs which make sense for other languages only. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. From the docu: isset — Determine if a variable is set and is not NULL There is nothing confusing about isset($this-Hours) == FALSE in your example if isset($this-seconds) == FALSE. Right, I understand how it would work, and the reasons why it would make sense, but it just feels wrong to me. When you unset() a variable in a class, that whole variable is gone. Its not just hiding somewhere, its completely gone. If a property were to pretend it is not set, with an isset method, it would still be there - just hiding. That is why it does not make sense to me. The main problem here is that unset and isset are not symmetric. isset() basically means there is a value. Where unset() destroys the _holder_ of the value. In that sense, unset is special since it works on another level, on the same level as property_exists(). There are several possible approaches, but the main point here is that at least isset() still makes sense. property_exists() and unset() should be dealt with carefully in another way. Best regards Stefan -- Stefan Marr Software Languages Lab Vrije Universiteit Brussel Pleinlaan 2 / B-1050 Brussels / Belgium http://soft.vub.ac.be/~smarr Phone: +32 2 629 2974 Fax: +32 2 629 3525 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hello, You are missing the point in PHP in that case. Because PHP is dynamic scripting language, public properties can be added and removed in the object on the fly. That's why there is isset and unset that works on object properties. Consider ActiveRecord, DataMappers, ORM, etc. They use that 100% to their advantage - I haven't yet seen a model witch defines all the properties in PHP code - mostly it takes table columns from DB and add these properties in dynamic way. That's why it isn't so straight forward of adding properties like you propose. I think you are correct, and I am beginning to see the light on this issue. In order for a property to be 100% compatible with regular variables, it needs to work properly with isset and unset. P.S. By the way, maybe I haven't being doing some really crazy stuff on PHP, but I rarely define getters and setters in my classes that do something except $this-val = $val and return $this-val. Well, honestly I haven't worked on some stuff developed by more that 6 programmers too (Latvia is a small county - no major epic projects at all), but still I think my point is valid. Properties have a variety of uses. One use is to make a read-only value that can later have a set method added in a child class. This is not possible with the readonly keyword. You can also provide different visibilities for the get and set, as well as marking them final or abstract individually. You can use properties to provide simple validation. For example: class TimePeriod { private $_hours; /// Hours must be between 1-12 public property Hours { get { return $this-_hours; } set { if ($value 1 || $value 12) { throw new Exception(Hours must be between 1-12); } $this-_hours = $value; } } }; You can also use properties to dynamically generate a value, such as in one of the examples in the RFC: class TimePeriod { private $seconds; public property Hours { get { return $this-seconds / 3600; } } public property Minutes { get { return $this-seconds / 60; } } }; Here is some additional reading on C# properties from MSDN: http://msdn.microsoft.com/en-us/library/ms229054.aspx http://msdn.microsoft.com/en-us/library/ms229006.aspx - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
presid...@basnetworks.net wrote: Its a defacto standard. Of course there is nothing stopping PHP from implementing properties that way, but by going against the standard set by the rest of the industry, it is very confusing for programmers coming from other languages to learn PHP. A good example is how == works differently in PHP than in other languages. In PHP, === works like == does everywhere else. (string)'0' == (int)0, for example is true in PHP, but false in most other languages. I have had countless conversations with PHP developers who claim the language is broken, because == does not work like they expect it to, after which I have to explain === to them. This is because PHP goes against the defacto standard. Maybe it would have been better if == and === had the opposite meaning, as to not squash the standard? You have got me there. = is assign == is equal value === is equal type and value At least on all the languages I've been using recently ... where is this a problem? Also isset() makes perfect sense when you have NULL values coming from a database. unset then kicks a NULL back to the database if updating. The varable exists but has a NULL value ... -- Lester Caine - G8HFL - Contact - http://lsces.co.uk/wiki/?page=contact L.S.Caine Electronic Services - http://lsces.co.uk EnquirySolve - http://enquirysolve.com/ Model Engineers Digital Workshop - http://medw.co.uk// Firebird - http://www.firebirdsql.org/index.php -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Larry, First of all, I have generally found the Bean-style getter/setter approach to be a sign of poor encapsulation to begin with. You shouldn't be mucking with internal elements of an object in the first place, period. More details on that here: http://www.garfieldtech.com/blog/property-visibility Interesting post, although I can't say I agree with your views. Your post leaves me wondering how the user is expected to get or give data to a class (for example, if I'm not supposed to do $customer-name or $customer-getName(), how do I get the customers name?). Additionally, you are forgetting the real power of properties, which is the ability to generate a get value, and process a set value, because get/set are methods. Properties are hardly just an indirection layer around an underlying piece of data. The idea of a -getName() method for retrieving a person's name is fine. My point there is that any assumption that it corresponds to a -name class member (as Bean definitions require) is invalid on its face. (The context there is a lengthy ongoing debate regarding the use of public vs. protected class members, with my basic point being that class members are an implementation detail and if you care about them in the first place then you have a bug. Yes, it's a deliberately stringent position.) Right, I think I understand the whole Bean thing now. Its just a struct, but has get/set methods instead of public properties? In that case, that is rather silly. A get/set method should not be required to correspond to any underlying value. A get could even return a constant, inline value for that matter. It shouldn't matter what a get returns, as long as it returns something! I do not agree with class members are an implementation detail. I would say private/protected members/methods are an implementation detail, which is true no matter how you slice it. There are perfectly valid reasons for exposing public class members. Heck I make classes that are just a set of public class members, and do not even have methods. This is what a struct is in C, C++ and C#. Its just a storage container (like a bean in java, but without silly methods for every class member). Arguably an array could be used for this, but an array has less structure and is not properly suited for a well-defined type. What I'm seeing here is that whether properties are intended as an indirection layer for class members (eg, a more robust __get/__set) or not is a fuzzy question. On the one hand they are (since the goal of the syntax is to make it irrelevant to the caller which is happening), but on the other they're supposed to be something different that can do all kinds of on the fly behavior. Properties can be thought of as a __get/__set that only handle a single class member name each. They are for single members, while __get/__set is generically for all members. I can see how you would call __get/__set and indirection layer because, since you are handling the values generically, doing anything other than indirection is too complicated. But when you are writing accessors for a single defined member, its easier to be more robust - you can do anything you could do in a normal method. - Which also brings up an interesting question: class Foo { public $a = 1; protected $b = 2; public property $a { get { return 3; } } public property $b { get { return 4; } } } $f = new Foo(); print $f-a . PHP_EOL; // Does this print 1 or 3? print $f-b . PHP_EOL; // Does this print 2 or 4, or error? Both of those throw an error. Properties and variables share the same namespace, so you cannot define a property and variable with the same name. Is this consistent with methods? Do those share a namespace, too? (I don't actually recall off the top of my head.) methods and variables have their own namespaces. This is because they are called differently: // variable $a print $f-a; // method a() print $f-a(); But variables and properties would be called the same way (both $f-a;). Because of this, they need to share the same namespace in order to avoid ambiguity. This is in fact a feature of properties, because this way an existing variable can later be replaced with a property, and all calling code will continue to work (or at least will compile). This is what I would imagine seeing, and would compile: class Foo { private $_a = 1; protected $_b = 2; public property $a { get { return 3; } } public property $b { get { return 4; } } } As you can see, there is no conflict or confusion this way. True, although for the record I have always detested the underscore prefix on variables as a difficult to read hack. :-) To be honest, I also detest the underscore prefix. In C# we use camel case for public and pascal case for private, but because PHP is case-insensitive, that (very unfortunately) is not possible. C# example: class Foo { private
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Larry, Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Consistency with other languages must also be balanced against consistency within PHP. Both are important. Class members and both existing class-member-ish mechanisms (__magic and ArrayAccess) have the concept of isset/unset. A third class-member-ish (syntactically speaking) mechanism will be expected to have the same set of primitives. To not have them will be a major language WTF, because to a normal user of an object they *look* like class members, not methods, they *taste* like class members, not methods, so they should *act* like class members, not methods. Basically, properties can only be considered a drop-in replacement for class members (as you've stated, correctly, is one of the potential big wins for them) if they fully emulate their behavior. If they do not, then it is incorrect to say that they can be swapped in for a class member without changing an API. Yes, you are correct, if they are to be a full drop-in replacement, they must handle isset/unset as expected. This is something I had not thought of earlier. __isset() is a whole different matter, without it we would have to assume that every possible member name either exists or does not exist. This is because __isset can handle ANY member name. Properties are bound to a single member name, therefore, they always exist, unless you were to physically remove that property from the class, which, like methods, that is not possible. No, but it can be easily emulated. Actually, I can even think of a concrete use case. Suppose I have an object that acts as a facade for a remote object over SOAP, REST, or whatever. It is using properties to represent attributes of a remote, say, insurance account. I want to know if a beneficiary has been set on the account. The most straightforward way to do so is if (isset($account-beneficiary)) { print $account-beneficiary-name; } If we are implementing such logic via __get(), we can do exactly that. If we are implementing it via properties, we should still be able to. Forcing the user to know that he needs to do it this way instead, but only if we're using properties rather than __get(): if ($account-hasBeneficiary()) { print $account-beneficiary-name; } is violating the principle of encapsulation as it means the user needs to know which of the three forms of $account-beneficiary happens to be in use. Hmm, I would have programmed it liked this: if ($account-beneficiary != null) { print $account-beneficiary-name; } To me, if a property is not set, it means it does not exist and will not be a valid property at any point in the object's lifetime. Null means that it is a valid *possible* property, but does not currently hold any value. This thinking is consistent with other languages. (I move between languages on a daily basis, so consistency is key to keeping my sanity!) Thinking about properties further, actually, there's two other (related) considerations that always give me grief when dealing with __get: Reference returns and complex member variables. If I want a reference to a class member, I can very easily do this: $foo = $bar-baz; If -baz is accessed via __get(), then that only works if __get() is defined as function __get($var) to start with. That's another encapsulation break. If baz is a property, I would imagine: $foo = $bar-baz; would get a reference to the property itself, not a reference to the return value of the set method. Therefore each call to the new reference would call either the get or set method, and would not operate on the return value of the get. Just a note, C# does not support references to properties, and yes, they break compatibility with variables by doing that. I imagine to get a reference to the return value of a property, you would do something like this: $foo = ($bar-baz); Similarly, the following does exactly what you'd expect with a normal class member: $foo-bar['baz']-narf = 'poink'; If $foo-bar is returned via __get(), though, then the above statement executes but does not actually save anything... *unless* __get() was defined to return by reference as above. Ok I think I understand what you are saying. In this case, $foo-bar is returning an array. You then access ['baz']-narf from that array. Arrays are always passed by reference, are they not? If so, than the above would work fine, no? Because $foo-bar would just be
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Sun, 28 Nov 2010, presid...@basnetworks.net wrote: Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax -1 Derick -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 2010-12-01, Arvids Godjuks arvids.godj...@gmail.com wrote: You are missing the point in PHP in that case. Because PHP is dynamic scripting language, public properties can be added and removed in the object on the fly. That's why there is isset and unset that works on object properties. Consider ActiveRecord, DataMappers, ORM, etc. They use that 100% to their advantage - I haven't yet seen a model witch defines all the properties in PHP code - mostly it takes table columns from DB and add these properties in dynamic way. That's why it isn't so straight forward of adding properties like you propose. The new generation of ORMs and data mappers are actually using plain old PHP objects -- which means you can define the properties up-front in your code, and the mappers then inject from whatever data source they pull from. They're *not* defining properties on the fly. (Original iterations of ActiveRecord and ORMs *were* -- but newer ones are typically not.) P.S. By the way, maybe I haven't being doing some really crazy stuff on PHP, but I rarely define getters and setters in my classes that do something except $this-val = $val and return $this-val. Well, honestly I haven't worked on some stuff developed by more that 6 programmers too (Latvia is a small county - no major epic projects at all), but still I think my point is valid. I think it *used* to be... but is getting less so with modern PHP developers, based on what I'm observing in a number of communities (ZF, Symfony, even Lithium...). 2010/12/1 presid...@basnetworks.net: public property Hours read getHours write setHours; I actually like that, though I think we should support the whole existing semantics, i.e. get/set/isset/unset. And probably keep the names, so we don't call the same thing both read and get. This doesn't make sense. To call isset() on a property, would be to ask if the property itself exists. But once defined, a property always exists (think of methods, for example). (Sorry for sending again Stas, I forgot to reply all) - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- Matthew Weier O'Phinney Project Lead| matt...@zend.com Zend Framework | http://framework.zend.com/ PGP key: http://framework.zend.com/zf-matthew-pgp-key.asc -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
presid...@basnetworks.net wrote: I feel that the downfall of this syntax, is that the get and set methods can easily be scattered at either end of a class definition. With the syntaxes I provided, it is easy to tell which of the methods a property has defined at a quick glance, because everything is in on spot. Additionally, public/private/protected/final/abstract/etc only has to be specified once on the property (but can be specified separately! - see the RFC). This means less to read, and clearer, cleaner syntax. Lastly, I think that grouping the two methods just makes sense, because a property is one conceptual object, not two. Separating the two methods makes as much sense logically as does separating a class definition into two parts. - Dennis Grouping the get and set is a good convention. But grouping all the gets (doing pretty similar things) and all the sets can be as good as it. You would need to enter into each class/project to see which convention fits better. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Wednesday, December 01, 2010 8:28:19 am presid...@basnetworks.net wrote: Is this consistent with methods? Do those share a namespace, too? (I don't actually recall off the top of my head.) methods and variables have their own namespaces. This is because they are called differently: // variable $a print $f-a; // method a() print $f-a(); But variables and properties would be called the same way (both $f-a;). Because of this, they need to share the same namespace in order to avoid ambiguity. This is in fact a feature of properties, because this way an existing variable can later be replaced with a property, and all calling code will continue to work (or at least will compile). See, here's the fundamental problem we're running into. There's three different definitions of what a property is that we keep bouncing between, each of which will dictate both syntax and semantics: 1) Properties are a smart masking layer over class members, like a smarter __get/__set, designed to make it possible to swap out in place of class members at will. In this case, both the syntax and semantics of properties should mirror class members as close as possible. 2) Properties are a short-hand for getFoo()/setFoo() methods (which in the general sense should *not* be understood to always map to class members, as discussed), designed to make typing $o-getFoo() and $o-setFoo() shorter/easier. In this case the syntax and semantics should make that clear and not confuse the user with class-member-like syntax. 3) Properties are a completely different animal, neither methods nor class members but a totally different concept. In this case the syntax should not be confusing with either methods or class members, and the semantics should probably then be taken from the most common/popular existing implementation feasible. We cannot mix #1 and #2 and expect to get something usable out the other end, nor can we defend doing so on the grounds of #3. The discussion of the proposal is doing exactly that, however, which I think is a fatal flaw. Personally, if we follow approach #1 (make them look and smell as much like class members as possible) then I'm all for it in concept. It might even simplify many of the regular arguments I have about public properties and good architecture. :-) But only if we can cleanly stick to one definition of purpose, syntax, and semantics. Treating properties as a method implementation that can work like class members if you look at them from the right angle even though they're not class members and don't really work like them is a sure-fire way to confuse the hell out of people. PHP is complicated enough without introducing wave/particle duality. --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Richard, I'd really like this feature to be part of PHP. I don't particularly like the use of what looks like a closure for the set/get. While it looks like a closure, it may not necessarily be one. What I have presented in my RFC is a syntax, but I make little assumption about how it would be implemented, as that would be out stepping my expertise. In C#, when a property gets compiled it is actually turned into two normal class methods in a special namespace. Looking at a compiled C# library with reflector will reveal this underlying implementation. So when a call to a property is compiled in C#, it is simple replaced with a call to a method. The properties themselves are nothing more than syntactic sugar. Since PHP is interpreted instead of compiled, this may not be an ideal solution, but I couldn't guess as to what would be a better method. Preferably something that re-uses the existing class method interpretation. I used to code in Delphi and I always like the way in which their properties were defined. Essentially, the setter and getter are normal methods which are cherry picked for a property [1]. ?php class TimePeriod { protected $seconds; public property Hours read getHours write setHours; protected function getHours() { return $this-seconds / 3600; } protected function setHours() { $this-seconds = $value * 3600; } // This property is read-only public property Minutes read getMinutes; protected function getMinutes() { return $this-seconds / 60; } public property Milliseconds read getMilliseconds write setMilliseconds; public function getMilliseconds() { // This method is public return $this-seconds * 60; } protected function setMilliseconds() { // This method is protected $this-seconds = $value * 3600; } } For me, the advantage here is that I can independently the methods from the property. If I want to force a subclass to implement a setter/getter, then I can abstract the function in the base class. Sure, some may say that I should be using an interface. I disagree as I probably don't want the methods to be public. Protected or even private and/or final. In the syntax I provided in my RFC, it is certainly possible to define a property with only a get or only a set method (these are implicit read-only and write-only properties). Furthermore, it is also possible to set the visibility of the get and set methods individually, as well as making either one final, static or (and I forgot to mention this in the RFC) abstract. But the advantage of my syntax, is not only can these things be set individually, but they can also be set just once for the pair, by specifying them on the property itself. This makes for cleaner and more readable code. My syntax also gives several other advantages over the delphi syntax. It is more logical, as it makes the property look more like a class variable than a class method. This makes sense because you call it like a variable. Additionally, because the get/set methods need to be contained within the body of the property definition, you immediately know if a property has both a get and a set method at a quick glance - you do not have to hunt through the class to see if there is another definition somewhere else. The classic example is one of shapes. Every shape has a public $area property, but the value would be provided by an abstract protected TShape::getArea(); method. I can also finalise them, so, for example, a triangle shape could have a final protected getArea() method and all sub classes of triangles (scalene, isosceles, equilateral) would not implement their own getArea() method. This is possible with the syntax I provided. I would suggest reading more about the C# syntax, which my suggested syntax is based off of, as it will explain all of your questions. http://msdn.microsoft.com/en-us/library/x9fsa0sw%28VS.80%29.aspx - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
RE: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hello, Hi! Nice RFC, just an idea for an alternative syntax (added to the RFC as #2): property Hours { get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; } // The variable $value holds the incoming value to be set } class TimePeriod { private $seconds; public [Hours] $hours1; public {use Hours;} $hours2; } If you change property to class or trait and get to __get you need almost no new syntax :) Right, it looks the same but the subtle difference is 'property Hours' wouldn't be registered as a class. It's just container code for get(), set() methods that would get 'compiled' into opcodes in the class TimePeriod (the property exists vs. searching for it in runtime). So you can think of it as a special 'trait' that only applies to properties. The idea behind this syntax is you can move the 'property' definition out of the class so that you can test and re-use it somewhere else (like traits). That might not be problem if you can define properties in traits (needs to be explained in the RFC): trait TimeUnits { public property Seconds { get { return $this-seconds; } set { $this-seconds = $value; }// The variable $value holds the incoming value to be set } public property Minutes { get { return $this-seconds / 60; } set { $this-seconds = $value * 60; } } public property Hours { get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; }// The variable $value holds the incoming value to be set } } class MyTime { uses TimeUnits; protected $_seconds; } I do not think that properties should make use of a trait-like syntax, as that is not what a property is about. A property is basically a layer of syntactic sugar over a pair of methods. The majority of the time when writing properties, you will not want to re-use them, so I have a hard time seeing many parallels to traits. However, it does make sense to be able to define a property as part of a trait, as again, it is basically just a pair of methods. When I get some time, I will try to add a syntax for traits to the RFC. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi: On 30 Nov 2010, at 14:42, presid...@basnetworks.net wrote: However, it does make sense to be able to define a property as part of a trait, as again, it is basically just a pair of methods. When I get some time, I will try to add a syntax for traits to the RFC. The only thing really necessary for that would be a specification on how to name/to refer to the getter/setter to be able to handle the conflicts. The rest should work out of the box. As far as I can see from the proposal. Best regards Stefna - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- Stefan Marr Software Languages Lab Vrije Universiteit Brussel Pleinlaan 2 / B-1050 Brussels / Belgium http://soft.vub.ac.be/~smarr Phone: +32 2 629 2974 Fax: +32 2 629 3525 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! I do not think that properties should make use of a trait-like syntax, as that is not what a property is about. A property is basically a layer of syntactic sugar over a pair of methods. The majority of the time when writing properties, you will not want to re-use them, so I have a hard time seeing many parallels to traits. A side note: in PHP, property actually has four methods, not two - get/set/unset/isset. -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
2010/11/29 Ángel González keis...@gmail.com: Richard Quadling wrote: As for reading $seconds directly ... Well. If you think of the element that follows read as $this-, then if the parser can handle both ... read $seconds read getSeconds then yes for both. If not, then I'd guess that the getSeconds version should be the one we use as the value may not actually exist without some processing. Richard. If it begins with $, it's a variable name, so map to that class member variable. If it is instead a plain T_STRING, take that as a member call. I'm not sure to be understanding the issue you're mentioning. If the proposal incorporated support for getting the value from a local-scoped variable (I assume the variable has to be part of the current class or one of its parents?) as well as calling the getter, then that really does seem to allow everyone everything they need. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hello Stas, I do not think that properties should make use of a trait-like syntax, as that is not what a property is about. A property is basically a layer of syntactic sugar over a pair of methods. The majority of the time when writing properties, you will not want to re-use them, so I have a hard time seeing many parallels to traits. A side note: in PHP, property actually has four methods, not two - get/set/unset/isset. That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. Because properties (as defined in my RFC) are not a variable, but rather a set of methods, I do not think there would be any way to unset them. Like a method, once they are defined, you cannot get rid of them. Therefore overloading isset and unset would not make any sense here. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Tue, 2010-11-30 at 09:15 -0500, presid...@basnetworks.net wrote: That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. Because properties (as defined in my RFC) are not a variable, but rather a set of methods, I do not think there would be any way to unset them. Like a method, once they are defined, you cannot get rid of them. Therefore overloading isset and unset would not make any sense here. This is different from the PHP Language then. You can isset() and unset() native properties. And use __isset() and __unset() magic methods. A new feature should be consistent with the language definition. johannes -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. This is also true for object properties - see magic methods. I don't see why you shouldn't be able to unset them - you can do that with regular properties... So what you imagine would happen if you call unset($foo-property) or isset($foo-property)? -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 30 November 2010 12:48, presid...@basnetworks.net wrote: Hi Richard, I'd really like this feature to be part of PHP. I don't particularly like the use of what looks like a closure for the set/get. While it looks like a closure, it may not necessarily be one. What I have presented in my RFC is a syntax, but I make little assumption about how it would be implemented, as that would be out stepping my expertise. In C#, when a property gets compiled it is actually turned into two normal class methods in a special namespace. Looking at a compiled C# library with reflector will reveal this underlying implementation. So when a call to a property is compiled in C#, it is simple replaced with a call to a method. The properties themselves are nothing more than syntactic sugar. Since PHP is interpreted instead of compiled, this may not be an ideal solution, but I couldn't guess as to what would be a better method. Preferably something that re-uses the existing class method interpretation. I used to code in Delphi and I always like the way in which their properties were defined. Essentially, the setter and getter are normal methods which are cherry picked for a property [1]. ?php class TimePeriod { protected $seconds; public property Hours read getHours write setHours; protected function getHours() { return $this-seconds / 3600; } protected function setHours() { $this-seconds = $value * 3600; } // This property is read-only public property Minutes read getMinutes; protected function getMinutes() { return $this-seconds / 60; } public property Milliseconds read getMilliseconds write setMilliseconds; public function getMilliseconds() { // This method is public return $this-seconds * 60; } protected function setMilliseconds() { // This method is protected $this-seconds = $value * 3600; } } For me, the advantage here is that I can independently the methods from the property. If I want to force a subclass to implement a setter/getter, then I can abstract the function in the base class. Sure, some may say that I should be using an interface. I disagree as I probably don't want the methods to be public. Protected or even private and/or final. In the syntax I provided in my RFC, it is certainly possible to define a property with only a get or only a set method (these are implicit read-only and write-only properties). Furthermore, it is also possible to set the visibility of the get and set methods individually, as well as making either one final, static or (and I forgot to mention this in the RFC) abstract. But the advantage of my syntax, is not only can these things be set individually, but they can also be set just once for the pair, by specifying them on the property itself. This makes for cleaner and more readable code. My syntax also gives several other advantages over the delphi syntax. It is more logical, as it makes the property look more like a class variable than a class method. This makes sense because you call it like a variable. Additionally, because the get/set methods need to be contained within the body of the property definition, you immediately know if a property has both a get and a set method at a quick glance - you do not have to hunt through the class to see if there is another definition somewhere else. The classic example is one of shapes. Every shape has a public $area property, but the value would be provided by an abstract protected TShape::getArea(); method. I can also finalise them, so, for example, a triangle shape could have a final protected getArea() method and all sub classes of triangles (scalene, isosceles, equilateral) would not implement their own getArea() method. This is possible with the syntax I provided. I would suggest reading more about the C# syntax, which my suggested syntax is based off of, as it will explain all of your questions. http://msdn.microsoft.com/en-us/library/x9fsa0sw%28VS.80%29.aspx - Dennis Thanks for your reply. Fundamentally, a big +1 from my little voice on having setters/getters in PHP. The issue of documentation is probably that the documentation tools would have to adapt. As things stand PHPDoc doesn't support namespaces, so setters/getters would just be added to the WIBNI list. With regard to the value supplied to the set method, would it make more sense for PHP to be ... set($value) { $this-seconds = $value * 3600; } or set { $this-seconds = __SETVALUE__ * 3600; } Having $value without a clear indication of where it comes from doesn't read quite right. $value is way to generic to be magically created. __SETVALUE__ (or __SOMETHINGELSE__) is clear in this regard. Richard. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY --
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Richard Quadling wrote: (I assume the variable has to be part of the current class or one of its parents?) Yes. I don't think it makes sense to have a class property actually read a global. If a project really need it (eg. some migration from procedural style to classes), then use the verbose syntax. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
I still want to keep the performance implications in mind, as this sounds like something that we'd want to use a lot but could also cost a lot more than it seems at first glance if we're not careful. By making properties in memory a little bigger one might write the accessors in the same table as the actual properties one might possibly reduce the CPU requirement abit. While one has to touch most places dealing with properties internally (while that's probably needed anyways). But well, unless there is an implementation all performance ideas are guesses ... educated guesses at best. Just to chime in on the subject of performance, here is how C# handles properties: When compiling, C# simply creates a normal class method for both the get and set method in a property. So basically, the property ceases to exist, and is replaced with two plain methods. These methods are either in their own namespace (or more likely) use a name that is not valid or possible in C# itself. After that, all calls to the property are replaced with calls to the new methods. Because of this, properties have no greater overhead than methods do, which is exactly what we want, since properties are meant to replace getter and setter methods. How much this informs performance in PHP, I do not know. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi Benjamin, I have been working with Objective-c lately, and it has a very flexible and short way to deal with properties, which could look like this in PHP : ?php class TimePeriod { protected $seconds; protected $minutes; protected $hours; @synthesize (readwrite) $hours, $minutes; @synthesize (readonly) $seconds; } NB : I intentionally skipped the @property declaration wich I believe is a specific need for objc (used to allow dot syntax usage). In objc, this notation allows to : - use dot syntax for accessing properties (using their getters/setters only, all properties are protected in objc) - write your own getters/setters (only the missing ones are generated) In Php, the pros of this syntax would be : - very concise - no interference with existing code (except certain conditions) - allows to override generated getters and setters with custom code - may work with the existing code base The cons : - new syntax to learn (even if it is quite simple) - need to use pre-determined setters and getters names to keep simplicity, which could potentially lead to BC break in some (hopefully rare) cases. What do you think about it ? The issue I have with this syntax is it does not look similar to any other syntax in PHP (that I know of). It looks out of place. Additionally, I believe the readonly and writeonly keywords are slated to have other meanings (as noted in my RFC), and this would cause confusion. Also, if a property is defined readonly, when we inherit the class, how do we now define the write method? I don't see any logical or coherent way with this syntax. Lastly, your syntax misses the point of properties. The point is not to put an alias on an existing variable, or even to read and write to different variables. The real power is that the get and set are methods! For example, in the get method, I could make a soap call to another server, load in a result document and get my value from there. In a set method, I could make a database call and store the value. These are extreme scenarios, but they show the power of properties. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
This is a very well-written and well-thought through RFC, Dennis. Nicely done. Thank you! First of all, I have generally found the Bean-style getter/setter approach to be a sign of poor encapsulation to begin with. You shouldn't be mucking with internal elements of an object in the first place, period. More details on that here: http://www.garfieldtech.com/blog/property-visibility Interesting post, although I can't say I agree with your views. Your post leaves me wondering how the user is expected to get or give data to a class (for example, if I'm not supposed to do $customer-name or $customer-getName(), how do I get the customers name?). Additionally, you are forgetting the real power of properties, which is the ability to generate a get value, and process a set value, because get/set are methods. Properties are hardly just an indirection layer around an underlying piece of data. However, I do see a potential use here if properties are treated conceptually as an entirely new concept and not as an indirection layer for class properties. That would make them more akin to a class that has both methods and also implements ArrayAccess for properties of the conceptual object, that may not have anything to do with internal class members. Viewed from that angle, I would have the following comments: - I strongly prefer the first syntax over the second. The property keyword improves readability, and the closing semi-colon is going to be forgotten on a daily basis. I still forget sometimes when to use it and when not to when writing Javascript. :-) I cannot speak to the engine complexity involved but from a PHP-autor point of view I believe the first syntax is much easier to use. Right, the property keyword ties together with the function keyword, and the semi-colon provides no real purpose to the author. I have however been told that the semi-colon is important from an internal perspective, and would ease the implementation. - The use of identical syntax for class members and properties could create confusion as to which is which. One could argue that is the point, but only if we view properties as just an indirection layer around the physical class members, which as I noted above I believe is a poor architectural design. There may not be an alternative here, but I mention it for completeness. Using the same syntax is exactly the point of properties, and is what gives them their power. From the outside, properties should look and act no differently than a simple variable class member. This is encapsulation at its greatest, because it hides the implementation! It is not important for a user of a class to know which is a property and which is a variable underneath. To use a different syntax would be to expose that. Another cool side effect of variables and properties sharing the same syntax, is that a variable can be replaced with a property that has the same name, at any time (and vice-versa) and all code that calls that member will continue to work. This is eternally useful when writing class libraries, where you want to do something more advanced with a class variable internally, but do not want to break the API. - The layering of accessibility keywords I find intriguing, in a mostly good way. That can offer a great deal of flexibility to control who can do what when. However, I am concerned about the confusion possible in the following: public property Hours { get { return $this-seconds / 3600; } protected set { $this-seconds = $value * 3600; } } The set method is then scoped with two different visibility directives: public and protected. Which applies? Since both are optional (presumably) I can see a potential here for confusion, especially if you also start mentioning keywords like final. This should be made more definitive if possible. The inner keywords always take precedence over the outer ones. So in this case by making the property public, and the set protected, it means the get is public and the set is protected. This would mean the same thing: property Hours { public get { return $this-seconds / 3600; } protected set { $this-seconds = $value * 3600; } } However, many people prefer to write it the way you quoted above, because they don't like to leave the outer property without a visibility keyword. Perhaps a better choice (which is also equivalent) would have been this: protected property Hours { public get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; } } Each one of these scenarios works as described in C#, and rarely causes confusion. The rule of thumb, is that if a get/set has no visibility keyword, it inherits the one from the outer property. I think that is fairly simple. - If interfaces can declare properties (niiice), Traits should be able to provide them. That provides full parallelism with methods, which I believe developers will expect. I agree, properties
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
... /** * */ public function set name(string $name) { $this-name = htmlentities($name); $this-name = strip_tags($this-name); } /** * */ public function get name($name) { return $this-name; } Greetings, Christian For whatever it's worth, I think that this syntax fits much better into PHP than do either of the those in the RFC. I feel that the downfall of this syntax, is that the get and set methods can easily be scattered at either end of a class definition. With the syntaxes I provided, it is easy to tell which of the methods a property has defined at a quick glance, because everything is in on spot. Additionally, public/private/protected/final/abstract/etc only has to be specified once on the property (but can be specified separately! - see the RFC). This means less to read, and clearer, cleaner syntax. Lastly, I think that grouping the two methods just makes sense, because a property is one conceptual object, not two. Separating the two methods makes as much sense logically as does separating a class definition into two parts. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
public property Hours read getHours write setHours; I actually like that, though I think we should support the whole existing semantics, i.e. get/set/isset/unset. And probably keep the names, so we don't call the same thing both read and get. This doesn't make sense. To call isset() on a property, would be to ask if the property itself exists. But once defined, a property always exists (think of methods, for example). (Sorry for sending again Stas, I forgot to reply all) - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 11/30/10 6:15 PM, presid...@basnetworks.net wrote: public property Hours read getHours write setHours; I actually like that, though I think we should support the whole existing semantics, i.e. get/set/isset/unset. And probably keep the names, so we don't call the same thing both read and get. This doesn't make sense. To call isset() on a property, would be to ask if the property itself exists. But once defined, a property always exists (think of methods, for example). (Sorry for sending again Stas, I forgot to reply all) - Dennis True, but if part of the intent (as noted in a previous email) is to provide a mechanism that looks to the outside world like a class member, and therefore one can switch between the two without breaking an API, then isset/unset should have some sort of useful meaning. They do for __*() magic methods and for ArrayAccess (albeit named differently), so there should be some sort of meaningful definition here. Otherwise they are only half a drop-in/break-no-API replacement for a class member. --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
You are missing the point in PHP in that case. Because PHP is dynamic scripting language, public properties can be added and removed in the object on the fly. That's why there is isset and unset that works on object properties. Consider ActiveRecord, DataMappers, ORM, etc. They use that 100% to their advantage - I haven't yet seen a model witch defines all the properties in PHP code - mostly it takes table columns from DB and add these properties in dynamic way. That's why it isn't so straight forward of adding properties like you propose. P.S. By the way, maybe I haven't being doing some really crazy stuff on PHP, but I rarely define getters and setters in my classes that do something except $this-val = $val and return $this-val. Well, honestly I haven't worked on some stuff developed by more that 6 programmers too (Latvia is a small county - no major epic projects at all), but still I think my point is valid. 2010/12/1 presid...@basnetworks.net: public property Hours read getHours write setHours; I actually like that, though I think we should support the whole existing semantics, i.e. get/set/isset/unset. And probably keep the names, so we don't call the same thing both read and get. This doesn't make sense. To call isset() on a property, would be to ask if the property itself exists. But once defined, a property always exists (think of methods, for example). (Sorry for sending again Stas, I forgot to reply all) - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. This is also true for object properties - see magic methods. I don't see why you shouldn't be able to unset them - you can do that with regular properties... So what you imagine would happen if you call unset($foo-property) or isset($foo-property)? As I replied elsewhere: Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. __isset is a whole different matter, without it we would have to assume that every possible member name in a class either exists or does not exist. This is because __isset, __get, __set and __unset can handle ANY member name. Properties are bound to a single member name, therefore, they always exist, unless you were to physically remove that property from the class, which, like methods, that is not possible. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 11/30/10 5:55 PM, presid...@basnetworks.net wrote: This is a very well-written and well-thought through RFC, Dennis. Nicely done. Thank you! First of all, I have generally found the Bean-style getter/setter approach to be a sign of poor encapsulation to begin with. You shouldn't be mucking with internal elements of an object in the first place, period. More details on that here: http://www.garfieldtech.com/blog/property-visibility Interesting post, although I can't say I agree with your views. Your post leaves me wondering how the user is expected to get or give data to a class (for example, if I'm not supposed to do $customer-name or $customer-getName(), how do I get the customers name?). Additionally, you are forgetting the real power of properties, which is the ability to generate a get value, and process a set value, because get/set are methods. Properties are hardly just an indirection layer around an underlying piece of data. The idea of a -getName() method for retrieving a person's name is fine. My point there is that any assumption that it corresponds to a -name class member (as Bean definitions require) is invalid on its face. (The context there is a lengthy ongoing debate regarding the use of public vs. protected class members, with my basic point being that class members are an implementation detail and if you care about them in the first place then you have a bug. Yes, it's a deliberately stringent position.) What I'm seeing here is that whether properties are intended as an indirection layer for class members (eg, a more robust __get/__set) or not is a fuzzy question. On the one hand they are (since the goal of the syntax is to make it irrelevant to the caller which is happening), but on the other they're supposed to be something different that can do all kinds of on the fly behavior. I'm not going to say pick one! because both are valid use cases with significant benefit, but it is a point of potential confusion in both the discussion and eventual documentation. Right, the property keyword ties together with the function keyword, and the semi-colon provides no real purpose to the author. I have however been told that the semi-colon is important from an internal perspective, and would ease the implementation. Another reason that the function keyword should remain mandatory, IMO. :-) I cannot speak to the implementation details, but I do know that the semi-colon would horribly confuse a lot of people. In C#, get and set methods of a property are compiled down to methods, and calls to a property are changed to calls to those methods. Therefore their performance in C# is exactly that of a method call. This is ideal, since properties are meant to be a replacement for the standard getXYZ/setXYZ design pattern. I cannot speak to the implementation potential in PHP as I have never looked at the compiler's code. - Which also brings up an interesting question: class Foo { public $a = 1; protected $b = 2; public property $a { get { return 3; } } public property $b { get { return 4; } } } $f = new Foo(); print $f-a . PHP_EOL; // Does this print 1 or 3? print $f-b . PHP_EOL; // Does this print 2 or 4, or error? Both of those throw an error. Properties and variables share the same namespace, so you cannot define a property and variable with the same name. Is this consistent with methods? Do those share a namespace, too? (I don't actually recall off the top of my head.) This is what I would imagine seeing, and would compile: class Foo { private $_a = 1; protected $_b = 2; public property $a { get { return 3; } } public property $b { get { return 4; } } } As you can see, there is no conflict or confusion this way. True, although for the record I have always detested the underscore prefix on variables as a difficult to read hack. :-) That's all I got for now. Once again, nice RFP but still needs some thinking. Of course, that is why I am harnessing your collective brains! BRAAAINS! --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Thanks for your reply. Fundamentally, a big +1 from my little voice on having setters/getters in PHP. The issue of documentation is probably that the documentation tools would have to adapt. As things stand PHPDoc doesn't support namespaces, so setters/getters would just be added to the WIBNI list. Here is a reply I wrote to Christan Kaps on the same subject: Christan Wrote: I like the idea of the property get/set syntax, but in my opinion it doesn't figure with PHP's syntax, because it breaks the readability. The problem for me is the nesting of the inner set and get. How do you document these syntax. /** * */ public $name { /** * */ get { return $this-name; } /** * */ set { $this-name = htmlentities($value); $this-name = strip_tags($this-name); } }; Typically you only document the property as a whole, and not the individual get and set method. Since they are a pair, there should be no reason to document them separately. If the get method is doing something totally different from the set, then they should not be paired, as that is confusing. In C# you would typically see documentation like this: Only a get method: /// summaryGets the duration of the Timespan in seconds./summary public int Seconds { get; } Only a set method: /// summarySets the duration of the Timespan in seconds./summary public int Seconds { set; } Both a get and set method: /// summaryGets/sets the duration of the Timespan in seconds./summary public int Seconds { get; set; } With regard to the value supplied to the set method, would it make more sense for PHP to be ... set($value) { $this-seconds = $value * 3600; } or set { $this-seconds = __SETVALUE__ * 3600; } Having $value without a clear indication of where it comes from doesn't read quite right. $value is way to generic to be magically created. __SETVALUE__ (or __SOMETHINGELSE__) is clear in this regard. That is a good point. In C# it is simple the variable value, which is where I got $value from. Rather magicy, yes. A constant could work, and would be more in line with PHP's magic constants. Just a quick question though, can a constant store all of the same data variable can? What about a reference? Also, sometimes users in C# like to modify the contents of the value variable before using it for something else. If it were a constant this would not be possible, you would have to define a new variable, then copy the value from the constant, which seems unnecessarily cumbersome. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 11/30/10 6:29 PM, presid...@basnetworks.net wrote: That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. Because properties (as defined in my RFC) are not a variable, but rather a set of methods, I do not think there would be any way to unset them. Like a method, once they are defined, you cannot get rid of them. Therefore overloading isset and unset would not make any sense here. This is different from the PHP Language then. You can isset() and unset() native properties. And use __isset() and __unset() magic methods. A new feature should be consistent with the language definition. Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. Consistency with other languages must also be balanced against consistency within PHP. Both are important. Class members and both existing class-member-ish mechanisms (__magic and ArrayAccess) have the concept of isset/unset. A third class-member-ish (syntactically speaking) mechanism will be expected to have the same set of primitives. To not have them will be a major language WTF, because to a normal user of an object they *look* like class members, not methods, they *taste* like class members, not methods, so they should *act* like class members, not methods. Basically, properties can only be considered a drop-in replacement for class members (as you've stated, correctly, is one of the potential big wins for them) if they fully emulate their behavior. If they do not, then it is incorrect to say that they can be swapped in for a class member without changing an API. __isset() is a whole different matter, without it we would have to assume that every possible member name either exists or does not exist. This is because __isset can handle ANY member name. Properties are bound to a single member name, therefore, they always exist, unless you were to physically remove that property from the class, which, like methods, that is not possible. No, but it can be easily emulated. Actually, I can even think of a concrete use case. Suppose I have an object that acts as a facade for a remote object over SOAP, REST, or whatever. It is using properties to represent attributes of a remote, say, insurance account. I want to know if a beneficiary has been set on the account. The most straightforward way to do so is if (isset($account-beneficiary)) { print $account-beneficiary-name; } If we are implementing such logic via __get(), we can do exactly that. If we are implementing it via properties, we should still be able to. Forcing the user to know that he needs to do it this way instead, but only if we're using properties rather than __get(): if ($account-hasBeneficiary()) { print $account-beneficiary-name; } is violating the principle of encapsulation as it means the user needs to know which of the three forms of $account-beneficiary happens to be in use. Thinking about properties further, actually, there's two other (related) considerations that always give me grief when dealing with __get: Reference returns and complex member variables. If I want a reference to a class member, I can very easily do this: $foo = $bar-baz; If -baz is accessed via __get(), then that only works if __get() is defined as function __get($var) to start with. That's another encapsulation break. Similarly, the following does exactly what you'd expect with a normal class member: $foo-bar['baz']-narf = 'poink'; If $foo-bar is returned via __get(), though, then the above statement executes but does not actually save anything... *unless* __get() was defined to return by reference as above. Details of my adventures in __get() insanity here, including performance considerations: http://www.garfieldtech.com/blog/magical-php-call How would properties deal with those scenarios? (The answer may well be it doesn't, screw off, that's way too esoteric, as it is for __get(), but we should at least consider if it's possible to handle those gracefully.) --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Object properties (or members, classic -var, not this proposed syntax) CURRENTLY, work this way: php -r 'class foo { public $bar; } $foo = new foo(); var_dump(isset($foo-bar));' bool(false) This is because you are confusing PHP's isset() with a property_exists(). Is set. Is the variable (or member/property) set to a value? In this case, both isset() and unset() work with the property get/set you are proposing. Imagine: $results = $db-query('SELECT SQL_CALC_FOUND_ROWS * FROM some_table WHERE foo = 'bar'); if (isset($results-count)) { foreach ($results-getResult() as $result) { // Do something } } where isset() would hit: protected property count { isset { $result = $this-execute('SELECT FOUND_ROWS()'); $this-count = $result-getColumn(); if ($this-count == 0) { return false; } return false; } } Not an ideal example, but it gives you an IDEA off the top of my head of a way to take advantage of it - Davey On Nov 30, 2010, at 7:31 PM, presid...@basnetworks.net wrote: That is true for PHP variables. isset is basically saying does this variable exist, and unset is saying to get rid of it. This is also true for object properties - see magic methods. I don't see why you shouldn't be able to unset them - you can do that with regular properties... So what you imagine would happen if you call unset($foo-property) or isset($foo-property)? As I replied elsewhere: Its not a matter of consistency - Properties, as a cross-language concept are not meant to work that way. You need to think of a property as a set of two methods that just have a pretty syntax. Methods cannot be unset, and nor should properties be allowed to. isset() should simply tell us whether a property with the specified name is part of the class or not. isset() in the way you suggest would just be confusing. It would allow is to say that a property does not exist, when in fact it does exist. This is not logical. __isset is a whole different matter, without it we would have to assume that every possible member name in a class either exists or does not exist. This is because __isset, __get, __set and __unset can handle ANY member name. Properties are bound to a single member name, therefore, they always exist, unless you were to physically remove that property from the class, which, like methods, that is not possible. - Dennis -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Sun, Nov 28, 2010 at 11:48 PM, Christian Kaps christian.k...@mohiva.com wrote: ... /** * */ public function set name(string $name) { $this-name = htmlentities($name); $this-name = strip_tags($this-name); } /** * */ public function get name($name) { return $this-name; } Greetings, Christian For whatever it's worth, I think that this syntax fits much better into PHP than do either of the those in the RFC. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 28 November 2010 23:18, presid...@basnetworks.net wrote: Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax Thanks, Dennis Robinson I'd really like this feature to be part of PHP. I don't particularly like the use of what looks like a closure for the set/get. I used to code in Delphi and I always like the way in which their properties were defined. Essentially, the setter and getter are normal methods which are cherry picked for a property [1]. ?php class TimePeriod { protected $seconds; public property Hours read getHours write setHours; protected function getHours() { return $this-seconds / 3600; } protected function setHours() { $this-seconds = $value * 3600; } // This property is read-only public property Minutes read getMinutes; protected function getMinutes() { return $this-seconds / 60; } public property Milliseconds read getMilliseconds write setMilliseconds; public function getMilliseconds() { // This method is public return $this-seconds * 60; } protected function setMilliseconds() { // This method is protected $this-seconds = $value * 3600; } } For me, the advantage here is that I can independently the methods from the property. If I want to force a subclass to implement a setter/getter, then I can abstract the function in the base class. Sure, some may say that I should be using an interface. I disagree as I probably don't want the methods to be public. Protected or even private and/or final. The classic example is one of shapes. Every shape has a public $area property, but the value would be provided by an abstract protected TShape::getArea(); method. I can also finalise them, so, for example, a triangle shape could have a final protected getArea() method and all sub classes of triangles (scalene, isosceles, equilateral) would not implement their own getArea() method. The downside is certainly that the code is more verbose than I would guess many people would like. Regards, Richard. [1] http://www.delphibasics.co.uk/RTL.asp?Name=Property -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! Nice RFC, just an idea for an alternative syntax (added to the RFC as #2): property Hours { get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; } // The variable $value holds the incoming value to be set } class TimePeriod { private $seconds; public [Hours] $hours1; public {use Hours;} $hours2; } If you change property to class or trait and get to __get you need almost no new syntax :) -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Richard Quadling wrote: I'd really like this feature to be part of PHP. I don't particularly like the use of what looks like a closure for the set/get. I used to code in Delphi and I always like the way in which their properties were defined. Essentially, the setter and getter are normal methods which are cherry picked for a property [1]. ?php class TimePeriod { protected $seconds; public property Hours read getHours write setHours; protected function getHours() { return $this-seconds / 3600; } protected function setHours() { $this-seconds = $value * 3600; } // This property is read-only public property Minutes read getMinutes; protected function getMinutes() { return $this-seconds / 60; } public property Milliseconds read getMilliseconds write setMilliseconds; public function getMilliseconds() { // This method is public return $this-seconds * 60; } protected function setMilliseconds() { // This method is protected $this-seconds = $value * 3600; } } For me, the advantage here is that I can independently the methods from the property. If I want to force a subclass to implement a setter/getter, then I can abstract the function in the base class. Sure, some may say that I should be using an interface. I disagree as I probably don't want the methods to be public. Protected or even private and/or final. The classic example is one of shapes. Every shape has a public $area property, but the value would be provided by an abstract protected TShape::getArea(); method. I can also finalise them, so, for example, a triangle shape could have a final protected getArea() method and all sub classes of triangles (scalene, isosceles, equilateral) would not implement their own getArea() method. The downside is certainly that the code is more verbose than I would guess many people would like. Regards, Richard. [1] http://www.delphibasics.co.uk/RTL.asp?Name=Property setMilliseconds() should have $value as parameter instead of a magic name. What about allowing this syntax to attach the property to a variable? For instance: ?php class TimePeriod { protected $seconds; protected $minutes; protected $hours; public property Seconds read $seconds write setSeconds; public property Minutes read $seconds write setMinutes; public property Hours read $seconds write setHours; public function setSeconds($seconds) { if ($seconds = 0 $seconds 60) $this-seconds = $seconds; } public function setMinutes($minutes) { if ($minutes = 0 $minutes 60) $this-minutes = $minutes; } public function setHours($hours) { if ($hours = 0 $hours 24) $this-hours = $hours; } } We only want to perform checks on write, so instead of writing the trivial getters, the property is set to the variable itself. Child classes could reattach it to a function if needing more control. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 2010-11-29, Richard Quadling rquadl...@gmail.com wrote: On 28 November 2010 23:18, presid...@basnetworks.net wrote: Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax Thanks, Dennis Robinson I'd really like this feature to be part of PHP. I don't particularly like the use of what looks like a closure for the set/get. I used to code in Delphi and I always like the way in which their properties were defined. Essentially, the setter and getter are normal methods which are cherry picked for a property [1]. ?php class TimePeriod { protected $seconds; public property Hours read getHours write setHours; protected function getHours() { return $this-seconds / 3600; } protected function setHours() { $this-seconds = $value * 3600; } snip For me, the advantage here is that I can independently the methods from the property. If I want to force a subclass to implement a setter/getter, then I can abstract the function in the base class. I prefer this as well. It often aids readability to use fluent interfaces when performing operations that are simply changing state, and being able to call the setters directly would make that possible: $time-setHours(3) -setMinutes(17) -setSeconds(34); Additionally, this seems like a very natural fit with traits, making it possible to really succinctly define behavior to mix in with classes. -- Matthew Weier O'Phinney Project Lead| matt...@zend.com Zend Framework | http://framework.zend.com/ PGP key: http://framework.zend.com/zf-matthew-pgp-key.asc -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 2010-11-29, Stas Malyshev smalys...@sugarcrm.com wrote: Nice RFC, just an idea for an alternative syntax (added to the RFC as #2): property Hours { get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; } // The variable $value holds the incoming value to be set } class TimePeriod { private $seconds; public [Hours] $hours1; public {use Hours;} $hours2; } If you change property to class or trait and get to __get you need almost no new syntax :) Not really. With __get() and __set(), it's entirely likely that the class into which the trait is mixed in might override this already -- and not take into account the properties. That would be quite a brittle solution. -- Matthew Weier O'Phinney Project Lead| matt...@zend.com Zend Framework | http://framework.zend.com/ PGP key: http://framework.zend.com/zf-matthew-pgp-key.asc -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi! public property Hours read getHours write setHours; I actually like that, though I think we should support the whole existing semantics, i.e. get/set/isset/unset. And probably keep the names, so we don't call the same thing both read and get. Having them called __get etc. would even remove the need for another keyword, probably, but this looks ugly :( -- Stanislav Malyshev, Software Architect SugarCRM: http://www.sugarcrm.com/ (408)454-6900 ext. 227 -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
RE: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Mon Nov 29 09:27 AM, Stas Malyshev wrote: Hi! Nice RFC, just an idea for an alternative syntax (added to the RFC as #2): property Hours { get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; } // The variable $value holds the incoming value to be set } class TimePeriod { private $seconds; public [Hours] $hours1; public {use Hours;} $hours2; } If you change property to class or trait and get to __get you need almost no new syntax :) Right, it looks the same but the subtle difference is 'property Hours' wouldn't be registered as a class. It's just container code for get(), set() methods that would get 'compiled' into opcodes in the class TimePeriod (the property exists vs. searching for it in runtime). So you can think of it as a special 'trait' that only applies to properties. The idea behind this syntax is you can move the 'property' definition out of the class so that you can test and re-use it somewhere else (like traits). That might not be problem if you can define properties in traits (needs to be explained in the RFC): trait TimeUnits { public property Seconds { get { return $this-seconds; } set { $this-seconds = $value; }// The variable $value holds the incoming value to be set } public property Minutes { get { return $this-seconds / 60; } set { $this-seconds = $value * 60; } } public property Hours { get { return $this-seconds / 3600; } set { $this-seconds = $value * 3600; }// The variable $value holds the incoming value to be set } } class MyTime { uses TimeUnits; protected $_seconds; } -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 11/29/10 11:51 AM, Jonathan Bond-Caron wrote: Right, it looks the same but the subtle difference is 'property Hours' wouldn't be registered as a class. It's just container code for get(), set() methods that would get 'compiled' into opcodes in the class TimePeriod (the property exists vs. searching for it in runtime). So you can think of it as a special 'trait' that only applies to properties. The idea behind this syntax is you can move the 'property' definition out of the class so that you can test and re-use it somewhere else (like traits). That might not be problem if you can define properties in traits (needs to be explained in the RFC): I think I'd prefer to use Traits for externally-defined properties rather than defining a new top-level construct. It's fewer moving parts and we don't need to figure out how autoloading would be affected. (Autoload would work the same way it does now for traits... whatever that is.) That would then imply we do need to be able to declare the existence of a property and whether it has get, set, or both independently of the definition, just like methods, so that we can have a proper interface/trait split for properties just as for methods. --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 11/29/10 8:30 AM, Ángel González wrote: What about allowing this syntax to attach the property to a variable? For instance: ?php class TimePeriod { protected $seconds; protected $minutes; protected $hours; public property Seconds read $seconds write setSeconds; public property Minutes read $seconds write setMinutes; public property Hours read $seconds write setHours; public function setSeconds($seconds) { if ($seconds= 0 $seconds 60) $this-seconds = $seconds; } public function setMinutes($minutes) { if ($minutes= 0 $minutes 60) $this-minutes = $minutes; } public function setHours($hours) { if ($hours= 0 $hours 24) $this-hours = $hours; } } We only want to perform checks on write, so instead of writing the trivial getters, the property is set to the variable itself. Child classes could reattach it to a function if needing more control. Another advantage here would presumably be performance. If there's no getter defined then the engine could simply map $foo-bar to the class member directly (which is really fast) and not to a method, so there's no added overhead there. That still leaves the question of what happens with name collisions, though. ... and that makes me think that someone is sure to ask about runtime changes to the property structure sooner or later, as we keep asking about methods (and *sort of* have figured out with binding closures to objects, if that did actually get committed), so I'll go ahead and ask it now. :-) --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Mon, 2010-11-29 at 12:18 -0600, la...@garfieldtech.com wrote: Another advantage here would presumably be performance. If there's no getter defined then the engine could simply map $foo-bar to the class member directly (which is really fast) and not to a method, so there's no added overhead there. That still leaves the question of what happens with name collisions, though. Don't kow what you mean by the engine in this case? The compiler? - no the compiler can't a) it has no idea what type $foo is b) think about inheritance etc. The executor - well there's no win possible. johannes -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On 11/29/10 12:41 PM, Johannes Schlüter wrote: On Mon, 2010-11-29 at 12:18 -0600, la...@garfieldtech.com wrote: Another advantage here would presumably be performance. If there's no getter defined then the engine could simply map $foo-bar to the class member directly (which is really fast) and not to a method, so there's no added overhead there. That still leaves the question of what happens with name collisions, though. Don't kow what you mean by the engine in this case? The compiler? - no the compiler can't a) it has no idea what type $foo is b) think about inheritance etc. The executor - well there's no win possible. johannes I was referring to the compiler I guess. I don't do C so I have no idea what it's capable of. If that's not a possible performance optimization point, then blargh. I still want to keep the performance implications in mind, as this sounds like something that we'd want to use a lot but could also cost a lot more than it seems at first glance if we're not careful. --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Mon, 2010-11-29 at 13:40 -0600, la...@garfieldtech.com wrote: I still want to keep the performance implications in mind, as this sounds like something that we'd want to use a lot but could also cost a lot more than it seems at first glance if we're not careful. By making properties in memory a little bigger one might write the accessors in the same table as the actual properties one might possibly reduce the CPU requirement abit. While one has to touch most places dealing with properties internally (while that's probably needed anyways). But well, unless there is an implementation all performance ideas are guesses ... educated guesses at best. johannes -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Richard Quadling wrote: As for reading $seconds directly ... Well. If you think of the element that follows read as $this-, then if the parser can handle both ... read $seconds read getSeconds then yes for both. If not, then I'd guess that the getSeconds version should be the one we use as the value may not actually exist without some processing. Richard. If it begins with $, it's a variable name, so map to that class member variable. If it is instead a plain T_STRING, take that as a member call. I'm not sure to be understanding the issue you're mentioning. -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi ! This is my first email here (I'm just a PHP user, with only very basic C skills, but I'm working on it), and I would love to contribute to this project. I have been working with Objective-c lately, and it has a very flexible and short way to deal with properties, which could look like this in PHP : ?php class TimePeriod { protected $seconds; protected $minutes; protected $hours; @synthesize (readwrite) $hours, $minutes; @synthesize (readonly) $seconds; } NB : I intentionally skipped the @property declaration wich I believe is a specific need for objc (used to allow dot syntax usage). In objc, this notation allows to : - use dot syntax for accessing properties (using their getters/setters only, all properties are protected in objc) - write your own getters/setters (only the missing ones are generated) In Php, the pros of this syntax would be : - very concise - no interference with existing code (except certain conditions) - allows to override generated getters and setters with custom code - may work with the existing code base The cons : - new syntax to learn (even if it is quite simple) - need to use pre-determined setters and getters names to keep simplicity, which could potentially lead to BC break in some (hopefully rare) cases. What do you think about it ? Regards, Benjamin Le 29 nov. 2010 à 17:10, Richard Quadling a écrit : 2010/11/29 Ángel González keis...@gmail.com: Richard Quadling wrote: setMilliseconds() should have $value as parameter instead of a magic name. What about allowing this syntax to attach the property to a variable? For instance: ?php class TimePeriod { protected $seconds; protected $minutes; protected $hours; public property Seconds read $seconds write setSeconds; public property Minutes read $seconds write setMinutes; public property Hours read $seconds write setHours; public function setSeconds($seconds) { if ($seconds = 0 $seconds 60) $this-seconds = $seconds; } public function setMinutes($minutes) { if ($minutes = 0 $minutes 60) $this-minutes = $minutes; } public function setHours($hours) { if ($hours = 0 $hours 24) $this-hours = $hours; } } We only want to perform checks on write, so instead of writing the trivial getters, the property is set to the variable itself. Child classes could reattach it to a function if needing more control. Ouch. I messed up on the example code. Completely forget that there was a parameter to process... As for reading $seconds directly ... Well. If you think of the element that follows read as $this-, then if the parser can handle both ... read $seconds read getSeconds then yes for both. If not, then I'd guess that the getSeconds version should be the one we use as the value may not actually exist without some processing. Richard. -- Richard Quadling Twitter : EE : Zend @RQuadling : e-e.com/M_248814.html : bit.ly/9O8vFY -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
On Sunday, November 28, 2010 5:18:40 pm presid...@basnetworks.net wrote: Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax Thanks, Dennis Robinson This is a very well-written and well-thought through RFC, Dennis. Nicely done. That said, I am not yet convinced. :-) First of all, I have generally found the Bean-style getter/setter approach to be a sign of poor encapsulation to begin with. You shouldn't be mucking with internal elements of an object in the first place, period. More details on that here: http://www.garfieldtech.com/blog/property-visibility However, I do see a potential use here if properties are treated conceptually as an entirely new concept and not as an indirection layer for class properties. That would make them more akin to a class that has both methods and also implements ArrayAccess for properties of the conceptual object, that may not have anything to do with internal class members. Viewed from that angle, I would have the following comments: - I strongly prefer the first syntax over the second. The property keyword improves readability, and the closing semi-colon is going to be forgotten on a daily basis. I still forget sometimes when to use it and when not to when writing Javascript. :-) I cannot speak to the engine complexity involved but from a PHP-autor point of view I believe the first syntax is much easier to use. - The use of identical syntax for class members and properties could create confusion as to which is which. One could argue that is the point, but only if we view properties as just an indirection layer around the physical class members, which as I noted above I believe is a poor architectural design. There may not be an alternative here, but I mention it for completeness. - I concur with the RFP's preference for implicit write-only properties rather than explicit, as it seems more flexible. - The layering of accessibility keywords I find intriguing, in a mostly good way. That can offer a great deal of flexibility to control who can do what when. However, I am concerned about the confusion possible in the following: public property Hours { get { return $this-seconds / 3600; } protected set { $this-seconds = $value * 3600; } } The set method is then scoped with two different visibility directives: public and protected. Which applies? Since both are optional (presumably) I can see a potential here for confusion, especially if you also start mentioning keywords like final. This should be made more definitive if possible. - If interfaces can declare properties (niiice), Traits should be able to provide them. That provides full parallelism with methods, which I believe developers will expect. - I am curious what the performance implication would be. For instance, I've benchmarked both magic property access (__get()) and ArrayAccess to be around 4 times as slow as accessing a class member. http://www.garfieldtech.com/blog/benchmarking-magic Since in essence what is happening here is binding a function to fire when a class member is accessed (given the identical syntax), I'm concerned that there would be a similar performance issue. A 4x slower performance cost would make me avoid properties in favor of class members unless I absolutely needed them. A 2x or less I could see making more use of. - Which also brings up an interesting question: class Foo { public $a = 1; protected $b = 2; public property $a { get { return 3; } } public property $b { get { return 4; } } } $f = new Foo(); print $f-a . PHP_EOL; // Does this print 1 or 3? print $f-b . PHP_EOL; // Does this print 2 or 4, or error? I'm sure there's arguments every which way. My preference would be for properties to always win over class members, followed by the above code sample being a compile error. It gets even tricker when you introduce inheritance. If a child class has a [property|class member] of the same name as a parent's [class member| property], then what? That's all I got for now. Once again, nice RFP but still needs some thinking. --Larry Garfield -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
hi, Great job, very well written proposal. Quick notice: the readonly keyword work without being used with a method (or the default getter/setter): class A { public readonly propro; } The writeonly property (useful from time to time) is not supported by default but using the custom definitions. I'm all in favour of having that in PHP. However not in an immediate future (ie 5.4) but the next major version. Cheers, On Mon, Nov 29, 2010 at 12:18 AM, presid...@basnetworks.net wrote: Hello, This is my first time using a mailing list, so please bear with me. Some time back I suggested that PHP should have a property get/set syntax similar to that of Microsoft's C# language. One of the PHP developers suggested that if I were serious about it, I should write an RFC. I have done just that, and I would now like to present my RFC to everyone here in internals, in order to start a discussion on the topic. The RFC: Many modern languages have a special syntax for writing get/set method pairs. All that PHP currently supports is __get and __set, which while great for writing generic get/set methods is nearly useless when it comes to individual properties. Our only other choice is the age old process of writing custom class methods to make our get/set methods. Not only does this lack any kind of uniformity, but it also complicates the syntax ($foo-getBar() and $foo-setBar('baz') instead of $foo-bar and $foo-bar='baz'). I believe that if PHP is going embrace modern object-oriented design, including encapsulation, than it needs a modern solution to property getters and setters. I wont add much more here, but rather let the RFC itself do the talking. It is fairly well fleshed out, and should explain everything clearly enough. Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax Thanks, Dennis Robinson -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php -- Pierre @pierrejoye | http://blog.thepimp.net | http://www.libgd.org -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php
Re: [PHP-DEV] RFC: C-sharp style property get/set syntax for PHP
Hi, I like the idea of the property get/set syntax, but in my opinion it doesn't figure with PHP's syntax, because it breaks the readability. The problem for me is the nesting of the inner set and get. How do you document these syntax. /** * */ public $name { /** * */ get { return $this-name; } /** * */ set { $this-name = htmlentities($value); $this-name = strip_tags($this-name); } }; What I also miss is the lack of type hinting. As I see it, it isn't possible with this syntax. I would prefer the syntax from ActionScript. This is more like the normal PHP function syntax with an additional set or get keyword. /** * */ public function set name(string $name) { $this-name = htmlentities($name); $this-name = strip_tags($this-name); } /** * */ public function get name($name) { return $this-name; } Greetings, Christian On Sun, 28 Nov 2010 18:18:40 -0500, presid...@basnetworks.net wrote: Hello, This is my first time using a mailing list, so please bear with me. Some time back I suggested that PHP should have a property get/set syntax similar to that of Microsoft's C# language. One of the PHP developers suggested that if I were serious about it, I should write an RFC. I have done just that, and I would now like to present my RFC to everyone here in internals, in order to start a discussion on the topic. The RFC: Many modern languages have a special syntax for writing get/set method pairs. All that PHP currently supports is __get and __set, which while great for writing generic get/set methods is nearly useless when it comes to individual properties. Our only other choice is the age old process of writing custom class methods to make our get/set methods. Not only does this lack any kind of uniformity, but it also complicates the syntax ($foo-getBar() and $foo-setBar('baz') instead of $foo-bar and $foo-bar='baz'). I believe that if PHP is going embrace modern object-oriented design, including encapsulation, than it needs a modern solution to property getters and setters. I wont add much more here, but rather let the RFC itself do the talking. It is fairly well fleshed out, and should explain everything clearly enough. Link to the RFC: http://wiki.php.net/rfc/propertygetsetsyntax Thanks, Dennis Robinson -- PHP Internals - PHP Runtime Development Mailing List To unsubscribe, visit: http://www.php.net/unsub.php