2015-05-11 3 views
1

На модели пользователя (таблица 4) записи, когда я:Laravel Коллекции подсчета результата

$coll = User::all(); 
echo $coll->count(); 

я получаю количество найденных записей (4).

Но когда я делаю:

$coll = User::find(2); 
echo $coll->count(); 

Я не получаю 1 (Как я ожидал), но количество атрибутов в результирующей коллекции (23 в данном случае).

Как проверить, найдено ли более одной записи?


UPDATE:

ОК, спасибо вам всем теперь я вижу разницу в результате между сбором и модели.

Но моя реальная проблема в том, что я должен определить, есть ли у меня модель или коллекция. В зависимости от этого результата я выполняю некоторые изменения в содержимом полей в элементах (с помощью map()) или модели. Как определить, является ли результат моделью или коллекцией?

if(count($coll) > 1) 

Работы, но это правильный подход?

+0

Я не верю в ':: найти()' возвращает коллекцию, на самом деле. –

+1

@ Don'tPanic На самом деле это может быть, если вы передадите ему массив id. Но в этом случае, если найдена запись с идентификатором id = 2, она вернет Eloquent Model. – Bogdan

+0

@Bogdan, хорошая точка. Думаю, я должен был сказать более конкретно ':: find (2)' не возвращает коллекцию. –

ответ

2

Вот что происходит с кодом, у вас там:

1. При вызове User::all() вы получите Illuminate\Database\Eloquent\Collection, на котором вы можете вызвать count, который подсчитывает элементы в коллекция как таковая:

public function count() 
{ 
    return count($this->items); 
} 

Это вернет количество предметов в коллекции, как вы правильно ожидали.

2. При вызове User::find(2) однако, Красноречивым Query Builder не будет возвращать Collection, потому что он будет проверять, чтобы увидеть, сколько результатов есть, и так как вы прошли один ID вы получите самое большее один результат, так что вместо этого он вернет Eloquent Model. Модель не имеет метод count(), поэтому при попытке вызова $coll->count(); он будет идти в волшебный __call метод, что класс реализован, который выглядит следующим образом:

public function __call($method, $parameters) 
{ 
    if (in_array($method, array('increment', 'decrement'))) 
    { 
     return call_user_func_array(array($this, $method), $parameters); 
    } 

    $query = $this->newQuery(); 

    return call_user_func_array(array($query, $method), $parameters); 
} 

Как вы можете видеть, что метод пытается увидеть если он должен вызвать пару жестко запрограммированных методов (increment и decrement), которые, конечно, не совпадают в этом случае, потому что $method = 'count', поэтому он продолжает создавать новый запрос, на который он вызовет метод count.

Суть в том, что и первый, и второй образцы кода в конечном итоге делают то же самое: подсчитывает все записи в таблице users.

И с тех пор, как я указывал наш выше, один идентификатор не может соответствовать более одной строки (поскольку идентификаторы уникальны), то ответ на ваш вопрос в том, что нет никакой необходимости или способа подсчета результатов find(2), так это может быть только 0 (если возвращается null) или 1 (если возвращается Model).


UPDATE

Прежде всего, в будущем вы можете использовать PHP get_class, чтобы определить имя класса объекта или get_parent_class для определения класса она расширяется. В вашем случае вторая функция get_parent_class может быть полезна для определения класса модели, так как класс User расширяет абстрактный класс модели Laravel.

Поэтому, если у вас есть модель get_class($coll) сообщит User, но get_parent_class($coll) сообщит \Illuminate\Database\Eloquent\Model.

Теперь, чтобы проверить, если результатом является коллекция или модель вы можете использовать instanceof:

instanceof используется для определения того, является ли переменная PHP является экземпляр объекта определенного класса

Ваши чеки должны выглядеть примерно так:

// Check if it's a Collection 
if ($coll instanceof \Illuminate\Support\Collection) 

// Check if it's a Model 
if ($coll instanceof \Illuminate\Database\Eloquent\Model) 

Возможно, вы также захотите проверить, равен ли результат null, так как find вернется null, если запись не найдена с данным ID:

if (is_null($coll)) 
+0

Конечно! Я не делал разницы между коллекцией и моделью. Спасибо, что освободил это для меня! Пожалуйста, ознакомьтесь с обновленным вопросом для реального решения, которое я ищу. – Klaaz

+0

@Klaaz Я обновил ответ с решением вашего обновленного вопроса. – Bogdan

+0

Отлично! Это делает вещи очень ясными, спасибо за объяснение :-) – Klaaz

Смежные вопросы