【问题标题】:I have a value 'marks' in a pivot table, how to find student rank based on 'marks' value using query builder?我在数据透视表中有一个值“标记”,如何使用查询生成器根据“标记”值查找学生排名?
【发布时间】:2019-04-23 03:37:38
【问题描述】:

我有两个模型考试和学生,在每个学生尝试考试后,她/他获得的分数存储在数据透视表exam_user 中。我需要根据获得的分数对学生进行排名。

现在我正在为此使用一个非常低效的解决方案,它涉及一个 for 循环。下面是实现

            $rank=0;
            $attempts = DB::table('exam_user')
                    ->where('exam_id',$exam->id)
                    ->orderBy('marks','desc')
                    ->get();
            foreach ($attempts as $attempt) {
                $rank++;
                if($attempt->user_id==Auth::id())
                    break;
            }

有什么方法可以在不使用 for 循环的情况下确定排名,只需使用 laravel 中的查询生成器。我想我在这里遗漏了一些 SQL 基础知识。

【问题讨论】:

    标签: sql laravel laravel-5 php-7 laravel-query-builder


    【解决方案1】:

    排名只是比你的价值更大的人数+1。

    因此你可以这样做:

    $userMarks = DB::table('exam_user')
        ->select('marks')
        ->where('exam_id', $exam->id)
        ->where('user_id', '=', Auth::id())
        ->firstOrFail()
        ->marks;
    
    $rank = DB::table('exam_user')
        ->where('exam_id', $exam->id)
        ->where('marks', '>', $userMarks)
        ->count() + 1;
    

    您也可以将其放入一个查询中:

    $userId = Auth::id();
    $rank = DB::table('exam_user')
                ->where('exam_id', $exam->id)
                ->whereRaw(
                    "marks > (select eu2.marks from exam_user eu2 where eu2.exam_id = {$exam->id} and eu2.user_id = {$userId}) limit 1"
                )
                ->count() + 1;
    

    您也可以考虑将数据透视表exam_user 作为一个实际模型,并将其命名为Marks,因为它包含您想要查询的重要数据。

    然后您可以将以下内容添加到 Exam 模型中:

    Class Exam {
        // ...
        public function marks() {
            $this->hasMany(Marks::class);
        }    
        // ...
    }
    

    这意味着您可以执行以下操作:

    $userId = Auth::id();
    $rank = $exam->marks()
                ->whereRaw(
                    "marks > (select marks from exam_user where exam_id = {$exam->id} and user_id = {$userId}) limit 1"
                )
                ->count() + 1;
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-10-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-08-13
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多