Hey list,
I was curious what everyone thought of implementing the ability to
specify class members in interfaces. I've run into a couple of
circumstances where I would like to specify public member names inside
of an interface to ensure that these members are accessed in a standard
way and to ensure that they exist. Currently, trying to include them in
an interface results in "Fatal error: Interfaces may not include
member variables in file/line number".
Thoughts?
Thanks.
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex Corporation
Please note: This message has been sent with information that could be confidential and meant only for the intended recipient. If you are not the intended recipient, please delete all copies and inform us of the error as soon as possible. Thank you for your cooperation.
Hello Jeremy,
interfaces cannot have properties, nor can they have method bodies - that
is the whole purpose of interfafces. We are thinking of adding traits which
would allow for both but would treat inheritance differently. Until we get
that you would need to provide an abstract interface to access data in the
same way.
marcus
Tuesday, April 29, 2008, 5:31:33 AM, you wrote:
Hey list,
I was curious what everyone thought of implementing the ability to
specify class members in interfaces. I've run into a couple of
circumstances where I would like to specify public member names inside
of an interface to ensure that these members are accessed in a standard
way and to ensure that they exist. Currently, trying to include them in
an interface results in "Fatal error: Interfaces may not include
member variables in file/line number".
Thoughts?
Thanks.
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex Corporation
Please note: This message has been sent with information that could be
confidential and meant only for the intended recipient. If you are not the
intended recipient, please delete all copies and inform us of the error as
soon as possible. Thank you for your cooperation.
Best regards,
Marcus
Marcus,
I understand why Interfaces can't have bodies, but could you explain why
Interfaces can't have properties?
Thanks,
John.
-----Original Message-----
From: Marcus Boerger [mailto:helly@php.net]
Sent: 29 April 2008 10:46
To: Jeremy Privett
Cc: PHP Developers Mailing List
Subject: Re: [PHP-DEV] Class Properties in Interfaces?
Hello Jeremy,
interfaces cannot have properties, nor can they have method bodies -
that is the whole purpose of interfafces. We are thinking of adding
traits which would allow for both but would treat inheritance
differently. Until we get that you would need to provide an abstract
interface to access data in the same way.
marcus
Tuesday, April 29, 2008, 5:31:33 AM, you wrote:
Hey list,
I was curious what everyone thought of implementing the ability to
specify class members in interfaces. I've run into a couple of
circumstances where I would like to specify public member names inside
of an interface to ensure that these members are accessed in a
standard way and to ensure that they exist. Currently, trying to
include them in an interface results in "Fatal error: Interfaces may
not include member variables in file/line number".
Thoughts?
Thanks.
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex Corporation
Please note: This message has been sent with information that could be
confidential and meant only for the intended recipient. If you are not
the intended recipient, please delete all copies and inform us of the
error as soon as possible. Thank you for your cooperation.
Best regards,
Marcus
--
To unsubscribe,
visit: http://www.php.net/unsub.php
John Carter -X (johncart - PolicyApp Ltd at Cisco) schrieb:
could you explain why Interfaces can't have properties
Because interfaces are implemented which makes no sense for attributes.
--
Sebastian Bergmann http://sebastian-bergmann.de/
GnuPG Key: 0xB85B5D69 / 27A7 2B14 09E4 98CD 6277 0E5B 6867 C514 B85B 5D69
I think I must be missing something here, but this sounds a little
tautological - "we can't do it because it doesn't make sense. This is
because it doesn't make sense"
Certainly most people (myself included) consider interfaces to be
methods only, but I can't find a reason why not, and a
search-on-wikipedia-instead-of-doing-proper-research appears to allow
it: http://en.wikipedia.org/wiki/Interface_%28computer_science%29
John.
-----Original Message-----
From: news [mailto:news@ger.gmane.org] On Behalf Of Sebastian Bergmann
Sent: 29 April 2008 11:16
To: internals@lists.php.net
Subject: Re: [PHP-DEV] Class Properties in Interfaces?
John Carter -X (johncart - PolicyApp Ltd at Cisco) schrieb:
could you explain why Interfaces can't have properties
Because interfaces are implemented which makes no sense for
attributes.
--
Sebastian Bergmann
http://sebastian-bergmann.de/
GnuPG Key: 0xB85B5D69 / 27A7 2B14 09E4 98CD 6277 0E5B 6867 C514 B85B
5D69
--
To unsubscribe,
visit: http://www.php.net/unsub.php
On Tue, Apr 29, 2008 at 6:28 AM, John Carter -X (johncart - PolicyApp Ltd at
Cisco) johncart@cisco.com wrote:
I think I must be missing something here, but this sounds a little
tautological - "we can't do it because it doesn't make sense. This is
because it doesn't make sense"Certainly most people (myself included) consider interfaces to be
methods only, but I can't find a reason why not, and a
search-on-wikipedia-instead-of-doing-proper-research appears to allow
it: http://en.wikipedia.org/wiki/Interface_%28computer_science%29
the problem with that article, as it pertains to this conversation is that
it is referring to interfaces as a general concept. 'interfaces' can be
formed in many ways, via extension of an abstract class or even an expected
set of a parameters in an HTTP request...
getting to the more concrete term 'interface' as it pertains to a language
keyword, interfaces define a contract; they do not specify implementation
details. member variables only facilitate the actions member functions
expose and therefore, they are part of the implementation.
additionally, one can look to java (and likely others) to see that public
attributes are not supported on interfaces. here is a definition from a
java5 cert book;
"When you create an interface, you're defining a contract for what a class
can do, without saying anything about how the class will do it. An
interface is a contract."
-nathan
The article explicitly mentions OOP interfaces in a few languages. But
the article, or for that matter any formal definition of an interface
isn't really what I asked about:
My question was simply: why can't interfaces have properties?
John.
On Tue, Apr 29, 2008 at 9:51 AM, John Carter -X (johncart - PolicyApp Ltd at
Cisco) johncart@cisco.com wrote:
The article explicitly mentions OOP interfaces in a few languages.
my bad.
But
the article, or for that matter any formal definition of an interface
isn't really what I asked about:My question was simply: why can't interfaces have properties?
when you say properties, do you mean a particular set of methods map to a
particular instance variable, as getters and setters (i saw that definition
from Sebastian earlier)? if thats the case than interfaces cant have
properties because they require instance variables.
-nathan
Nathan,
By example:
interface EggLayer
{
public $eggsLaid;
}
class Chicken implements EggLayer;
Some would say (and maybe I would too) that you should have a
getEggsLaid() method, that's fair enough. But why not the above?
You say interfaces can't have properties because they require instance
variables. Why do they require instance variables? I also think for the
purposes of this discussion, property and instance variable mean the
same thing.
John.
On Tue, Apr 29, 2008 at 10:28 AM, John Carter -X (johncart - PolicyApp Ltd
at Cisco) johncart@cisco.com wrote:
Nathan,
By example:
interface EggLayer
{
public $eggsLaid;
}class Chicken implements EggLayer;
Some would say (and maybe I would too) that you should have a
getEggsLaid() method, that's fair enough. But why not the above?
because, from above, $eggsLaid constitutes the implementation of any class
that implements EggLayer.
You say interfaces can't have properties because they require instance
variables.
thats fine, in fact thats what i take the two terms to mean; however, there
was an alternate definition given in an earlier post and i just wanted to
clarify whether you were referring to that definition of property. hence
forth i understand that you are not referring to that definition.
Why do they require instance variables?
this was only based on the aforementioned definition of properties whereby a
property is an instance variable that has respective getters and setters.
in the absence of that definition, my statement is irrelevant.
I also think for the
purposes of this discussion, property and instance variable mean the
same thing.
cool, then i would say that interfaces cannot have public properties in them
because it imposes implementation requirements on any implementors. to
specify implementation details, there is the abstract class.
-nathan
Hello John,
the main reason really is storage. If you allow storage in interfaces
then you get multiple inheritance with its virtual inheritance (diamond
style inheritance) issue. That however onlly applies to plain attributes
and not properties which are usually understood as attributes that result
in function calls (getter & setter). That said, if PHP had properties, PHP
could also allow peroperties in interfaces. So the actual question shoul
dbe why we do not support properties. To give an idea how properties could
look like:
interface Coordinate {
public $coord = __get => getCoord, __set => setCoord,
__isset => hasCoord, __unset => delCoord;
public getCoord();
public setCoord($val);
public hasCoord();
public delCoord();
}
class MyCoord implements Coordinate {
private $_coord = array(0, 0); // actual storage for $coord
public __construct($x, $y) {
$this->coord = array($x, $y); // calls setCoord
}
public getCoord() {
return $this->_coord;
}
public setCoord($val) {
if (!is_array($val) || count($val) != 2
|| !is_numeric($val[0]) || !is_numeric($val[1])) {
throw new UnexpectedValueException('Array(x,y) of floats expected');
}
$this->_coord = $val;
}
public hasCoord() {
return isset($this->_coord[0]) || isset($this->_coord[1]);
}
public delCoord() {
$this->_coord = array(0, 0);
}
}
This tells me two things:
a) Pretty damn complex and in that kind of the opposite of PHP's usual KISS
approach (Keep It Simple Safe).
b) Pretty sexy as it gives a hell lot of control and you can document
everything. Check out all the minor details and think of what that would
allow.
My conclusion is that even it looks sexy, it might be a bit tooooo complex.
A much shorter thing to do might be:
interface Coord {
abstract $coord;
}
This would just somehow make sure the attribute $this->coord will be
accessible as a public attribute in the implementing class. The same rules
as for methods would apply.
Derick and me discussed solutions around abstract/virtual attributes a lot
in the passed. They were all refused however. But what we had in mind also
was more about specifying attributes in an abstract way in classes so that
they become documentable while being still handled through __get() and
friends.
marcus
Tuesday, April 29, 2008, 5:51:30 PM, you wrote:
The article explicitly mentions OOP interfaces in a few languages. But
the article, or for that matter any formal definition of an interface
isn't really what I asked about:My question was simply: why can't interfaces have properties?
John.
From: Nathan Nobbe [mailto:quickshiftin@gmail.com]
Sent: 29 April 2008 16:17
To: John Carter -X (johncart - PolicyApp Ltd at Cisco)
Cc: internals@lists.php.net
Subject: Re: Re: [PHP-DEV] Class Properties in Interfaces?
On Tue, Apr 29, 2008 at 6:28 AM, John Carter -X (johncart - PolicyApp
Ltd at Cisco) johncart@cisco.com wrote:
I think I must be missing something here, but this sounds a
little
tautological - "we can't do it because it doesn't make sense.
This is
because it doesn't make sense"Certainly most people (myself included) consider interfaces to
be
methods only, but I can't find a reason why not, and a
search-on-wikipedia-instead-of-doing-proper-research appears to
allow
it:
http://en.wikipedia.org/wiki/Interface_%28computer_science%29
the problem with that article, as it pertains to this conversation is
that it is referring to interfaces as a general concept. 'interfaces'
can be formed in many ways, via extension of an abstract class or even
an expected set of a parameters in an HTTP request...
getting to the more concrete term 'interface' as it pertains to a
language keyword, interfaces define a contract; they do not specify
implementation details. member variables only facilitate the actions
member functions expose and therefore, they are part of the
implementation.
additionally, one can look to java (and likely others) to see that
public attributes are not supported on interfaces. here is a definition
from a java5 cert book;
"When you create an interface, you're defining a contract for what a
class can do, without saying anything about how the class will do it.
An interface is a contract."
-nathan
Best regards,
Marcus
Hi Marcus,
I think this is really specifying implementation details in an
interface:
interface Coordinate {
public $coord = __get => getCoord, __set => setCoord,
__isset => hasCoord, __unset => delCoord;
public getCoord();
public setCoord($val);
public hasCoord();
public delCoord();
}
This looks to me like the best way to handle this in interfaces:
interface Coord {
abstract $coord;
}
I think this example could be simplified if the basic accessor methods
didn't have to be explicitly declared:
class MyCoord implements Coordinate {
protected $_coord; // actual storage for $coord
public $coord = __get => $_coord, __set => setCoord,
__isset => $_coord, __unset => $coord; // Satisfies
the interface
public __construct($x, $y) {
$this->coord = array($x, $y); // calls setCoord
}
public setCoord($val) {
if (!is_array($val) || count($val) != 2
|| !is_numeric($val[0]) || !is_numeric($val[1])) {
throw new UnexpectedValueException('Array(x,y) of floats
expected');
}
$this->_coord = $val;
}
}
One thing about this syntax is that it give PHP a lot of information
to optimize the performance of property access.
Or you could do this
class MyCoord implements Coordinate {
public $coord; // satisfies interface
}
The nice thing about this kind of property is that you can switch
between these two implementations over time with out changing how
callers use the interface.
Maybe there are some things that could be done with syntax on this:
public $coord = __get => $_coord, __set => setCoord,
__isset => $_coord, __unset => $coord;
Can some standard implementation of the __isset and __unset be used to
simplify this declaration to something like this?
public $coord = __get => $_coord, __set => setCoord;
or
public $coord __get $_coord __set SetCoord;
or to cut down on the underlines...
public $coord get $_coord set SetCoord;
Additionally, with this syntax, we can allow accessors to have
differing visibility, which we cannot do with virtual properties:
public $coord get $_coord protected set SetCoord; // Public property
with protected setter
There are some advantages to this with inheritance, too
class Parent {
public $foo;
}
class Child extends Parent {
protected $_foo;
public $foo get $_foo set SetFoo;
function SetFoo($value) { ... }
}
In this example, a child has added an accessor method to a property
defined on a parent without changing the parent. Something you cannot
do with virtual properties.
I think structural properties would be a useful feature.
Best Regards,
Jeff
Hello John,
the main reason really is storage. If you allow storage in interfaces
then you get multiple inheritance with its virtual inheritance
(diamond
style inheritance) issue. That however onlly applies to plain
attributes
and not properties which are usually understood as attributes that
result
in function calls (getter & setter). That said, if PHP had
properties, PHP
could also allow peroperties in interfaces. So the actual question
shoul
dbe why we do not support properties. To give an idea how properties
could
look like:interface Coordinate {
public $coord = __get => getCoord, __set => setCoord,
__isset => hasCoord, __unset => delCoord;
public getCoord();
public setCoord($val);
public hasCoord();
public delCoord();
}class MyCoord implements Coordinate {
private $_coord = array(0, 0); // actual storage for $coord
public __construct($x, $y) {
$this->coord = array($x, $y); // calls setCoord
}
public getCoord() {
return $this->_coord;
}
public setCoord($val) {
if (!is_array($val) || count($val) != 2
|| !is_numeric($val[0]) || !is_numeric($val[1])) {
throw new UnexpectedValueException('Array(x,y) of floats
expected');
}
$this->_coord = $val;
}
public hasCoord() {
return isset($this->_coord[0]) || isset($this->_coord[1]);
}
public delCoord() {
$this->_coord = array(0, 0);
}
}This tells me two things:
a) Pretty damn complex and in that kind of the opposite of PHP's
usual KISS
approach (Keep It Simple Safe).b) Pretty sexy as it gives a hell lot of control and you can document
everything. Check out all the minor details and think of what that
would
allow.My conclusion is that even it looks sexy, it might be a bit tooooo
complex.A much shorter thing to do might be:
interface Coord {
abstract $coord;
}This would just somehow make sure the attribute $this->coord will be
accessible as a public attribute in the implementing class. The same
rules
as for methods would apply.Derick and me discussed solutions around abstract/virtual attributes
a lot
in the passed. They were all refused however. But what we had in
mind also
was more about specifying attributes in an abstract way in classes
so that
they become documentable while being still handled through __get() and
friends.marcus
Tuesday, April 29, 2008, 5:51:30 PM, you wrote:
The article explicitly mentions OOP interfaces in a few languages.
But
the article, or for that matter any formal definition of an interface
isn't really what I asked about:My question was simply: why can't interfaces have properties?
John.
From: Nathan Nobbe [mailto:quickshiftin@gmail.com]
Sent: 29 April 2008 16:17
To: John Carter -X (johncart - PolicyApp Ltd at Cisco)
Cc: internals@lists.php.net
Subject: Re: Re: [PHP-DEV] Class Properties in Interfaces?On Tue, Apr 29, 2008 at 6:28 AM, John Carter -X (johncart - PolicyApp
Ltd at Cisco) johncart@cisco.com wrote:I think I must be missing something here, but this sounds a
little
tautological - "we can't do it because it doesn't make sense.
This is
because it doesn't make sense"Certainly most people (myself included) consider interfaces to
be
methods only, but I can't find a reason why not, and a
search-on-wikipedia-instead-of-doing-proper-research appears
to
allow
it:
http://en.wikipedia.org/wiki/Interface_%28computer_science%29the problem with that article, as it pertains to this conversation is
that it is referring to interfaces as a general concept.
'interfaces'
can be formed in many ways, via extension of an abstract class or
even
an expected set of a parameters in an HTTP request...
getting to the more concrete term 'interface' as it pertains to a
language keyword, interfaces define a contract; they do not specify
implementation details. member variables only facilitate the actions
member functions expose and therefore, they are part of the
implementation.additionally, one can look to java (and likely others) to see that
public attributes are not supported on interfaces. here is a
definition
from a java5 cert book;
"When you create an interface, you're defining a contract for
what a
class can do, without saying anything about how the class will do it.
An interface is a contract."-nathan
Best regards,
Marcus
Hi Marcus, et al.,
Am Dienstag, den 06.05.2008, 09:09 -0700 schrieb Jeff Moore:
[...]
I think this is really specifying implementation details in an
interface:
I agree.
[...]
This looks to me like the best way to handle this in interfaces:
interface Coord {
abstract $coord;
}
I think this is too unspecific. At least the visibility, setter and/or
getter and type-hint (assuming we will have type hints) should be
defined. Otherwise defining properties in interfaces become useless as
it does not tell somebody more except "there is a property".
interface Something
{
public $property {
string public function get();
string protected function set(string $value);
}
}
Just my 2¢
cu, Lars
I think this is too unspecific. At least the visibility, setter and/or
getter and type-hint (assuming we will have type hints) should be
defined. Otherwise defining properties in interfaces become useless as
it does not tell somebody more except "there is a property".
i agree entirely.
-nathan
Hello Lars,
Tuesday, May 6, 2008, 9:21:12 PM, you wrote:
Hi Marcus, et al.,
Am Dienstag, den 06.05.2008, 09:09 -0700 schrieb Jeff Moore:
[...]I think this is really specifying implementation details in an
interface:
I agree.
[...]
This looks to me like the best way to handle this in interfaces:
interface Coord {
abstract $coord;
}
I think this is too unspecific. At least the visibility, setter and/or
getter and type-hint (assuming we will have type hints) should be
defined. Otherwise defining properties in interfaces become useless as
it does not tell somebody more except "there is a property".
interface Something
{
public $property {
string public function get();
string protected function set(string $value);
}
}
All fine with me. However we would need to specify which function is
getter, setter, isset or unset. We need to avoid introducing new keywords,
so I hope __get and so on in the hope that it would help in that direction.
Also note that we do not need to define anything inside the property or we
could choose to exactly do everything there.
public $property {
string public function __get() {
return $this->_property;
}
string protected function __set(string $value) {...}
}
vs:
public $property {
__get = getProperty;
__set = setProperty;
}
string public function getProperty() {
return $this->_property;
}
string protected function setProperty(string $value) {}
The advantage of keeping everything inside the property definition is that
there is no need at all for any new keyword. And the handlers cannot get
separated. The disadvantage is that the functions are always named __get and
so on for all properties, so PHP would need to do an internal renaming.
Which means we probably would not be able to call the functions manually.
That larger handlers could clutter the code doesn't appear to be a
disadvantage for me as it can easily be avoided if the handler just
forwards the call.
The next question I have now is what to do when people want direct access
to the underlying value? Or do we force people to always specify
get,set,isset und unset? Or should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()), unset()~>set(NULL))?
Best regards,
Marcus
Hi Marcus!
Am Dienstag, den 06.05.2008, 21:45 +0200 schrieb Marcus Boerger:
[...]
All fine with me. However we would need to specify which function is
getter, setter, isset or unset.
[...]
public $property {
string public function __get() {
return $this->_property;
}
string protected function __set(string $value) {...}
}
That's the variant I prefer. It is pretty similar to the C# does it and
therefore follows the common PHP strategy of steeling everything
together ;)
[...]
The advantage of keeping everything inside the property definition is that
there is no need at all for any new keyword. And the handlers cannot get
separated. The disadvantage is that the functions are always named __get and
so on for all properties, so PHP would need to do an internal renaming.
Which means we probably would not be able to call the functions manually.
Do you see any real use-case for calling them directly?
That larger handlers could clutter the code doesn't appear to be a
disadvantage for me as it can easily be avoided if the handler just
forwards the call.
Either that or folding in the editor helps etc. pp.
The next question I have now is what to do when people want direct access
to the underlying value?
I would think that accessing $this->property from __get()/__set() of the
property would address the value itself. Everything else would be
redirected to the accessors.
Or do we force people to always specify get,set,isset und unset? Or
should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()),
unset()~>set(NULL))?
Not sure about that. Forcing the user to define four accessors for a
property seems to be clutter but it would be - technically spoken -
correct. I don't have a fixed opinion here.
cu, Lars
Hi All,
Lars Strojny schrieb:
Hi Marcus!
Am Dienstag, den 06.05.2008, 21:45 +0200 schrieb Marcus Boerger:
[...]All fine with me. However we would need to specify which
function is getter, setter, isset or unset.[...]
public $property { string public function __get() { return
$this->_property; } string protected function __set(string
$value) {...} }That's the variant I prefer. It is pretty similar to the C# does it
and therefore follows the common PHP strategy of steeling
everything together ;)
I'd really like to use that functionality instead of my current getXXX()
setXXX().
Back to lurking.
regards,
Jens
2008/5/6 Lars Strojny lars@strojny.net:
Hi Marcus!
Am Dienstag, den 06.05.2008, 21:45 +0200 schrieb Marcus Boerger:
[...]All fine with me. However we would need to specify which function is
getter, setter, isset or unset.[...]
public $property {
string public function __get() {
return $this->_property;
}
string protected function __set(string $value) {...}
}That's the variant I prefer. It is pretty similar to the C# does it and
therefore follows the common PHP strategy of steeling everything
together ;)[...]
The advantage of keeping everything inside the property definition is that
there is no need at all for any new keyword. And the handlers cannot get
separated. The disadvantage is that the functions are always named __get and
so on for all properties, so PHP would need to do an internal renaming.
Which means we probably would not be able to call the functions manually.Do you see any real use-case for calling them directly?
That larger handlers could clutter the code doesn't appear to be a
disadvantage for me as it can easily be avoided if the handler just
forwards the call.Either that or folding in the editor helps etc. pp.
The next question I have now is what to do when people want direct access
to the underlying value?I would think that accessing $this->property from __get()/__set() of the
property would address the value itself. Everything else would be
redirected to the accessors.Or do we force people to always specify get,set,isset und unset? Or
should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()),
unset()~>set(NULL))?Not sure about that. Forcing the user to define four accessors for a
property seems to be clutter but it would be - technically spoken -
correct. I don't have a fixed opinion here.cu, Lars
You would only normally need to define the four accessors if your
property isn't a bog standard one or you didn't want to trigger any
activity when a property changed.
class foo {
public $bar;
}
is fine. foo::bar is a completely normal property as we know it.
--
Richard Quadling
Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498&r=213474731
"Standing on the shoulders of some very clever giants!"
public $property {
__get = getProperty;
__set = setProperty;
}
string public function getProperty() {
return $this->_property;
}
string protected function setProperty(string $value) {}
Hi Marcus,
I prefer this approach.
One advantage is that it is compatible with existing classes that have
done the getXXX() style accessors already.
One thing That I am hoping to avoid, though, is the need to declare
these kinds of basic accessor methods at all. (the ones that do
nothing but set or read a backing property.) it seems like PHP should
be able to generate them, or just fallback into a simple property
access on the backing store, if that store is specified as part of the
property.
This should be the same as the previous example replacing setProperty
and getProperty with direct references to the backing store:
protected $_property;
public $property {
__get = $_property;
__set = $_property;
}
Or do we force people to always specify
get,set,isset und unset? Or should we only enforce get/set and have
isset
and unset emulated with them (isset()~>isset(get()),
unset()~>set(NULL))?
it would be nice to have exactly this emulation for __isset and
__unset when they are not declared.
However, leaving out the __set should make the property read only and
leaving out the __get should make the property write only (less
useful, but symmetric).
Following the C# convention for declaring properties in interfaces
would declare the previous as
interface bar {
public $property {__set; __get;}
}
Best Regards,
Jeff
2008/5/7 Jeff Moore jeff@procata.com:
public $property {
__get = getProperty;
__set = setProperty;
}
string public function getProperty() {
return $this->_property;
}
string protected function setProperty(string $value) {}Hi Marcus,
I prefer this approach.
One advantage is that it is compatible with existing classes that have done
the getXXX() style accessors already.One thing That I am hoping to avoid, though, is the need to declare these
kinds of basic accessor methods at all. (the ones that do nothing but set
or read a backing property.) it seems like PHP should be able to generate
them, or just fallback into a simple property access on the backing store,
if that store is specified as part of the property.This should be the same as the previous example replacing setProperty and
getProperty with direct references to the backing store:protected $_property;
public $property {
__get = $_property;
__set = $_property;}
Or do we force people to always specify
get,set,isset und unset? Or should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()), unset()~>set(NULL))?it would be nice to have exactly this emulation for __isset and __unset
when they are not declared.However, leaving out the __set should make the property read only and
leaving out the __get should make the property write only (less useful, but
symmetric).Following the C# convention for declaring properties in interfaces would
declare the previous asinterface bar {
public $property {__set; __get;}
}Best Regards,
Jeff
If the interface iFoo says property bar must be implemented, then it
would seem inappropriate to allow the unsetting of property bar.
My reasoning is that the interface says this is how all objects
implementing this interface look (the contract), then allowing one of
the instances to remove the property breaks the contract.
If you follow this (I hope someone does), then as a consequence, isset
now becomes slightly different in that it is behaving more like an
empty().
Regards,
Richard.
Richard Quadling
Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498&r=213474731
"Standing on the shoulders of some very clever giants!"
Hello Richard,
Wednesday, May 7, 2008, 3:33:24 PM, you wrote:
2008/5/7 Jeff Moore jeff@procata.com:
public $property {
__get = getProperty;
__set = setProperty;
}
string public function getProperty() {
return $this->_property;
}
string protected function setProperty(string $value) {}Hi Marcus,
I prefer this approach.
One advantage is that it is compatible with existing classes that have done
the getXXX() style accessors already.One thing That I am hoping to avoid, though, is the need to declare these
kinds of basic accessor methods at all. (the ones that do nothing but set
or read a backing property.) it seems like PHP should be able to generate
them, or just fallback into a simple property access on the backing store,
if that store is specified as part of the property.This should be the same as the previous example replacing setProperty and
getProperty with direct references to the backing store:protected $_property;
public $property {
__get = $_property;
__set = $_property;}
Or do we force people to always specify
get,set,isset und unset? Or should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()), unset()~>set(NULL))?it would be nice to have exactly this emulation for __isset and __unset
when they are not declared.However, leaving out the __set should make the property read only and
leaving out the __get should make the property write only (less useful, but
symmetric).Following the C# convention for declaring properties in interfaces would
declare the previous asinterface bar {
public $property {__set; __get;}
}Best Regards,
Jeff
If the interface iFoo says property bar must be implemented, then it
would seem inappropriate to allow the unsetting of property bar.
Why? Unset would simply set the storage to NULL, not undeclare it.
My reasoning is that the interface says this is how all objects
implementing this interface look (the contract), then allowing one of
the instances to remove the property breaks the contract.
If you follow this (I hope someone does), then as a consequence, isset
now becomes slightly different in that it is behaving more like an
empty().
Regards,
Richard.
Richard Quadling
Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498&r=213474731
"Standing on the shoulders of some very clever giants!"
Best regards,
Marcus
2008/5/12 Marcus Boerger helly@php.net:
Hello Richard,
Wednesday, May 7, 2008, 3:33:24 PM, you wrote:
2008/5/7 Jeff Moore jeff@procata.com:
public $property {
__get = getProperty;
__set = setProperty;
}
string public function getProperty() {
return $this->_property;
}
string protected function setProperty(string $value) {}Hi Marcus,
I prefer this approach.
One advantage is that it is compatible with existing classes that have done
the getXXX() style accessors already.One thing That I am hoping to avoid, though, is the need to declare these
kinds of basic accessor methods at all. (the ones that do nothing but set
or read a backing property.) it seems like PHP should be able to generate
them, or just fallback into a simple property access on the backing store,
if that store is specified as part of the property.This should be the same as the previous example replacing setProperty and
getProperty with direct references to the backing store:protected $_property;
public $property {
__get = $_property;
__set = $_property;}
Or do we force people to always specify
get,set,isset und unset? Or should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()), unset()~>set(NULL))?it would be nice to have exactly this emulation for __isset and __unset
when they are not declared.However, leaving out the __set should make the property read only and
leaving out the __get should make the property write only (less useful, but
symmetric).Following the C# convention for declaring properties in interfaces would
declare the previous asinterface bar {
public $property {__set; __get;}
}Best Regards,
Jeff
If the interface iFoo says property bar must be implemented, then it
would seem inappropriate to allow the unsetting of property bar.Why? Unset would simply set the storage to NULL, not undeclare it.
My reasoning is that the interface says this is how all objects
implementing this interface look (the contract), then allowing one of
the instances to remove the property breaks the contract.If you follow this (I hope someone does), then as a consequence, isset
now becomes slightly different in that it is behaving more like an
empty().Regards,
Richard.
For scalars and accessible properties, unset() does indeed undeclare
the scalar/property.
<?php
$foo = 'bar';
echo $foo;
unset($foo);
echo $foo;
?>
results in Notice: Undefined variable: foo in C:- on line 5
and
<?php
class foo {
public $bar;
public function __construct() {
$this->bar = 'snafu';
}
}
$o_Foo = new foo();
echo $o_Foo->bar;
unset($o_Foo->bar);
echo $o_Foo->bar;
?>
outputs ...
snafu
Notice: Undefined property: foo::$bar in C:- on line 13
But if the property is part of an interface, then allowing the
property to be undeclared would seem to me to be breaking the
contract.
Say $bar is in iFoo.
We would expect if ($someobj implements iFoo) then $someobj->bar to
exist. The interface says it does. If it has been removed, then the
interface is lying or the contract isn't as strong as is expected.
If we are saying that unset() on an interfaced property works
differently to unset on scalars/normal properties then seems
potentially confusing.
Richard.
--
Richard Quadling
Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498&r=213474731
"Standing on the shoulders of some very clever giants!"
Hello Richard,
Monday, May 12, 2008, 5:03:39 PM, you wrote:
2008/5/12 Marcus Boerger helly@php.net:
Hello Richard,
Wednesday, May 7, 2008, 3:33:24 PM, you wrote:
2008/5/7 Jeff Moore jeff@procata.com:
public $property {
__get = getProperty;
__set = setProperty;
}
string public function getProperty() {
return $this->_property;
}
string protected function setProperty(string $value) {}Hi Marcus,
I prefer this approach.
One advantage is that it is compatible with existing classes that have done
the getXXX() style accessors already.One thing That I am hoping to avoid, though, is the need to declare these
kinds of basic accessor methods at all. (the ones that do nothing but set
or read a backing property.) it seems like PHP should be able to generate
them, or just fallback into a simple property access on the backing store,
if that store is specified as part of the property.This should be the same as the previous example replacing setProperty and
getProperty with direct references to the backing store:protected $_property;
public $property {
__get = $_property;
__set = $_property;}
Or do we force people to always specify
get,set,isset und unset? Or should we only enforce get/set and have isset
and unset emulated with them (isset()~>isset(get()), unset()~>set(NULL))?it would be nice to have exactly this emulation for __isset and __unset
when they are not declared.However, leaving out the __set should make the property read only and
leaving out the __get should make the property write only (less useful, but
symmetric).Following the C# convention for declaring properties in interfaces would
declare the previous asinterface bar {
public $property {__set; __get;}
}Best Regards,
Jeff
If the interface iFoo says property bar must be implemented, then it
would seem inappropriate to allow the unsetting of property bar.Why? Unset would simply set the storage to NULL, not undeclare it.
My reasoning is that the interface says this is how all objects
implementing this interface look (the contract), then allowing one of
the instances to remove the property breaks the contract.If you follow this (I hope someone does), then as a consequence, isset
now becomes slightly different in that it is behaving more like an
empty().Regards,
Richard.
For scalars and accessible properties, unset() does indeed undeclare
the scalar/property.
<?php
$foo = 'bar';
echo $foo;
unset($foo);
echo $foo;
?>>
results in Notice: Undefined variable: foo in C:- on line 5
This is correct.
and
<?php
class foo {
public $bar;
public function __construct() { $this->bar = 'snafu'; }
}
$o_Foo = new foo();
echo $o_Foo->bar;
unset($o_Foo->bar);
echo $o_Foo->bar;
?>>
outputs ...
snafu
Notice: Undefined property: foo::$bar in C:- on line 13
At this point you found an error. Because this allows unset() to modify an
instance in a way that it nolonger adheres to its class that means at this
point the following is nolonger valid: $o_Foo is-a foo. And that is the
basic design rule we chose for PHP. Please file as a bug!
But if the property is part of an interface, then allowing the
property to be undeclared would seem to me to be breaking the
contract.
Say $bar is in iFoo.
We would expect if ($someobj implements iFoo) then $someobj->bar to
exist. The interface says it does. If it has been removed, then the
interface is lying or the contract isn't as strong as is expected.
If we are saying that unset() on an interfaced property works
differently to unset on scalars/normal properties then seems
potentially confusing.
Richard.
Best regards,
Marcus
Marcus Boerger wrote:
unset($o_Foo->bar);
echo $o_Foo->bar;
?>>outputs ...
Notice: Undefined property: foo::$bar in C:- on line 13At this point you found an error. Because this allows unset() to modify an
instance in a way that it nolonger adheres to its class that means at this
point the following is nolonger valid: $o_Foo is-a foo. And that is the
basic design rule we chose for PHP. Please file as a bug!
So you are saying that
$o_Foo->bar = array(42);
is ok when the class "expects" a string but
unset($o_Foo->bar);
or (as as slight variation)
$o->Foo->bar = null;
is not?
I'd ask not to change this behaviour as you'll just add another (IMHO
bogus) restriction on how an object or class can be modified at runtime.
An error possibly caused by this is already handled by the E_NOTICE
message anyway.
For comparison: Having to declare static class variables is a similar
restriction which got in my way more often than it helped me.
- Chris
Hi!
point the following is nolonger valid: $o_Foo is-a foo. And that is the
basic design rule we chose for PHP. Please file as a bug!
I don't think it's a bug. PHP as a dynamic language allows to do a lot
of think that Java or C++ do not. This is one of them.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
Hello Christian, Stas,
Tuesday, May 13, 2008, 4:08:09 PM, you wrote:
Marcus Boerger wrote:
unset($o_Foo->bar);
echo $o_Foo->bar;
?>>outputs ...
Notice: Undefined property: foo::$bar in C:- on line 13At this point you found an error. Because this allows unset() to modify an
instance in a way that it nolonger adheres to its class that means at this
point the following is nolonger valid: $o_Foo is-a foo. And that is the
basic design rule we chose for PHP. Please file as a bug!
So you are saying that
$o_Foo->bar = array(42);
is ok when the class "expects" a string but
unset($o_Foo->bar);
or (as as slight variation)
$o->Foo->bar = null;
is not?
I Do not get the connection here? And since when can we 'expect' a string
only for a property?
My point is that an object should always have a property, whether it has
the value NULL
or not doesn't matter at all. And actually unsetting a
property right now doesn't change much besides that it breaks inhereitance
rules and affects reflection (maybe, not tested). Becasue when a defined
property is unset() and that infact results in deletion than the property
information ist still present in the class. The next access to that
property now must not result in an error (not even E_NOTICE
as even that
would be misleading, people would try to find the error in the class). And
anyway PHP happily recreates the property with value NULL
if being
accessed. And if the property is not declared than PHP will simply create a
new property on access. This creation of undeclared properties does not
affect any inheritance rules and was decided on. This is what Sats meant
with what PHP allows beyond C++ and Java. Allowing anythign more breaks our
basic design principles.
I'd ask not to change this behaviour as you'll just add another (IMHO
bogus) restriction on how an object or class can be modified at runtime.
An error possibly caused by this is already handled by theE_NOTICE
message anyway.
For comparison: Having to declare static class variables is a similar
restriction which got in my way more often than it helped me.
- Chris
Best regards,
Marcus
Am 14.05.2008 um 02:06 schrieb Marcus Boerger:
So you are saying that
$o_Foo->bar = array(42);
is ok when the class "expects" a string but
unset($o_Foo->bar);
or (as as slight variation)
$o->Foo->bar = null;
is not?I Do not get the connection here? And since when can we 'expect' a
string
only for a property?
You stated that allowing unset() is a bug. I replied that unset() is
not different from setting the value to array(42) or null and should
be allowed.
Apropos 'expect': A programmer of a class can have some expectations
of what is stored in attributes, PHP does not enforce these
expectations (hence I put expect in quotes). And just to make it
clear: I want to keep it that way, I do not want PHP to become more
strict than it is.
So I completely agree with Stas here.
- Chris
2008/5/14 Christian Schneider cschneid@cschneid.com:
Am 14.05.2008 um 02:06 schrieb Marcus Boerger:
So you are saying that
$o_Foo->bar = array(42);
is ok when the class "expects" a string but
unset($o_Foo->bar);
or (as as slight variation)
$o->Foo->bar = null;
is not?I Do not get the connection here? And since when can we 'expect' a string
only for a property?You stated that allowing unset() is a bug. I replied that unset() is not
different from setting the value to array(42) or null and should be allowed.Apropos 'expect': A programmer of a class can have some expectations of what
is stored in attributes, PHP does not enforce these expectations (hence I
put expect in quotes). And just to make it clear: I want to keep it that
way, I do not want PHP to become more strict than it is.So I completely agree with Stas here.
- Chris
Chris (and others).
IF the property was defined in an interface, should "unset" be
"allowed" to remove the property?
The current behaviour of allowing a property of a normal class to be
removed is debatable. (It is currently doing so, so for BC it should
probably stay as such).
With the interface though, we are saying we want to enforce its
existence, so it must always exist and as such unset() would/should
have no meaning and be an error (attempting to change an enforced
interface structure).
Maybe this is a difference for E_STRICT?
Richard.
--
Richard Quadling
Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498&r=213474731
"Standing on the shoulders of some very clever giants!"
Richard Quadling wrote:
IF the property was defined in an interface, should "unset" be
"allowed" to remove the property?
a) Interfaces do not define attributes, they define a set of methods.
b) If the above would be changed I still want to be able to shoot myself
in the foot if I explicitely say so.
- Chris
Richard Quadling wrote:
IF the property was defined in an interface, should "unset" be
"allowed" to remove the property?a) Interfaces do not define attributes, they define a set of methods.
b) If the above would be changed I still want to be able to shoot myself
in the foot if I explicitely say so.
I think in the case of an property declared in an interface, the
semantics should be tightened slightly. Rather than doing a complete
unset where the property is removed, instead the property would be
unlinked from any references (if such is the case) and assigned the
value null. This will still preserve the desired behaviour when checking
the property with isset() but the property will still exist so that the
interface requirement for the property to exist is still met.
The point about shooting yourself in the foot doesn't really apply here
since you can't shoot yourself in the foot by not declaring a method
when implementing an interface so why should you be allowed that option
for a property specified in an interface? Your alternative is as it
always is... don't use the interface or use one that lets you shoot
yourself in the foot.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
Hello Christian,
Wednesday, May 14, 2008, 10:57:24 AM, you wrote:
Am 14.05.2008 um 02:06 schrieb Marcus Boerger:
So you are saying that
$o_Foo->bar = array(42);
is ok when the class "expects" a string but
unset($o_Foo->bar);
or (as as slight variation)
$o->Foo->bar = null;
is not?I Do not get the connection here? And since when can we 'expect' a
string
only for a property?
You stated that allowing unset() is a bug. I replied that unset() is
not different from setting the value to array(42) or null and should
be allowed.
Not allowing unset() is the bug. Having unset delete the property would be
the error. As long as the property still exists with value NULL
all is
fine.
Apropos 'expect': A programmer of a class can have some expectations
of what is stored in attributes, PHP does not enforce these
expectations (hence I put expect in quotes). And just to make it
clear: I want to keep it that way, I do not want PHP to become more
strict than it is.
So I completely agree with Stas here.
- Chris
Best regards,
Marcus
Hi Marcus,
Am 18.05.2008 um 13:20 schrieb Marcus Boerger:
Not allowing unset() is the bug. Having unset delete the property
would be
the error. As long as the property still exists with valueNULL
all is
fine.
I think unset($foo->bar) should unset while $foo->bar = null should
set to null to keep things consistent and true to the operation's name.
But as long as unset() is allowed (with either semantics) I'm happy to
end this thread.
- Chris
Hello Christian,
Sunday, May 18, 2008, 1:30:08 PM, you wrote:
Hi Marcus,
Am 18.05.2008 um 13:20 schrieb Marcus Boerger:
Not allowing unset() is the bug. Having unset delete the property
would be
the error. As long as the property still exists with valueNULL
all is
fine.
I think unset($foo->bar) should unset while $foo->bar = null should
set to null to keep things consistent and true to the operation's name.
Just to make this clear once and for ever. If unset() deletes the property then:
a) it would break inheritance
b) accomplish nothing, as the next access would simply recreate it
But as long as unset() is allowed (with either semantics) I'm happy to
end this thread.
- Chris
Best regards,
Marcus
Hi Marcus,
Am 18.05.2008 um 18:41 schrieb Marcus Boerger:
Just to make this clear once and for ever. If unset() deletes the
property then:
a) it would break inheritance
b) accomplish nothing, as the next access would simply recreate it
Ok, you don't want this thread to die, so here we go: You keep on
repeating your two points, care to show some code demonstrating it?
Contradicting tests:
class A { var $foo = 42; }
$a = new A;
var_dump($a);
Output: object(A)#2 (1) { ["foo"]=> int(42) }
$a->foo = null;
var_dump($a);
Output: object(A)#2 (1) { ["foo"]=> NULL
}
unset($a->foo);
var_dump($a);
Output: object(A)#2 (0) { }
$x = $a->foo;
var_dump($a);
Output: object(A)#2 (0) { }
This is exactly the same behaviour as for any variable, nothing broken
here.
Can we please move on now?
Regards,
- Chris
Hello Christian,
Sunday, May 18, 2008, 7:16:55 PM, you wrote:
Hi Marcus,
Am 18.05.2008 um 18:41 schrieb Marcus Boerger:
Just to make this clear once and for ever. If unset() deletes the
property then:
a) it would break inheritance
b) accomplish nothing, as the next access would simply recreate it
Ok, you don't want this thread to die, so here we go: You keep on
repeating your two points, care to show some code demonstrating it?
Contradicting tests:
class A { var $foo = 42; }
$a = new A;
var_dump($a);Output: object(A)#2 (1) { ["foo"]=> int(42) }
$a->foo = null;
var_dump($a);Output: object(A)#2 (1) { ["foo"]=>
NULL
}
unset($a->foo);
var_dump($a);Output: object(A)#2 (0) { }
$x = $a->foo;
var_dump($a);Output: object(A)#2 (0) { }
This is exactly the same behaviour as for any variable, nothing broken
here.
Can we please move on now?
A member variable simply is not like any other variable. It is being
declared and part of an interface. Removing it means changing the
interface means breaking inheritance. So making this possible is a bug in
the engine. End of the story.
Best regards,
Marcus
Hi!
declared and part of an interface. Removing it means changing the
interface means breaking inheritance. So making this possible is a bug in
the engine. End of the story.
Or that makes interface variables make much less sense than initially
thought :)
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
Hi!
Just to make this clear once and for ever. If unset() deletes the property then:
But that's what unset does right now in any context. It deletes the
variable given as its argument. Changing this may have a lot of
unexpected effects.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
I think this is too unspecific. At least the visibility, setter and/or
getter and type-hint (assuming we will have type hints) should be
defined. Otherwise defining properties in interfaces become useless as
it does not tell somebody more except "there is a property".interface Something
{
public $property {
string public function get();
string protected function set(string $value);
}
}
Hi Lars,
It isn't necessary to specify the visibility in an interface because
all interface members are public.
Specifying the accessor methods in an interface reveals too much of
the implementation. Properties (the kind with accessor methods) are
themselves an abstract concept. You want to be able to take an
interface definition such as:
interface foo {
public $bar; // if you prefer this to abstract $foo;
}
and implement it like this:
class DoIt implements foo {
public $bar;
}
or to implement it using setters, using your notation:
class DoIt2 implements foo {
public $foo {
public function get();
protected function set($value);
}
}
The whole point of this kind of property is that the caller is never
supposed to know if they are just accessing a object instance variable
or an accessor method. This is called the uniform access principle.
http://en.wikipedia.org/wiki/Uniform_access_principle
Here is how C# handles properties in an interface:
http://msdn.microsoft.com/en-us/library/64syzecx.aspx
"The accessor of an interface property does not have a body. Thus, the
purpose of the accessors is to indicate whether the property is read-
write, read-only, or write-only."
So, yeah, "there is a property named foo" is about all an interface
should say.
Best Regards,
Jeff
Marcus Boerger wrote:
A much shorter thing to do might be:
interface Coord {
abstract $coord;
}
Something like that is exactly what I was looking for in my original
question. I don't want to specify implementation details, I just want to
ensure the property exists on the classes that implements the interface.
(Type hinting support would be beautiful, too.)
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex Corporation
Please note: This message has been sent with information that could be confidential and meant only for the intended recipient. If you are not the intended recipient, please delete all copies and inform us of the error as soon as possible. Thank you for your cooperation.
Marcus,
I think the idea of supporting properties via getters/setters is a fine
idea (just like Java, Delphi etc). Many of us simulate this behaviour
with __get()/__set(), and it would be nice to formalise it a little.
However I don't quite understand the "multiple inheritance" argument - I
understand that we can't implement two interfaces that have the same
declared method, why wouldn't we just prevent people declaring an
identical attribute in the same way?
John.
-----Original Message-----
From: Marcus Boerger [mailto:helly@php.net]
Sent: 06 May 2008 15:22
To: John Carter -X (johncart - PolicyApp Ltd at Cisco); Derick Rethans
Cc: internals@lists.php.net
Subject: Re: [PHP-DEV] Class Properties in Interfaces?
Hello John,
the main reason really is storage. If you allow storage in interfaces
then you get multiple inheritance with its virtual inheritance (diamond
style inheritance) issue. That however onlly applies to plain attributes
and not properties which are usually understood as attributes that
result in function calls (getter & setter). That said, if PHP had
properties, PHP could also allow peroperties in interfaces. So the
actual question shoul dbe why we do not support properties. To give an
idea how properties could look like:
interface Coordinate {
public $coord = __get => getCoord, __set => setCoord,
__isset => hasCoord, __unset => delCoord;
public getCoord();
public setCoord($val);
public hasCoord();
public delCoord();
}
class MyCoord implements Coordinate {
private $_coord = array(0, 0); // actual storage for $coord
public __construct($x, $y) {
$this->coord = array($x, $y); // calls setCoord
}
public getCoord() {
return $this->_coord;
}
public setCoord($val) {
if (!is_array($val) || count($val) != 2
|| !is_numeric($val[0]) || !is_numeric($val[1])) {
throw new UnexpectedValueException('Array(x,y) of floats
expected');
}
$this->_coord = $val;
}
public hasCoord() {
return isset($this->_coord[0]) || isset($this->_coord[1]);
}
public delCoord() {
$this->_coord = array(0, 0);
}
}
This tells me two things:
a) Pretty damn complex and in that kind of the opposite of PHP's usual
KISS approach (Keep It Simple Safe).
b) Pretty sexy as it gives a hell lot of control and you can document
everything. Check out all the minor details and think of what that would
allow.
My conclusion is that even it looks sexy, it might be a bit tooooo
complex.
A much shorter thing to do might be:
interface Coord {
abstract $coord;
}
This would just somehow make sure the attribute $this->coord will be
accessible as a public attribute in the implementing class. The same
rules as for methods would apply.
Derick and me discussed solutions around abstract/virtual attributes a
lot in the passed. They were all refused however. But what we had in
mind also was more about specifying attributes in an abstract way in
classes so that they become documentable while being still handled
through __get() and friends.
marcus
Tuesday, April 29, 2008, 5:51:30 PM, you wrote:
The article explicitly mentions OOP interfaces in a few languages. But
the article, or for that matter any formal definition of an interface
isn't really what I asked about:My question was simply: why can't interfaces have properties?
John.
From: Nathan Nobbe [mailto:quickshiftin@gmail.com]
Sent: 29 April 2008 16:17
To: John Carter -X (johncart - PolicyApp Ltd at Cisco)
Cc: internals@lists.php.net
Subject: Re: Re: [PHP-DEV] Class Properties in Interfaces?
On Tue, Apr 29, 2008 at 6:28 AM, John Carter -X (johncart - PolicyApp
Ltd at Cisco) johncart@cisco.com wrote:
I think I must be missing something here, but this sounds a
little
tautological - "we can't do it because it doesn't make sense.
This is
because it doesn't make sense"Certainly most people (myself included) consider interfaces to
be
methods only, but I can't find a reason why not, and a
search-on-wikipedia-instead-of-doing-proper-research appears
to
allow
it:
http://en.wikipedia.org/wiki/Interface_%28computer_science%29
the problem with that article, as it pertains to this conversation is
that it is referring to interfaces as a general concept. 'interfaces'
can be formed in many ways, via extension of an abstract class or even
an expected set of a parameters in an HTTP request...
getting to the more concrete term 'interface' as it pertains to a
language keyword, interfaces define a contract; they do not specify
implementation details. member variables only facilitate the actions
member functions expose and therefore, they are part of the
implementation.
additionally, one can look to java (and likely others) to see that
public attributes are not supported on interfaces. here is a
definition
from a java5 cert book;
"When you create an interface, you're defining a contract for what a
class can do, without saying anything about how the class will do it.
An interface is a contract."
-nathan
Best regards,
Marcus
John Carter -X (johncart - PolicyApp Ltd at Cisco) schrieb:
could you explain why Interfaces can't have properties
Because interfaces are implemented which makes no sense for
attributes.
Sebastian,
This is true for the data storage representation of a property.
But, when you add the possibility of getters and setters, a property
becomes an abstraction. It would make sense that an interface
declares abstractly that a property will be available while leaving it
up to a class to implement it. Whether the implementation would be
through a instance variable or through accessor methods is an
implementation detail. This is known as the uniform access principle.
http://en.wikipedia.org/wiki/Uniform_access_principle
However, right now, we only have the virtual or "missing property"
technique of defining accessors with __get and __set, rather than a
structural syntax that could be used to verify interface
implementations. (The structural way could also offer better
reflection, better performance, differing visibility for getters and
setters, etc.)
Properties in interfaces make no sense now, but if we ever get a
structural method of declaring getters and setters, they might make
sense.
Best Regards,
Jeff
Hi!
But, when you add the possibility of getters and setters, a property
becomes an abstraction. It would make sense that an interface declares
Nothing prevents you from having getters and setters as part of the
interface :)
Properties in interfaces make no sense now, but if we ever get a
structural method of declaring getters and setters, they might make sense.
You can easily have it right now:
function __get($name) {
$name = "__get".ucfirst($name);
return $this->$name();
}
etc.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
I think there's been two responses to this query:
-
We can't have properties in interfaces because interfaces don't have
properties. I would say this is tautological and doesn't add anything. -
Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real technical
reason for not having properties in interfaces, but getters and setters
work just fine and no-one (including me) really misses them.
John.
On Tue, 2008-04-29 at 20:04 +0200, John Carter -X (johncart - PolicyApp
Ltd at Cisco) wrote:
I think there's been two responses to this query:
We can't have properties in interfaces because interfaces don't have
properties. I would say this is tautological and doesn't add anything.Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real technical
reason for not having properties in interfaces, but getters and setters
work just fine and no-one (including me) really misses them.
I have to agree. Enforcing existence of a property is just as much part
of an interface as enforcing the existence of a method. Why go down the
clutzy getter and setter method route when properties were meant to be
accessed. Why should code be made slower? Methods are at least an order
of magnitude slower than direct property access.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
Robert Cummings wrote:
On Tue, 2008-04-29 at 20:04 +0200, John Carter -X (johncart - PolicyApp
Ltd at Cisco) wrote:I think there's been two responses to this query:
We can't have properties in interfaces because interfaces don't have
properties. I would say this is tautological and doesn't add anything.Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real technical
reason for not having properties in interfaces, but getters and setters
work just fine and no-one (including me) really misses them.I have to agree. Enforcing existence of a property is just as much part
of an interface as enforcing the existence of a method. Why go down the
clutzy getter and setter method route when properties were meant to be
accessed. Why should code be made slower? Methods are at least an order
of magnitude slower than direct property access.Cheers,
Rob.
I'm glad someone out there agrees with me.
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex Corporation
Please note: This message has been sent with information that could be confidential and meant only for the intended recipient. If you are not the intended recipient, please delete all copies and inform us of the error as soon as possible. Thank you for your cooperation.
2008/4/30 Robert Cummings robert@interjinn.com:
On Tue, 2008-04-29 at 20:04 +0200, John Carter -X (johncart - PolicyApp
Ltd at Cisco) wrote:
I think there's been two responses to this query:
We can't have properties in interfaces because interfaces don't have
properties. I would say this is tautological and doesn't add anything.Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real technical
reason for not having properties in interfaces, but getters and setters
work just fine and no-one (including me) really misses them.I have to agree. Enforcing existence of a property is just as much part
of an interface as enforcing the existence of a method. Why go down the
clutzy getter and setter method route when properties were meant to be
accessed. Why should code be made slower? Methods are at least an order
of magnitude slower than direct property access.Cheers,
Rob.http://www.interjinn.com
Application and Templating Framework for PHP
There are some advantages.
1 - Read only / write only properties can be created more obviously,
rather than having the logic spread thoughout the __magic_functions.
2 - Automatic document tools get a real benefit from having a defined
mechanism to work from.
Using a simple shape class, it is a toss up between $shape->getArea()
vs $shape->area
If PHP supported setters/getters in this way, then the interface for a
shape would have a fCalcArea member function requirement. You may want
to have the area updated upon the change of any of the dimensions.
Ideally the interface should also have a read only property of area,
but the support of properties in an interface is disputed here. In
this limited example, it would seem useful.
Richard.
--
Richard Quadling
Zend Certified Engineer : http://zend.com/zce.php?c=ZEND002498&r=213474731
"Standing on the shoulders of some very clever giants!"
On Tue, Apr 29, 2008 at 6:14 PM, Richard Quadling rquadling@googlemail.com
wrote:
2008/4/30 Robert Cummings robert@interjinn.com:
On Tue, 2008-04-29 at 20:04 +0200, John Carter -X (johncart - PolicyApp
Ltd at Cisco) wrote:
I think there's been two responses to this query:
We can't have properties in interfaces because interfaces don't
have
properties. I would say this is tautological and doesn't add anything.Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real
technical
reason for not having properties in interfaces, but getters and
setters
work just fine and no-one (including me) really misses them.I have to agree. Enforcing existence of a property is just as much part
of an interface as enforcing the existence of a method. Why go down the
clutzy getter and setter method route when properties were meant to be
accessed. Why should code be made slower? Methods are at least an order
of magnitude slower than direct property access.Cheers,
Rob.http://www.interjinn.com
Application and Templating Framework for PHPThere are some advantages.
1 - Read only / write only properties can be created more obviously,
rather than having the logic spread thoughout the __magic_functions.
2 - Automatic document tools get a real benefit from having a defined
mechanism to work from.
not only that, but the only recourse to add logic to access of previously
declared public variables without changing the interface is to resort to
magic methods. up front, using public member variables may be enticing,
there are less instance methods and access is faster, sure. but when, down
the road, some logic is required around access, and the only recourse is to
employ a magic method, what would be slower then? the magic method doing
runtime introspection on the class instance prior to invoking said logic, or
having a purpose built method(s) there in the first place? obviously the
later; and that is just one more reason why getters and setters, coupled
with hidden member variables, make sense, even in php.
-nathan
On Tue, Apr 29, 2008 at 6:14 PM, Richard Quadling rquadling@googlemail.com
wrote:2008/4/30 Robert Cummings robert@interjinn.com:
On Tue, 2008-04-29 at 20:04 +0200, John Carter -X (johncart - PolicyApp
Ltd at Cisco) wrote:
I think there's been two responses to this query:
We can't have properties in interfaces because interfaces don't
have
properties. I would say this is tautological and doesn't add anything.Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real
technical
reason for not having properties in interfaces, but getters and
setters
work just fine and no-one (including me) really misses them.I have to agree. Enforcing existence of a property is just as much part
of an interface as enforcing the existence of a method. Why go down the
clutzy getter and setter method route when properties were meant to be
accessed. Why should code be made slower? Methods are at least an order
of magnitude slower than direct property access.Cheers,
Rob.http://www.interjinn.com
Application and Templating Framework for PHPThere are some advantages.
1 - Read only / write only properties can be created more obviously,
rather than having the logic spread thoughout the __magic_functions.
2 - Automatic document tools get a real benefit from having a defined
mechanism to work from.not only that, but the only recourse to add logic to access of previously
declared public variables without changing the interface is to resort to
magic methods. up front, using public member variables may be enticing,
there are less instance methods and access is faster, sure. but when, down
the road, some logic is required around access, and the only recourse is to
employ a magic method, what would be slower then? the magic method doing
runtime introspection on the class instance prior to invoking said logic, or
having a purpose built method(s) there in the first place? obviously the
later; and that is just one more reason why getters and setters, coupled
with hidden member variables, make sense, even in php.
That should be a matter of choice for the developer. When you say "but
when, down the road, some logic...", all I see is you waving your hands
in the air and presuming that the logic will change. The logic may not
change, in which case why am I incurring the cost of getter/setter
methods. "If" the logic changes, I'll be happy to add getter and setter
methods at that time and punt the needed functionality into the magic
methods which will call the appropriate getter or setter method. You are
preparing for a future that may not come, I am willing to retroactively
handle that future "if" it arrives. Neither approach strikes me as being
more correct but rather they each presume an educated guess on the
likelihood of the property changing it's semantics down the road.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
On Tue, Apr 29, 2008 at 9:22 PM, Robert Cummings robert@interjinn.com
wrote:
On Tue, Apr 29, 2008 at 6:14 PM, Richard Quadling <
rquadling@googlemail.com>
wrote:2008/4/30 Robert Cummings robert@interjinn.com:
On Tue, 2008-04-29 at 20:04 +0200, John Carter -X (johncart -
PolicyAppLtd at Cisco) wrote:
I think there's been two responses to this query:
We can't have properties in interfaces because interfaces don't
have
properties. I would say this is tautological and doesn't add
anything.Why would you need to? Getters and setters work.
So I suppose to answer my question for myself, there's no real
technical
reason for not having properties in interfaces, but getters and
setters
work just fine and no-one (including me) really misses them.I have to agree. Enforcing existence of a property is just as much
part
of an interface as enforcing the existence of a method. Why go down
the
clutzy getter and setter method route when properties were meant to
be
accessed. Why should code be made slower? Methods are at least an
order
of magnitude slower than direct property access.Cheers,
Rob.http://www.interjinn.com
Application and Templating Framework for PHPThere are some advantages.
1 - Read only / write only properties can be created more obviously,
rather than having the logic spread thoughout the __magic_functions.
2 - Automatic document tools get a real benefit from having a defined
mechanism to work from.not only that, but the only recourse to add logic to access of previously
declared public variables without changing the interface is to resort to
magic methods. up front, using public member variables may be enticing,
there are less instance methods and access is faster, sure. but when,
down
the road, some logic is required around access, and the only recourse is
to
employ a magic method, what would be slower then? the magic method doing
runtime introspection on the class instance prior to invoking said logic,
or
having a purpose built method(s) there in the first place? obviously the
later; and that is just one more reason why getters and setters, coupled
with hidden member variables, make sense, even in php.That should be a matter of choice for the developer. When you say "but
when, down the road, some logic...", all I see is you waving your hands
in the air and presuming that the logic will change. The logic may not
change, in which case why am I incurring the cost of getter/setter
methods. "If" the logic changes, I'll be happy to add getter and setter
methods at that time and punt the needed functionality into the magic
methods which will call the appropriate getter or setter method. You are
preparing for a future that may not come, I am willing to retroactively
handle that future "if" it arrives. Neither approach strikes me as being
more correct but rather they each presume an educated guess on the
likelihood of the property changing it's semantics down the road.
the developer does have a choice. to use an interface, or an abstract
class. data facilitates methods accomplishing what it is they purport.
quite frankly, i have never written an interface with getters and / or
setters anyway, nor do i see the need to. i would consider it silly.
interfaces are typically used to say, any class that makes this happen will
likely do it in a way differently than all the others. since, getters and
setters are almost always implemented the exact same way i find these topics
to be rather different. if there is in fact a standard way of doing things
for any given interface, then to realize it, a common implementor class can
be composed, and delegated to by classes that implement said interface in
the 'standard' way.
-nathan
On Tue, Apr 29, 2008 at 9:22 PM, Robert Cummings robert@interjinn.com
wrote:That should be a matter of choice for the developer. When you say
"but
when, down the road, some logic...", all I see is you waving your
hands
in the air and presuming that the logic will change. The logic may
not
change, in which case why am I incurring the cost of getter/setter
methods. "If" the logic changes, I'll be happy to add getter and
setter
methods at that time and punt the needed functionality into the
magic
methods which will call the appropriate getter or setter method. You
are
preparing for a future that may not come, I am willing to
retroactively
handle that future "if" it arrives. Neither approach strikes me as
being
more correct but rather they each presume an educated guess on the
likelihood of the property changing it's semantics down the road.the developer does have a choice. to use an interface, or an abstract
class. data facilitates methods accomplishing what it is they
purport.
quite frankly, i have never written an interface with getters and / or
setters anyway, nor do i see the need to. i would consider it silly.
interfaces are typically used to say, any class that makes this happen
will
likely do it in a way differently than all the others. since, getters
and
setters are almost always implemented the exact same way i find these
topics
to be rather different. if there is in fact a standard way of doing
things
for any given interface, then to realize it, a common implementor
class can
be composed, and delegated to by classes that implement said interface
in
the 'standard' way.
Abstract classes and interfaces are not the same. They are used for
fundamentally different reasons. An interface is to enforce a contract
for all implementations of the interface. Therefore if I were to create
an interface with an interface property of x, then all implementations
using that interface would know that property x exists and could use it
thusly without having to check for it's existence. Using an abstract
class is a hack, it's not sufficient for enforcement, and you can't
combine multiple abstract classes as you can with interfaces.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
On Wed, Apr 30, 2008 at 12:05 AM, Robert Cummings robert@interjinn.com
wrote:
On Tue, Apr 29, 2008 at 9:22 PM, Robert Cummings robert@interjinn.com
wrote:That should be a matter of choice for the developer. When you say
"but
when, down the road, some logic...", all I see is you waving your
hands
in the air and presuming that the logic will change. The logic may
not
change, in which case why am I incurring the cost of getter/setter
methods. "If" the logic changes, I'll be happy to add getter and
setter
methods at that time and punt the needed functionality into the
magic
methods which will call the appropriate getter or setter method. You
are
preparing for a future that may not come, I am willing to
retroactively
handle that future "if" it arrives. Neither approach strikes me as
being
more correct but rather they each presume an educated guess on the
likelihood of the property changing it's semantics down the road.the developer does have a choice. to use an interface, or an abstract
class. data facilitates methods accomplishing what it is they
purport.
quite frankly, i have never written an interface with getters and / or
setters anyway, nor do i see the need to. i would consider it silly.
interfaces are typically used to say, any class that makes this happen
will
likely do it in a way differently than all the others. since, getters
and
setters are almost always implemented the exact same way i find these
topics
to be rather different. if there is in fact a standard way of doing
things
for any given interface, then to realize it, a common implementor
class can
be composed, and delegated to by classes that implement said interface
in
the 'standard' way.Abstract classes and interfaces are not the same. They are used for
fundamentally different reasons. An interface is to enforce a contract
for all implementations of the interface. Therefore if I were to create
an interface with an interface property of x, then all implementations
using that interface would know that property x exists and could use it
thusly without having to check for it's existence.
i am fully aware of the differences between interfaces and abstract
classes. however, if a public method is defined on any class, abstract or
concrete, it may be used without checking by client code; i believe thats
the entire point..
Using an abstractclass is a hack, it's not sufficient for enforcement, and
you can't
combine multiple abstract classes as you can with interfaces.
abstract classes have their place. primarily they are well suited for
template method because some methods can be forced to be implemented by
children and others can be optionally overridden.
and lastly, coming to multiple inheritance (for lack of better terminology);
that is the only argument with any value for adding public attributes to the
interface construct; however i am still not receptive to it. from my
perspective data is an implementation detail, period.
-nathan
On Wed, Apr 30, 2008 at 12:05 AM, Robert Cummings
Abstract classes and interfaces are not the same. They are used for fundamentally different reasons. An interface is to enforce a contract for all implementations of the interface. Therefore if I were to create an interface with an interface property of x, then all implementations using that interface would know that property x exists and could use it thusly without having to check for it's existence.
i am fully aware of the differences between interfaces and abstract
classes. however, if a public method is defined on any class,
abstract or concrete, it may be used without checking by client code;
i believe thats the entire point..Using an abstractclass is a hack, it's not sufficient for enforcement, and you can't combine multiple abstract classes as you can with interfaces.
abstract classes have their place. primarily they are well suited for
template method because some methods can be forced to be implemented
by children and others can be optionally overridden.and lastly, coming to multiple inheritance (for lack of better
terminology); that is the only argument with any value for adding
public attributes to the interface construct; however i am still not
receptive to it. from my perspective data is an implementation
detail, period.
We are not talking about data here. We are talking about properties.
Data is assigned to a property which is akin to functionality being
assigned to a method. A property has all the features of the most simple
getter/setter method combination in one fell statement and without the
envelope overhead. As such, there is no reason why it could not be part
of the interface design.
Cheers,
Rob.
--
http://www.interjinn.com
Application and Templating Framework for PHP
On Wed, Apr 30, 2008 at 1:07 AM, Robert Cummings robert@interjinn.com
wrote:
On Wed, Apr 30, 2008 at 12:05 AM, Robert Cummings
Abstract classes and interfaces are not the same. They are used for fundamentally different reasons. An interface is to enforce a contract for all implementations of the interface. Therefore if I were to create an interface with an interface property of x, then all implementations using that interface would know that property x exists and could use it thusly without having to check for it's existence.
i am fully aware of the differences between interfaces and abstract
classes. however, if a public method is defined on any class,
abstract or concrete, it may be used without checking by client code;
i believe thats the entire point..Using an abstractclass is a hack, it's not sufficient for enforcement, and you can't combine multiple abstract classes as you can with interfaces.
abstract classes have their place. primarily they are well suited for
template method because some methods can be forced to be implemented
by children and others can be optionally overridden.and lastly, coming to multiple inheritance (for lack of better
terminology); that is the only argument with any value for adding
public attributes to the interface construct; however i am still not
receptive to it. from my perspective data is an implementation
detail, period.We are not talking about data here. We are talking about properties.
Data is assigned to a property which is akin to functionality being
assigned to a method. A property has all the features of the most simple
getter/setter method combination in one fell statement and without the
envelope overhead. As such, there is no reason why it could not be part
of the interface design.
so a 'property' could be any data type? that sounds contradictory to the
concept of an interface to me. the only special connotation i have ever
encountered for the term 'property' is my very brief work w/ vb.net as a
teacher. there is a mechanism whereby getters and setters can be declared
and a member variable can be named.. then when using instances of the
class, client code uses the name of the 'property' which has the same syntax
as accessing a public data member, however, the client is transparently
being driven through the methods of the 'property'. between SPL
ArrayAccess, and magic methods, php already has multiple ways to realize
'properties'.
-nathan
We are not talking about data here. We are talking about properties. Data is assigned to a property which is akin to functionality being assigned to a method. A property has all the features of the most simple getter/setter method combination in one fell statement and without the envelope overhead. As such, there is no reason why it could not be part of the interface design.
so a 'property' could be any data type? that sounds contradictory to
the concept of an interface to me. the only special connotation i
have ever encountered for the term 'property' is my very brief work
w/ vb.net as a teacher. there is a mechanism whereby getters and
setters can be declared and a member variable can be named.. then
when using instances of the class, client code uses the name of the
'property' which has the same syntax as accessing a public data
member, however, the client is transparently being driven through the
methods of the 'property'. between SPL ArrayAccess, and magic
methods, php already has multiple ways to realize 'properties'.
Seriously, are you having this much difficulty understanding that a
property is not itself data until such time as it is given a value? If I
say something has colour I haven't said what colour, only that it has
colour. Red, blue, green, these are data. "colour" is a property. If I
had an interface where I defined the following:
<?php
Interface Fibre
{
public $colour;
}
?>
I'm saying that all classes that implement Fibre must have a $colour
property. i didn't say what colour.
<?php
Class Hair implements Fibre
{
public $colour = null;
}
$hair = new Hair();
$hair->colour = 'brown';
?>
The above is a much less wordy way of doing the following:
<?php
Interface Fibre
{
public function setColour( $colour );
public function getColour();
}
Class Hair implements Fibre
{
public $colour = null;
public function setColour( $colour )
{
$this->colour = $colour;
}
public function getColour()
{
return $this->colour;
}
}
$hair = new Hair();
$hair->setColour( 'brown' );
?>
Now do you see the equivalence? I don't think I can simplify it anymore.
Since they are equivalent your argument is void since it hinges on data.
To throw your void argument back at you about a "property can be any
type" so too can a parameter:
$hair->setColour( 3.14 );
This is a feature of a dynamic language, not a flaw in my argument. And
to beat the dead horse... a parameter declaration isn't data either.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
$hair = new Hair();
$hair->colour = 'brown';
You can do this without pre-defining any properties.
The above is a much less wordy way of doing the following:
No, it is not the same. You can override what happens when you do
setColor - like send notification to some other object or set also
matching color for the shoes, etc. :) but you can't have any behavior
attached to setting value.
This is a feature of a dynamic language, not a flaw in my argument. And
Not having rigid definitions of properties is also a feature of dynamic
language ;)
--
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
$hair = new Hair();
$hair->colour = 'brown';You can do this without pre-defining any properties.
yes but the following (as I'm you certainly know):
echo $hair->colour
generates an E_NOTICE
if the property isn't defined.
The above is a much less wordy way of doing the following:
No, it is not the same. You can override what happens when you do
setColor - like send notification to some other object or set also
matching color for the shoes, etc. :) but you can't have any behavior
attached to setting value.
But it is the same... I can override the behaviour in magic get/set
methods if I want. But the point is not necessarily to override, only to
ensure the property is defined by all users of the interface. One
approach (the getter/setter approach) is more versatile downstream (in
the possibly unlikely event that the semantics for the property need to
change), the other approach is more efficient.
This is a feature of a dynamic language, not a flaw in my argument. And
Not having rigid definitions of properties is also a feature of dynamic
language ;)
There's nothing rigid about what Jeremy proposed. He just asked why
properties can't be part of an interface definition. I don't see why
not, I've shown the equivalence of properties to getter/setter methods
(in simple usage case anyways), and so I've argued the point. It's not a
particularly necessary feature for me, but that doesn't negate his
original question as to why they couldn't be supported. Anyways, I'll
stop being noisy on the list now. Nothing more to add :)
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
On Wed, Apr 30, 2008 at 12:01 AM, Robert Cummings robert@interjinn.com
wrote:
On Wed, Apr 30, 2008 at 1:07 AM, Robert Cummings robert@interjinn.com
wrote:We are not talking about data here. We are talking about properties. Data is assigned to a property which is akin to functionality being assigned to a method. A property has all the features of the most simple getter/setter method combination in one fell statement and without the envelope overhead. As such, there is no reason why it could not be part of the interface design.
so a 'property' could be any data type? that sounds contradictory to
the concept of an interface to me. the only special connotation i
have ever encountered for the term 'property' is my very brief work
w/ vb.net as a teacher. there is a mechanism whereby getters and
setters can be declared and a member variable can be named.. then
when using instances of the class, client code uses the name of the
'property' which has the same syntax as accessing a public data
member, however, the client is transparently being driven through the
methods of the 'property'. between SPL ArrayAccess, and magic
methods, php already has multiple ways to realize 'properties'.Seriously, are you having this much difficulty understanding that a
property is not itself data until such time as it is given a value? If I
say something has colour I haven't said what colour, only that it has
colour. Red, blue, green, these are data. "colour" is a property. If I
had an interface where I defined the following:<?php
Interface Fibre
{
public $colour;
}?>
I'm saying that all classes that implement Fibre must have a $colour
property. i didn't say what colour.<?php
Class Hair implements Fibre
{
public $colour = null;
}$hair = new Hair();
$hair->colour = 'brown';?>
The above is a much less wordy way of doing the following:
<?php
Interface Fibre
{
public function setColour( $colour );public function getColour();
}Class Hair implements Fibre
{
public $colour = null;public function setColour( $colour )
{
$this->colour = $colour;
}public function getColour()
{
return $this->colour;
}
}$hair = new Hair();
$hair->setColour( 'brown' );?>
Now do you see the equivalence? I don't think I can simplify it anymore.
Since they are equivalent your argument is void since it hinges on data.
To throw your void argument back at you about a "property can be any
type" so too can a parameter:$hair->setColour( 3.14 );
This is a feature of a dynamic language, not a flaw in my argument. And
to beat the dead horse... a parameter declaration isn't data either.
so really, all we would get is a group of member variables we know would be
there... wow, that seems pretty pointless to me. and in the case of the
setter, the client doesnt know about the logic behind the call, so the fact
is supplying 3.14 may not result in 3.14 actually getting set. this is why
setter methods are import, per my previous statements. i do not consider
adding data 'after declaring properties' in interfaces equivalent to
supplying an implementation for the method, because php is not strongly
typed, therefore no class will ever be able to control what sort of data is
set on the properties. that is the entire problem with your proposition.
i have to work today, and im sure people are getting sick of my bickering,
but truthfully, i would like to know why interfaces were added to php in the
first place? where, if any place, did they take inspiration from, java,
c++, neither ? i only ask because im dying to know and we're on the topic..
-nathan
so really, all we would get is a group of member variables we know
would be there...
No, you know nothing about the existence of properties when using
getters and setters. Just because you have getColour() and setColour()
in no way implies you have $this->colour
wow, that seems pretty pointless to me.
It would seem it does. Wrapping all my properties in redundant
getter/setter methods often seems pointless to me and a whole slew of
other people.
and in the case of the setter, the client doesnt know about the logic
behind the call, so the fact is supplying 3.14 may not result in 3.14
actually getting set.
You're presuming logic. I'm not. I just want to get/set the property
without invoking a function call. If properties didn't have their uses,
then you wouldn't be able to access them from the object. Since I'm not
forced to use a getter/setter method, then it follows that properties
were designed to be accessed and not necessarily wrapped in a method for
retrieval and setting.
this is why setter methods are import, per my previous statements.
Important for some. You once again, with all your hand flapping, assume
we want some kind of operation on the data. If we do not, and this
happens a lot, then we're just wasting cycles... and order of magnitude
more cycles.
i do not consider adding data 'after declaring properties' in
interfaces equivalent to supplying an implementation for the method,
because php is not strongly typed, therefore no class will ever be
able to control what sort of data is set on the properties. that is
the entire problem with your proposition.
Ummm, this functionality already exists. Your argument neglects to
consider that objects already exist where the properties can be directly
accessed and set. Your argument assumes a need to "manage" the data
being assigned. Your argument assumes the data wasn't already "managed"
by the assigner of the data. You assume a lot, and yet we all know in
practice there are many, many, MANY implementations of classes where the
properties are directly exposed. This may not be something YOU like, but
it is what many others like. Some people still care about efficient code
versus the flexibility of meeting a demand that may never arise.
i have to work today, and im sure people are getting sick of my
bickering, but truthfully, i would like to know why interfaces were
added to php in the first place? where, if any place, did they take
inspiration from, java, c++, neither ? i only ask because im dying to
know and we're on the topic..
Create a new thread. You rider question isn't relevant to this thread.
Cheers,
Rob.
--
http://www.interjinn.com
Application and Templating Framework for PHP
On Wed, Apr 30, 2008 at 9:55 AM, Robert Cummings robert@interjinn.com
wrote:
so really, all we would get is a group of member variables we know
would be there...No, you know nothing about the existence of properties when using
getters and setters. Just because you have getColour() and setColour()
in no way implies you have $this->colour
right, thats exactly it, the client doesnt know anything about the data. it
is being driven through a well-defined interface whereby the client has no
control but to ask the provider to do something for it.
wow, that seems pretty pointless to me.
It would seem it does. Wrapping all my properties in redundant
getter/setter methods often seems pointless to me and a whole slew of
other people.
so put the public properties on classes that implement interfaces. as i
said, getters and setters on an interfaces make little sense, since
implementors are assumed to provide different implementations.
and in the case of the setter, the client doesnt know about the logic
behind the call, so the fact is supplying 3.14 may not result in 3.14
actually getting set.You're presuming logic. I'm not. I just want to get/set the property
without invoking a function call. If properties didn't have their uses,
then you wouldn't be able to access them from the object. Since I'm not
forced to use a getter/setter method, then it follows that properties
were designed to be accessed and not necessarily wrapped in a method for
retrieval and setting.
i understand your point. but just because the public access level exists,
doesnt mean it was intended that member variables be assigned that level of
access either. convention is to mark member variables protected or private,
and drive access through a public well-defined interface. i have read at
least a dozen books, ranging from various languages and topics and never
have i heard of properties constituting part of the interface. indeed this
would be an entirely new concept after generations that have arrived at the
conclusion that an interface is a set of methods signatures.
this is why setter methods are import, per my previous statements.
Important for some. You once again, with all your hand flapping, assume
we want some kind of operation on the data. If we do not, and this
happens a lot, then we're just wasting cycles... and order of magnitude
more cycles.
you are currently free to place public properties on any class or abstract
class you wish. imho, that is entirely adequate. what i can say however,
is that allowing such a feature forces designers and groups of developers to
fall back on convention. that deviates from the entire purpose of
interfaces. interfaces are about control; you must adhere to this
contract. since php is loosely typed, the only way to maintain the
'intended' use of these properties would mean rigorous checking by
developers of the code at design time. im not saying this is impossible, or
something some people wouldnt be happy to do, in light of the performance
gains. but the fact remains, the only thing that could maintain the
integrity of the public properties would be rigorously maintained
conventions.
i do not consider adding data 'after declaring properties' in
interfaces equivalent to supplying an implementation for the method,
because php is not strongly typed, therefore no class will ever be
able to control what sort of data is set on the properties. that is
the entire problem with your proposition.
Ummm, this functionality already exists. Your argument neglects to
consider that objects already exist where the properties can be directly
accessed and set. Your argument assumes a need to "manage" the data
being assigned. Your argument assumes the data wasn't already "managed"
by the assigner of the data. You assume a lot, and yet we all know in
practice there are many, many, MANY implementations of classes where the
properties are directly exposed. This may not be something YOU like, but
it is what many others like. Some people still care about efficient code
versus the flexibility of meeting a demand that may never arise.
this much you are right about.
i have to work today, and im sure people are getting sick of my
bickering, but truthfully, i would like to know why interfaces were
added to php in the first place? where, if any place, did they take
inspiration from, java, c++, neither ? i only ask because im dying to
know and we're on the topic..Create a new thread. You rider question isn't relevant to this thread.
fine.
-nathan
If you guys don't like the way interfaces work then do not use them. If your
going to talk about cycles, just lose the abstraction all together.
Important for some. You once again, with all your hand flapping, assume
we want some kind of operation on the data. If we do not, and this
happens a lot, then we're just wasting cycles... and order of magnitude
more cycles.
You speak of cycles, but I downloaded your framework that you created and
grepped for get and set methods, and what did I find? Thinks like:
function getId()
{
return $this->sessionId;
}
function setId( $newId )
{
$this->sessionId = $newId;
}
function setNew( $status=true )
{
$this->newSession = true;
}
function isNew()
{
return $this->newSession;
}
function &getDataStructure()
{
return $this->data;
}
This is wasting space in my mailbox, this conversation is pointless. I'm
trying to read about thinks that are important like language changes.
-Chris
If you guys don't like the way interfaces work then do not use them.
If your going to talk about cycles, just lose the abstraction all
together.Important for some. You once again, with all your hand flapping, assume we want some kind of operation on the data. If we do not, and this happens a lot, then we're just wasting cycles... and order of magnitude more cycles.
You speak of cycles, but I downloaded your framework that you created
and grepped for get and set methods, and what did I find? Thinks like:function getId() { return $this->sessionId; } function setId( $newId ) { $this->sessionId = $newId; } function setNew( $status=true ) { $this->newSession = true; } function isNew() { return $this->newSession; } function &getDataStructure() { return $this->data; }
This is wasting space in my mailbox, this conversation is pointless.
I'm trying to read about thinks that are important like language
changes.
I use both styles where I find them appropriate. I already mentioned in
a previous email that support of such a feature doesn't impact me much,
but that Jeremey's original argument is still valid. Personal attacks on
my coding style or my framework have no bearing on the topic being
discussed. My framework was originally designed 6 years ago before many
of the great features of PHP5. Feel free to sit back down and ignore
these emails. BTW, hard-drive space is cheap, "wasting space" is such a
bullshit argument for text emails.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
an interface with an interface property of x, then all implementations
using that interface would know that property x exists and could use it
You can use property in PHP without declaring it previously.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
an interface with an interface property of x, then all implementations
using that interface would know that property x exists and could use itYou can use property in PHP without declaring it previously.
But then you need to check if it exists lest you raise an E_NOTICE
because it doesn't exist. Additionally, E_NOTICE
is run-time, interface
checking is compile-time.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
But then you need to check if it exists lest you raise an
E_NOTICE
because it doesn't exist. Additionally,E_NOTICE
is run-time, interface
checking is compile-time.
I don't understand what you mean here. PHP can't check variable accesses
compile-time. In fact, in PHP "compile-time" doesn't mean much anyway,
since everything is runtime.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
But then you need to check if it exists lest you raise an
E_NOTICE
because it doesn't exist. Additionally,E_NOTICE
is run-time, interface
checking is compile-time.I don't understand what you mean here. PHP can't check variable accesses
compile-time. In fact, in PHP "compile-time" doesn't mean much anyway,
since everything is runtime.
Oh, I'm sorry, perhaps I should have said parse time-- either way PHP
does compile an internal bytecode so compile-time is not incorrect.
Obviously interface errors are detected when the script is parsed NOT
when the code itself is run. if PHP can check method definition
compliance when the script is parsed, surely it can check property
definition compliance also.
Cheers,
Rob.
http://www.interjinn.com
Application and Templating Framework for PHP
I would start by saying it's bad design. you should use getters and setters
which you can define in you interface
--
/James
On Tue, Apr 29, 2008 at 11:07 AM, John Carter -X (johncart - PolicyApp Ltd
at Cisco) johncart@cisco.com wrote:
Marcus,
I understand why Interfaces can't have bodies, but could you explain why
Interfaces can't have properties?Thanks,
John.
-----Original Message-----
From: Marcus Boerger [mailto:helly@php.net]
Sent: 29 April 2008 10:46
To: Jeremy Privett
Cc: PHP Developers Mailing List
Subject: Re: [PHP-DEV] Class Properties in Interfaces?Hello Jeremy,
interfaces cannot have properties, nor can they have method bodies -
that is the whole purpose of interfafces. We are thinking of adding
traits which would allow for both but would treat inheritance
differently. Until we get that you would need to provide an abstract
interface to access data in the same way.marcus
Tuesday, April 29, 2008, 5:31:33 AM, you wrote:
Hey list,
I was curious what everyone thought of implementing the ability to
specify class members in interfaces. I've run into a couple of
circumstances where I would like to specify public member names insideof an interface to ensure that these members are accessed in a
standard way and to ensure that they exist. Currently, trying to
include them in an interface results in "Fatal error: Interfaces maynot include member variables in file/line number".
Thoughts?
Thanks.
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex CorporationPlease note: This message has been sent with information that could be
confidential and meant only for the intended recipient. If you are not
the intended recipient, please delete all copies and inform us of the
error as soon as possible. Thank you for your cooperation.Best regards,
Marcus--
To unsubscribe,
visit: http://www.php.net/unsub.php
It might be bad design, but design is down to the application developer
and not the people who define a language.
I'm not necessary asking for the feature, I just want to understand why
we can't do it.
John.
James Dempster schrieb:
you should use getters and setters which you can define in interface
BTW: An attribute with getter and setter is what I would call a
property.
--
Sebastian Bergmann http://sebastian-bergmann.de/
GnuPG Key: 0xB85B5D69 / 27A7 2B14 09E4 98CD 6277 0E5B 6867 C514 B85B 5D69
Hi!
I understand why Interfaces can't have bodies, but could you explain why
Interfaces can't have properties?
Interfaces are API descriptions. API is usually seen as composed of
functions. Some go even as far as recommending even classes don't have
public properties at all :)
In any case, whenever you want to write $foo->bar, just write
$foo->getBar() and $foo->setBar(), and it'd work :)
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
Hi Stas, hi everbody,
Am Dienstag, den 29.04.2008, 10:22 -0700 schrieb Stanislav Malyshev:
[...]
In any case, whenever you want to write $foo->bar, just write
$foo->getBar() and $foo->setBar(), and it'd work :)
I think the issue is, that PHP does not have defined properties with
attached validation (yes, I know about __get()/__set()). Now we just
have plain properties that may contain everything. If we would have
something like this:
class Clazz
{
public $property
{
function get()
{
return $this->property;
}
function set($property)
{
$this->property = (int)$property;
}
}
}
In this case it, maybe it would make sense to allow definitions of
properties in interfaces. For example the following could require a
property to be read only:
class Clazz
{
public $property
{
function get();
}
}
An interface defines a halfway strict API. Allowing the current
properties in interfaces would not add any sensible functionality
because it would not define the API better.
cu, Lars
Hi!
have plain properties that may contain everything. If we would have
something like this:
You can easily do this by having __get call getProperty. That's like 1
line of code to do. No language change needed.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
Stanislav Malyshev wrote:
Hi!
have plain properties that may contain everything. If we would have
something like this:You can easily do this by having __get call getProperty. That's like 1
line of code to do. No language change needed.
I don't know about you, but I'm not interested in that kind of
performance trade-off.
--
Jeremy Privett
C.E.O. & C.S.A.
Omega Vortex Corporation
Please note: This message has been sent with information that could be confidential and meant only for the intended recipient. If you are not the intended recipient, please delete all copies and inform us of the error as soon as possible. Thank you for your cooperation.
Good evening Stas,
Am Mittwoch, den 30.04.2008, 10:02 -0700 schrieb Stanislav Malyshev:
[...]
You can easily do this by having __get call getProperty. That's like 1
line of code to do. No language change needed.
With the substantial difference, that __get()/__set() does not work
properly with inheritance, as the language can't verify the LSP.
class Mother
{
public function __set($property, $value)
{
switch ($property) {
case 'foo':
$this->_foo = (string)$value;
return true;
}
}
}
class Child extends Mother
{
public function __set($property, $value)
{
switch ($property) {
case 'foo':
throw new Exception('Foo is not allowed to set');
}
return parent::__set($property, $value);
}
}
This means, Child behaves more strict than Mother and breaks the
principle.
With advanced properties, the interpreter could at least verify that
getting/setting properties is not stricter in subclasses.
SO far, Lars
Hi!
With the substantial difference, that __get()/__set() does not work
properly with inheritance, as the language can't verify the LSP.
Language never could verify the LSP. The developer should do it - the
language has no idea of what pre/postconditions in your code are.
Language can provide a tiny bit of LSP support - namely, method
signatures, etc. - but that's it.
This means, Child behaves more strict than Mother and breaks the
principle.
Well, don't write such code. :)
With advanced properties, the interpreter could at least verify that
getting/setting properties is not stricter in subclasses.
How? For that you'd need the interpreter to actually understand what the
code does. While I'd like to have such thing one day (provided it does
not rebel and decide to kill all humans, of course ;) PHP interpreter is
definitely not it.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com
Am Mittwoch, den 30.04.2008, 12:25 -0700 schrieb Stanislav Malyshev:
[...]
How? For that you'd need the interpreter to actually understand what the
code does. While I'd like to have such thing one day (provided it does
not rebel and decide to kill all humans, of course ;) PHP interpreter is
definitely not it.
Take a look at this:
class Mother
{
public $foo
{
function get()
{
}
}
}
class Child extends Mother
{
public $foo
{
}
}
In Child $foo is redefined without a getter-method. This breaks the
substitution principle and the language can detect this.
cu, Lars
Hi!
In Child $foo is redefined without a getter-method. This breaks the
How it's not "in Child the get method is inherited from Mother"? But
suppose it is as you say. Yes, in this particular case it would be
detected - however, it is not the code you brought in the last example,
where the actual code - not method presence - was changed.
Summarily, LSP can not be enforced by language means. The language can
only give support for some limited subset of cases. PHP's get/set
handlers allow you to do the same as your property syntax and more,
albeit with different syntax.
Stanislav Malyshev, Zend Software Architect
stas@zend.com http://www.zend.com/
(408)253-8829 MSN: stas@zend.com