Таким образом, в PHPDoc можно указывать @var
выше объявление переменной-члена, чтобы намекнуть на его тип. Тогда IDE, например. PHPEd будет знать, с каким типом объекта он работает, и сможет обеспечить понимание кода для этой переменной.
<?php
class Test
{
/** @var SomeObj */
private $someObjInstance;
}
?>
Это прекрасно работает до тех пор, пока мне не понадобится сделать то же самое с массивом объектов, чтобы иметь возможность получить правильный совет, когда я буду повторять эти объекты позже.
Итак, есть ли способ объявить тег PHPDoc, чтобы указать, что переменная-член является массивом SomeObj
s? Например, @var
массива недостаточно, и @var array(SomeObj)
он кажется недействительным.
Ответы:
Использование:
при вводе строковых переменных и
для свойств класса.
Предыдущий ответ от '09, когда PHPDoc (и IDE, такие как Zend Studio и Netbeans) не имели такой возможности:
Лучшее, что вы можете сделать, это сказать,
Я часто этим занимаюсь в Zend Studio. Не знаю о других редакторах, но это должно работать.
источник
/** @var $Obj Test */
не работает.@var Object[] $objects
говорит, что «$ objects» - это массив экземпляров Object.)/** @var TYPE $variable_name */
правильный синтаксис; не меняйте порядок типа и имени переменной (как предложено ранее в комментариях), так как это не будет работать во всех случаях.В IDE PhpStorm от JetBrains вы можете использовать
/** @var SomeObj[] */
, например:phpdoc рекомендует этот метод:
источник
foreach(getSomeObjects() as $obj)
не работает, но для$objs = getSomeObjects(); foreach($objs as $obj)
@var Obj[string]
для ассоциативных массивов.Netbeans намеки:
Вы получаете завершение кода для
$users[0]->
и для$this->
массива пользовательских классов.Вы также можете увидеть тип массива в списке членов класса, когда вы делаете завершение
$this->...
источник
array_pop()
по какой-то причине это не работает после использования или подобных функций. Кажется, что Netbeans не понимает, что эти функции возвращают единственный элемент входного массива.Чтобы указать переменную, это массив объектов:
Это работает в Netbeans 7.2 (я использую его)
Работает также с:
Поэтому использование декларации внутри
foreach
не обязательно.источник
/* @var $Obj Test */
аннотации каждый раз./**
2. Правильный формат@var <data-type> <variable-name>
PSR-5: PHPDoc предлагает форму нотации в стиле Generics.
Синтаксис
Значения в коллекции МОГУТ быть даже другим массивом и даже другой коллекцией.
Примеры
Примечание. Если вы ожидаете, что в среде IDE будет помогать код, тогда возникает другой вопрос, поддерживает ли IDE нотацию коллекций в стиле PHPDoc Generic.
Из моего ответа на этот вопрос .
источник
Я предпочитаю читать и писать чистый код - как изложено в «Чистом коде» Роберта С. Мартина. Следуя его кредо, вы не должны требовать, чтобы разработчик (как пользователь вашего API) знал (внутреннюю) структуру вашего массива.
Пользователь API может спросить: это массив только с одним измерением? Распространены ли объекты на всех уровнях многомерного массива? Сколько вложенных циклов (foreach и т. Д.) Мне нужно для доступа ко всем объектам? Какие типы объектов «хранятся» в этом массиве?
Как вы обрисовали в общих чертах, вы хотите использовать этот массив (который содержит объекты) как одномерный массив.
Как указано Ниши, вы можете использовать:
для этого.
Но опять же: имейте в виду - это не стандартное обозначение докблока. Это обозначение было введено некоторыми производителями IDE.
Хорошо, хорошо, как разработчик, вы знаете, что «[]» привязан к массиву в PHP. Но что означает «что-то []» в обычном контексте PHP? «[]» означает: создать новый элемент внутри «чего-то». Новый элемент может быть всем. Но то, что вы хотите выразить, это: массив объектов с одинаковым типом и точным типом. Как видите, производитель IDE вводит новый контекст. Новый контекст, который вы должны были изучить. Новый контекст, которому должны были научиться другие PHP-разработчики (чтобы понять ваши докблоки). Плохой стиль (!).
Поскольку у вашего массива есть одно измерение, вы можете назвать этот «массив объектов» списком. Имейте в виду, что «список» имеет особое значение в других языках программирования. Например, было бы лучше назвать это «коллекцией».
Помните: вы используете язык программирования, который дает вам все возможности ООП. Используйте класс вместо массива и сделайте свой класс проходимым как массив. Например:
Или, если вы хотите хранить внутренние объекты на разных уровнях в многомерной структуре массива / объекта:
Это решение заменяет ваш массив объектом типа "orderCollection", но пока не включает завершение кода в вашей IDE. Ладно. Следующий шаг:
Реализуйте методы, которые представлены интерфейсом с помощью docblocks - в частности:
Не забудьте использовать тип подсказки для:
Это решение перестает вводить много:
по всем вашим кодовым файлам (например, внутри циклов), как подтвердила Захимака своим ответом. Ваш пользователь API не обязан вводить эти docblocks для завершения кода. Наличие @return только в одном месте уменьшает избыточность (@var) настолько, насколько это возможно. Прибавьте «docBlocks with @var», чтобы ваш код стал хуже читаемым.
Наконец, вы сделали. Выглядит трудно достичь? Похоже, взять кувалду, чтобы сломать орех? Не совсем, так как вы знакомы с этими интерфейсами и с чистым кодом. Помните: ваш исходный код написан один раз / прочитал много.
Если завершение кода в вашей среде IDE не работает с этим подходом, переключитесь на лучший (например, IntelliJ IDEA, PhpStorm, Netbeans) или отправьте запрос функции на средство отслеживания проблем вашего производителя IDE.
Спасибо Кристиану Вейссу (из Германии) за то, что он мой тренер и научил меня таким замечательным вещам. PS: Встретимся со мной на XING.
источник
SomeObj[]
что знаете, что это двумерный массивSomeObj
экземпляров, а затем вы знаете, что с ним делать. Я не думаю, что это не следует кредо "чистого кода".@return <className>
forcurrent()
и всех парней. PhpStorm поддерживает, поэтому он мне очень помог. Спасибо друг!использование
array[type]
в Zend Studio.В Zend Studio,
array[MyClass]
илиarray[int]
или дажеarray[array[MyClass]]
отлично работают.источник
В NetBeans 7.0 (может быть и ниже) вы можете объявить возвращаемый тип «массив с текстовыми объектами» так же, как
@return Text
будет работать подсказка кода:Изменить: обновил пример с предложением @Bob Fanger
и просто используйте это:
Он не идеален, но лучше просто оставить его «смешанным», что не приносит никакой пользы.
CONS - вы можете использовать массив как текстовый объект, который будет выдавать ошибки.
источник
Как упомянула DanielaWaranie в своем ответе, есть способ указать тип $ item, когда вы выполняете итерации по $ items в $ collectionObject: Add
@return MyEntitiesClassName
tocurrent()
and rest ofIterator
иArrayAccess
методы -methods, которые возвращают значения.Boom! Нет необходимости в
/** @var SomeObj[] $collectionObj */
overforeach
и работает правильно с объектом коллекции, нет необходимости возвращать коллекцию с помощью специального метода, описанного как@return SomeObj[]
.Я подозреваю, что не все IDE поддерживают его, но он прекрасно работает в PhpStorm, что делает меня счастливее.
Пример:
Что полезного я собирался добавить, разместив этот ответ
В моем случае
current()
и остальныеinterface
-методы реализованы вAbstract
классе -collection, и я не знаю, какие сущности будут в конечном итоге храниться в коллекции.Итак, вот хитрость: не указывайте возвращаемый тип в абстрактном классе, вместо этого используйте описание PhpDoc
@method
в описании конкретного класса коллекции.Пример:
Теперь использование классов:
Еще раз: я подозреваю, что не все IDE поддерживают это, но PhpStorm поддерживает. Попробуйте свои, оставьте в комментариях результаты!
источник
Я знаю, что опаздываю на вечеринку, но недавно я работал над этой проблемой. Я надеюсь, что кто-то видит это, потому что принятый ответ, хотя и правильный, не самый лучший способ сделать это. По крайней мере, не в PHPStorm, я не тестировал NetBeans.
Лучший способ заключается в расширении класса ArrayIterator, а не в использовании собственных типов массивов. Это позволяет вам вводить подсказки на уровне класса, а не на уровне экземпляра, что означает, что вам нужно только один раз PHPDoc, а не весь код (который не только грязный и нарушает DRY, но также может быть проблематичным, когда речь идет о рефакторинг - у PHPStorm есть привычка пропускать PHPDoc при рефакторинге)
Смотрите код ниже:
Ключевым моментом здесь является PHPDoc,
@method MyObj current()
переопределяющий возвращаемый тип, унаследованный от ArrayIterator (который естьmixed
). Включение этого PHPDoc означает, что когда мы перебираем свойства класса, используяforeach($this as $myObj)
, мы получаем завершение кода при обращении к переменной$myObj->...
Для меня это самый лучший способ достичь этого (по крайней мере, до тех пор, пока PHP не введет Typed Arrays, если они вообще когда-либо это сделают), поскольку мы объявляем тип итератора в итерируемом классе, а не в экземплярах класса, разбросанных по всему коду.
Я не показал здесь полное решение для расширения ArrayIterator, поэтому, если вы используете эту технику, вы также можете:
offsetGet($index)
иnext()
is_a($object, MyObj::class)
из конструктора в приватный методoffsetSet($index, $newval)
иappend($value)
источник
Проблема в том, что
@var
можно просто обозначить один тип - не содержать сложной формулы. Если у вас был синтаксис «array of Foo», зачем останавливаться на достигнутом и не добавлять синтаксис для «array of array, который содержит 2 Foo и три Bar»? Я понимаю, что список элементов, возможно, более общий, но это скользкий путь.Лично я иногда использовал
@var Foo[]
для обозначения «массива Foo», но он не поддерживается IDE.источник
/* @var $foo Foo[] */
. Просто написал ответ ниже об этом. Это также может быть использовано внутриforeach(){}
цикловисточник
Я нашел то, что работает, это может спасти жизни!
источник