[php] Laravel-웅변 또는 유창한 임의 행

Laravel 프레임 워크에서 Eloquent 또는 Fluent를 사용하여 임의의 행을 선택하려면 어떻게해야합니까?

SQL을 사용하면 RAND ()로 주문할 수 있다는 것을 알고 있습니다. 그러나 초기 쿼리 이전의 레코드 수를 계산 하지 않고 임의의 행을 얻고 싶습니다 .

어떤 아이디어?



답변

라 라벨> = 5.2 :

User::all()->random();
User::all()->random(10); // The amount of items you wish to receive

또는

User::inRandomOrder()->get();

또는 특정 수의 레코드를 얻기 위해

//5 indicates the number of records
User::inRandomOrder()->limit(5)->get();

라 라벨 4.2.7-5.1 :

User::orderByRaw("RAND()")->get();

라 라벨 4.0-4.2.6 :

User::orderBy(DB::raw('RAND()'))->get();

라 라벨 3 :

User::order_by(DB::raw('RAND()'))->get();

이 기사 는 MySQL 무작위 행에서 확인하십시오 . Laravel 5.2는이를 지원합니다. 이전 버전의 경우 RAW 쿼리 를 사용하는 것보다 더 나은 솔루션은 없습니다 .

편집 1 : Double Gras가 언급했듯이 orderBy ()는 변경 이후 ASC 또는 DESC 이외의 다른 것을 허용하지 않습니다 . 이에 따라 답변을 업데이트했습니다.

편집 2 : Laravel 5.2는 마침내 이것을 위해 래퍼 기능 을 구현 합니다 . inRandomOrder () 라고 합니다.


답변

이것은 잘 작동합니다.

$model=Model::all()->random(1)->first();

임의 함수에서 인수를 변경하여 둘 이상의 레코드를 얻을 수도 있습니다.

참고 : 대량의 데이터가 있으면 모든 행을 먼저 가져온 다음 임의의 값을 반환하므로 권장하지 않습니다.


답변

tl; dr : 요즘은 라 라벨에 구현되어 있습니다. 아래의 “편집 3″을보십시오.


안타깝게도 오늘 현재 ->orderBy(DB::raw('RAND()'))제안 된 솔루션에 대한 몇 가지주의 사항이 있습니다.

  • DB에 구애받지 않습니다. 예 : SQLite 및 PostgreSQL 사용RANDOM()
  • 더 나쁜 것은 이 변경 이후이 솔루션은 더 이상 적용되지 않습니다 .

    $direction = strtolower($direction) == 'asc' ? 'asc' : 'desc';

편집 : 이제 orderByRaw () 메소드를 사용할 수 있습니다 :->orderByRaw('RAND()') . 그러나 이것은 여전히 ​​DB에 구애받지 않습니다.

FWIW, CodeIgniter는 특별한 구현 RANDOM 정렬 방향을 쿼리를 작성할 때 올바른 문법으로 대체됩니다. 또한 구현하기가 상당히 쉬운 것 같습니다. 라 라벨 개선 후보가있는 것 같습니다 🙂

업데이트 : 여기 GitHub 의 문제 와 보류중인 pull 요청이 있습니다.

편집 2 : 체이스를 잘라 봅시다. Laravel 5.1.18부터 쿼리 작성기에 매크로를 추가 할 수 있습니다.

use Illuminate\Database\Query\Builder;

Builder::macro('orderByRandom', function () {

    $randomFunctions = [
        'mysql'  => 'RAND()',
        'pgsql'  => 'RANDOM()',
        'sqlite' => 'RANDOM()',
        'sqlsrv' => 'NEWID()',
    ];

    $driver = $this->getConnection()->getDriverName();

    return $this->orderByRaw($randomFunctions[$driver]);
});

용법:

User::where('active', 1)->orderByRandom()->limit(10)->get();

DB::table('users')->where('active', 1)->orderByRandom()->limit(10)->get();

편집 3 : 마지막으로! Laravel 5.2.33 ( changelog , PR # 13642 )부터 기본 메소드를 사용할 수 있습니다 inRandomOrder().

User::where('active', 1)->inRandomOrder()->limit(10)->get();

DB::table('users')->where('active', 1)->inRandomOrder()->limit(10)->get();


답변

에서는 Laravel 4 및 5order_by로 대체orderBy

따라서 다음과 같아야합니다.

User::orderBy(DB::raw('RAND()'))->get();


답변

당신은 사용할 수 있습니다 :

ModelName::inRandomOrder()->first();


답변

라 라벨 5.2의 경우> =

Eloquent 방법을 사용하십시오 :

inRandomOrder()

inRandomOrder 메소드는 쿼리 결과를 무작위로 정렬하는 데 사용될 수 있습니다. 예를 들어,이 방법을 사용하여 임의의 사용자를 가져올 수 있습니다.

$randomUser = DB::table('users')
            ->inRandomOrder()
            ->first();

문서에서 : https://laravel.com/docs/5.2/queries#ordering-grouping-limit-and-offset


답변

다음과 같이 유창하고 웅변적인 order_by 메소드를 사용할 수도 있습니다.

Posts::where_status(1)->order_by(DB::raw(''),DB::raw('RAND()')); 

이것은 약간 이상한 사용법이지만 작동합니다.

편집 : @ Alex가 말했듯 이이 사용법은 더 깨끗하고 작동합니다.

Posts::where_status(1)->order_by(DB::raw('RAND()'));