Я пытаюсь сделать PHP (5) объект, который может выполнить итерации через его свойства, создав SQL-запрос, базирующийся только на его общественных собственностях, не его частных.
Поскольку этот метод родительского объекта должен использоваться дочерними объектами, я не могу просто принять решение пропустить частные собственности по имени (я не буду знать то, что они находятся в дочерних объектах).
Существует ли простой способ обнаружить из объекта, какое из его свойств является частным?
Вот упрощенный пример того, что я имею до сих пор, но этот вывод включает значение $bar:
class testClass {
public $foo = 'foo';
public $fee = 'fee';
public $fum = 'fum';
private $bar = 'bar';
function makeString()
{
$string = "";
foreach($this as $field => $val) {
$string.= " property '".$field."' = '".$val."' <br/>";
}
return $string;
}
}
$test = new testClass();
echo $test->makeString();
Дает вывод:
property 'foo' = 'foo'
property 'fee' = 'fee'
property 'fum' = 'fum'
property 'bar' = 'bar'
Я хотел бы, чтобы это не включало 'панель'.
Если бы существует лучший способ выполнить итерации через просто общественные собственности объекта, который работал бы здесь также.
Вы можете использовать Reflection для проверки свойств класса. Чтобы получить только общедоступные и защищенные свойства, профилируйте подходящий фильтр для метода ReflectionClass :: getProperties
.
Вот быстрый пример использования этого метода makeString
.
public function makeString()
{
$string = "";
$reflection = new ReflectionObject($this);
$properties = $reflection->getProperties(ReflectionProperty::IS_PUBLIC);
foreach ($properties as $property) {
$name = $property->getName();
$value = $property->getValue($this);
$string .= sprintf(" property '%s' = '%s' <br/>", $name, $value);
}
return $string;
}
Вы можете использовать массив для хранения общедоступных свойств, добавить некоторый метод-оболочку и использовать массив для вставки данных в SQL.
Проверьте этот код на http://php.net/manual/reflectionclass.getproperties.php#93984
public function listProperties() {
$reflect = new ReflectionObject($this);
foreach ($reflect->getProperties(ReflectionProperty::IS_PUBLIC /* + ReflectionProperty::IS_PROTECTED*/) as $prop) {
print $prop->getName() . "\n";
}
}
Если вы приведете объект к массиву до итерации по нему, закрытые и защищенные члены будут иметь специальные префиксы:
class Test{
public $a = 1;
private $b = 1;
protected $c = 1;
}
$a = new Test();
var_dump((array) $a);
отображает это:
array(3) {
["a"]=>
int(1)
["Testb"]=>
int(1)
["*c"]=>
int(1)
}
Там также есть скрытые символы, которые не отображаются. Но вы можете написать код для их обнаружения. Например, регулярное выражение / \ 0 \ * \ 0 (. *) $ /
будет соответствовать защищенным ключам, а / \ 0. * \ 0 (. *) $ /
будет соответствовать частным. В обоих случаях первая группа захвата соответствует имени члена.