views:

3244

answers:

6

So, in PHPDoc one can specify @var above the member variable declaration to hint at its type. Then an IDE, for ex. PHPEd, will know what type of object it's working with and will be able to provide a code insight for that variable.

<?php
  class Test
  {
    /** @var SomeObj */
    private $someObjInstance;
  }
?>

This works great until I need to do the same to an array of objects to be able to get a proper hint when I iterate through those objects later on.

So, is there a way to declare a PHPDoc tag to specify that the member variable is an array of SomeObj's? @var array is not enough, and @var array(SomeObj) doesn't seem to be valid, for example.

A: 

you can use the casting syntax for your variables. to cast a variable into a specific data type, you may use this syntax: (type) value. like this:

$number = '1';
echo (integer)$number + 3;
// output: 4;

if you use this kind of syntax when you are using your array members, you could hope that your IDE supports it. like this

private $userList = array();
$userList = User::fetchAll(); // now $userList is an array of User objects
foreach ($userList as (User)$user) {
   echo $user->getName();
}

I use Netbeans IDE v.6.5.1 and it works for me. although it marks the casting expression an error, and I clear after I wrote my code, but for the time of calling my methods, it will help me.

farzad
Sorry, that's a horrible way to do this. Zahymaka's hint and my sample in the comment achieve the same thing without causing errors.
Artem Russakovskii
+10  A: 

The best you can do is say,

foreach ($Objs as $Obj)
{
    /* @var $Obj Test */
    // You should be able to get hinting after the preceding line if you type $Obj->
}

I do that a lot in Zend Studio. Don't know about other editors, but it ought to work.

Zahymaka
This makes sense but it didn't work for PHPEd 5.2. The only thing I was able to come up with that worked is foreach ($Objs as /** @var Test */$Obj), which is horribly ugly. :(
Artem Russakovskii
This works in NetBeans 6.7 (I think it's bugged, since you get a ? for the type when you hit ctrl-space, but it **is** able autocomplete the object's members/methods).
therefromhere
Works a treat in NetBeans 6.8+. $Obj-> then ctrl-space brings up the expect list of properties and methods.
Jon Cram
+1  A: 

The problem is that @var can just denote a single type - Not contain a complex formula. If you had a syntax for "array of Foo", why stop there and not add a syntax for "array of array, that contains 2 Foo's and three Bar's"? I understand that a list of elements is perhaps more generic than that, but it's a slippery slope.

Personally, I have some times used @var Foo[] to signify "an array of Foo's", but it's not supported by IDE's.

troelskn
+3  A: 

In Web IDE (PHP edition) from JetBrains, you can use /** @var SomeObj[] */, e.g.:

/**
 * @return SomeObj[]
 */
function getSomeObjects() {...}
Nishi
ah, PhpStorm is so great :)
mgroves
I just downloaded and have been using phpstorm for the past week. Beats the heck out of Aptana (which is great for being free). This is exactly what I was looking for. Actually, it is the same way you'd do it for JavaScript, I should have guessed
Juan Mendes
+1  A: 

I've found something which is working, it can save lives !

private $userList = array();
$userList = User::fetchAll(); // now $userList is an array of User objects
foreach ($userList as $user) {
   $user instanceof User;
   echo $user->getName();
}
eupho
only problem is that introduces additional code to be executed, which is purely used by your IDE only. It's much better to define type hinting within the comments instead.
Ben Rowe
Wow this works great. You would end up with additional code but it seems to be harmless. I'm going to start doing: $x instanceof Y; // typehint
igor
A: 
<?php foreach($this->models as /** @var Model_Object_WheelModel */ $model): ?>
    <?php
    // Type hinting now works:
    $model->getImage();
    ?>
<?php endforeach; ?>
Scott Hovestadt
which IDEs support this?
philfreo