Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Can PHP objects be constructed and their variables set in one operation?

In perl I'm used to doing

my $foo = new WhatEver( bar => 'baz' );

and now I'm trying to figure out if PHP objects can ever be constructed this way. I only see this:

my $foo = new WhatEver();
$foo->{bar} = 'baz';

is it possible to do it in one step?

like image 323
AmbroseChapel Avatar asked May 30 '13 23:05

AmbroseChapel


3 Answers

You can lay out your constructor as follows:

 class MyClass {
     public function __construct($obj=null) {
         if ($obj && $obj instanceof Traversable || is_array($obj)) {
             foreach ($obj as $k => $v) {
                if (property_exists($this,$k)) {
                    $this->{$k} = $v;
                }
             }
         }
     }
 }

This has a serie of drawbacks:

  • This is inefficient
  • The variables you create will not show up on any doc software you use
  • This is the open door to all forms of slackery

However, it also presents the following benefits:

  • This can be extended pretty safely
  • It allows you to lazy-implement variables
  • It also allows you to set private variables, provided that you know their names. It is pretty good in that respect if not abused.
like image 115
Sébastien Renauld Avatar answered Sep 18 '22 23:09

Sébastien Renauld


The parameters passed in the parentheses (which can be omitted, by the way, if there aren't any) go to the constructor method where you can do whatever you please with them. If a class is defined, for example, like this:

class WhatEver
{
    public $bar;

    public function __construct($bar)
    {
        $this -> bar = $bar;
    }
}

You can then give it whatever values you need.

$foo = new WhatEver('baz');
like image 45
pilsetnieks Avatar answered Sep 20 '22 23:09

pilsetnieks


There are a few ways to accomplish this, but each has its own drawbacks.

If your setters return an instance of the object itself, you can chain your methods.

my $foo = new WhatEver();
$foo->setBar("value")->setBar2("value2");

class WhatEver
{
    public $bar;
    public $bar2;

    public function setBar($bar)
    {
        $this->bar = $bar;
        return $this;
    }

    public function setBar2($bar2)
    {
        $this->bar2 = $bar2;
        return $this;
    }
}

However, this doesn't reduce it to one step, merely condenses every step after instantiation.

See: PHP method chaining?

You could also declare your properties in your constructor, and just pass them to be set at creation.

my $foo = new WhatEver($bar1, $bar2, $bar3);

This however has the drawback of not being overtly extensible. After a handful of parameters, it becomes unmanageable.

A more concise but less efficient way would be to pass one argument that is an associative array, and iterate over it setting each property.

like image 37
radicalpi Avatar answered Sep 18 '22 23:09

radicalpi