php.net |  support |  documentation |  report a bug |  advanced search |  search howto |  statistics |  random bug |  login
Request #49526 C# style property get/set syntax
Submitted: 2009-09-11 01:02 UTC Modified: 2021-03-15 16:51 UTC
Votes:59
Avg. Score:4.5 ± 1.1
Reproduced:36 of 37 (97.3%)
Same Version:25 (69.4%)
Same OS:22 (61.1%)
From: president at basnetworks dot net Assigned:
Status: Suspended Package: Scripting Engine problem
PHP Version: * OS: *
Private report: No CVE-ID: None
View Add Comment Developer Edit
Welcome! If you don't have a Git account, you can't do anything here.
You can add a comment by following this link or if you reported this bug, you can edit this bug over here.
(description)
Block user comment
Status: Assign to:
Package:
Bug Type:
Summary:
From: president at basnetworks dot net
New email:
PHP Version: OS:

 

 [2009-09-11 01:02 UTC] president at basnetworks dot net
Description:
------------
I would like to request a C# style get/set syntax (called a property in C#) for PHP.  Basically, it looks and acts like a class member/variable from outside the class, but it is actually a set of two methods.  It can be used to provide only read or write access to a class member, do pre or post processing on a member, or be completely dynamic like a set of class methods.

A property contains two methods between braces, named get and set.  get must always have a return statement, while set has a magic variable "value" or "$value" which is the variable that was passed to the property.  Either method can be omitted to make the property read-only or write-only.

The same effect can be achieved by creating a GetVar() and SetVar() method to create a sudo-property "var", although it is by far much clumsier and less intuitive.

I also realize the same effect received outside the class can be achieved using the __get() and __set() methods, but these methods are only really useful in a small instance of situations, like giving access to an internal array as though each index is a property.  These magic methods are not at all useful for using on an individual property basis, and it gets worse when inheritance is introduced.

The C# syntax is as follows:

class TimePeriod
{
    private double seconds;

    public double Hours
    {
        get { return seconds / 3600; }
        set { seconds = value * 3600; }
    }
}



The PHP syntax would be similar to the following:

class TimePeriod
{
    private $seconds;

    public property Hours
    {
        get { return $this->seconds / 3600; }
        set { $this->seconds = $value * 3600; }
    }
}



You would use it exactly the same as a public class member:

$time = new TimePeriod();
$time->Hours = 24;
echo $time->Hours;



As opposed to the alternative:
$time = new TimePeriod();
$time->SetHours(24);
echo $time->GetHours();



Additionally, the get and set methods can have separate visibilities like in the following example where get is public and set is protected:

public property Name
{
    get { return $this->name; }
    protected set { $this->name = $value; }
}



There is another ticket that is similar but not the same thing here:
http://bugs.php.net/bug.php?id=34194

It suggests separate getter/setter methods, which in my opinion are much less intuitive.  I believe that following the C# format would help to keep a standard format, and would be the least confusing.

The poster of that bug also fails to realize that separate visibility levels can be achieved for properties using the C# syntax, as shown above.



The C# documentation on properties is available here:
http://msdn.microsoft.com/en-us/library/x9fsa0sw%28VS.80%29.aspx

The C# documentation on Asymmetric Accessor Accessibility for properties is available here:
http://msdn.microsoft.com/en-us/library/75e8y5dd%28VS.80%29.aspx


Patches

v2.2 (last revision 2011-12-12 03:55 UTC by php-dev at zerocue dot com)
v2.1 (last revision 2011-12-12 00:17 UTC by php-dev at zerocue dot com)
accessor_v2.diff (last revision 2011-12-11 19:20 UTC by php-dev at zerocue dot com)

Add a Patch

Pull Requests

Add a Pull Request

History

AllCommentsChangesGit/SVN commitsRelated reports
 [2009-09-12 12:22 UTC] kalle@php.net
Hey

The best way to request this feature is to write an RFC in our wiki at:
http://wiki.php.net/rfc/

Request an account at:
http://wiki.php.net/start?do=register

And then send an email to the webmaster list (php-webmaster@lists.php.net) requesting write access to the rfc namespace and repost this feature request as an RFC. When you are done, start a new thread on internals (internals@lists.php.net) explaining your RFC.

As for reference, this idea was discussed at the last PDM in May, see:
http://wiki.php.net/summits/pdmnotesmay09#php_6 point #16
 [2009-09-13 04:24 UTC] president at basnetworks dot net
Hi Kalle,

Thanks for the information.  I will follow your instructions and start working on the RFC over the next week(s).  Also, thanks for the link about the Developer Summit, but it does not show the outcome of the discussion, am I able to find that anywhere?
 [2009-09-13 19:56 UTC] president at basnetworks dot net
For reference, the RFC for this feature request now exists at this URL:

http://wiki.php.net/rfc/propertygetsetsyntax
 [2010-10-28 00:48 UTC] rayro at gmx dot de
I also recommend this but i have a little idea too:

1. Most of the time i use get<VariableName>() syntax and I have to write new functions for that (or using __call or __set), because i protect the properties with private or protected to protect for writing them.
2. Most of all the code is ugly or has limitations using readonly/writeonly properties with __get(&$v) or __set($v,&$c) by reference.
3. It is not perfectly clean to write less code with __get or getter/setter if only want to protecting them... And less code matters!

I would like to see a new, or 2 new keywords, e.g. "readonly" and "writonly", because the code will look smoother and i dont have to make the use of magic methods... Or some own designed errors for that...

Now an simple example:
======================

<?php
class A
{
  /** the following syntax is just invented  **/
  static readable protected $foo = 1;
  static writable protected $bar = 2;
}

A::$foo++; // raises error "variable is not writeable from this context"
echo(A::$foo); // will simple echo $foo
A::$bar++; // will increment $bar to 3
echo(A::$bar); // raises error "variable is not readable from this context"
?>

( what about is_readable() or is_writable() for that? )
I dont think that these functions will be used, so only Reflection should be extended...

and now, instead of the current syntax:
======================================

<?php
class A
{
  static protected $foo = 1;
  static protected $bar = 1;
  function __get($v) {
    if ($v == 'bar') {
      trigger_error('$bar is not readble from this context',E_USER_ERROR);
    }
    return $this->$v;
  }
  function __set($v, $c)
  {
    if ($v == 'foo') {
      trigger_error('$foo is not writable from this context',E_USER_ERROR);
    }
    $this->$v = $c;
    return true;
  }
}
?>

get/set syntax will be nice but also nasty if only read/writablity is desired...

this can be confusing as this:
==============================
<?php
class A
{
  /** the following syntax is just invented  **/
  static protected $foo {
    function __get() {
      return $this->foo;
    }
    function __set() {
      trigger_error('$foo is not writable from this context',E_USER_ERROR);
    }
  } = 1;
  static protected $bar {
    function __get() {
      trigger_error('$bar is not readable from this context',E_USER_ERROR);
    }
    function __set() {
      $this->bar = 1;
      return true;
    }
  } = 2;
}
?>

think about it... many developers will waive the old way or functions like getVarname and setVarname... and for all other, getter/setter will be nice as described in the rfc...
 [2010-12-29 12:27 UTC] jani@php.net
-Package: Feature/Change Request +Package: Scripting Engine problem -Operating System: +Operating System: * -PHP Version: 6SVN-2009-09-11 (SVN) +PHP Version: *
 [2012-01-28 01:45 UTC] phpdev at zerocue dot com
An "as implemented" document has been created here:
https://wiki.php.net/rfc/propertygetsetsyntax-as-implemented

Only thing remaining to be implemented is static accessors.
 [2013-01-09 01:36 UTC] anka17pinky at yahoo dot com
I wish this request was implemented in PHP 5.5 :(

There are so many questions on SO asking for ways to implement readonly properties in PHP...
 [2013-03-02 18:36 UTC] reeze@php.net
@see https://wiki.php.net/rfc/propertygetsetsyntax-v1.2

this RFC failed to win the vote sadly.
 [2015-03-21 15:48 UTC] andreas dot prucha at gmail dot com
I noticed that the RFC failed because it did not pass the 2/3-Limit, but got more than 50 %.

I would also like to see support for properties as I know them from Delphi/ObjectPascal. Basically it's 

property <propertyName> read <var-or-getter> write <var-or-setter>

In PHP I could imagine a syntax 

property <propertyName> get <var-or-getter> set <var-or-setter>

for Example:

public property $foo get $bar set setFoo;

This means reading from $this->foo would read $bar directly, while writing to $this->foo would call the method setFoo, passing the value.

Implementation in PhpDocumentor would also be quite easy.
 [2021-03-15 16:51 UTC] cmb@php.net
-Status: Open +Status: Suspended
 [2021-03-15 16:51 UTC] cmb@php.net
This is certainly a useful feature, but clearly requires the RFC
process[1].  Anybody is welcome to pursue this process.  For the
time being, I suspend this ticket.

[1] <https://wiki.php.net/rfc/howto>
 
PHP Copyright © 2001-2024 The PHP Group
All rights reserved.
Last updated: Thu Apr 18 13:01:27 2024 UTC