在PHP3中,如何在Group by之前执行Order by?

在PHP3中,如何在Group by之前执行Order by?,php,cakephp,cakephp-3.0,greatest-n-per-group,Php,Cakephp,Cakephp 3.0,Greatest N Per Group,我正在获取用户给出的所有答案。但我只需要用户的最新回答/响应(使用响应id)。我正在运行下面的查询 $users_all_answers=$this->SurveySectionAnswers->find('all') ->where(['survey_response_id IN'=>$response_ids]) ->order(['survey_

我正在获取用户给出的所有答案。但我只需要用户的最新回答/响应(使用响应id)。我正在运行下面的查询

$users_all_answers=$this->SurveySectionAnswers->find('all')
                             ->where(['survey_response_id IN'=>$response_ids])
                             ->order(['survey_response_id'=>'desc'])
                             ->group(['survey_question_id'])
                             ->hydrate(false)
                             ->toArray();
但我得到的是用户的答案,而不是最新的响应,因为在Order by之前在Group by上执行。那么,有什么解决方案可以让我通过用户的最新响应获得所有答案呢

得到这样的数组

[0] => Array
    (
        [id] => 527
        [survey_response_id] => 74
        [survey_question_id] => 84
        [survey_answer] => 
        [survey_score] => 0
        [survey_section_id] => 50
        [survey_answer_id] => 138
        [completed] => 1
    )

[1] => Array
    (
        [id] => 528
        [survey_response_id] => 74
        [survey_question_id] => 85
        [survey_answer] => 
        [survey_score] => 0
        [survey_section_id] => 48
        [survey_answer_id] => 142
        [completed] => 1
    )
但是我想要像

[0] => Array
    (
        [id] => 527
        [survey_response_id] => 76
        [survey_question_id] => 84
        [survey_answer] => 
        [survey_score] => 0
        [survey_section_id] => 50
        [survey_answer_id] => 138
        [completed] => 1
    )

[1] => Array
    (
        [id] => 528
        [survey_response_id] => 76
        [survey_question_id] => 85
        [survey_answer] => 
        [survey_score] => 0
        [survey_section_id] => 48
        [survey_answer_id] => 142
        [completed] => 1
    )

在MySQL中,GROUPBY在ORDERBY之前执行。GROUP BY将始终选择结果集中的第一行,因此在执行该分组之前,它不受ORDER BY的影响

在MySQL中,有一种方法可以实现您所描述的功能。我更喜欢使用这样一种方法,即以确保最新的行是实际选中的行的方式将表连接到自身

在CakePHP中,它看起来像:

$users_all_answers = $this->SurveySectionAnswers->find()
    ->join([
        'SurveySectionAnswers_2' => [
            'table' => 'survey_section_answers',
            'type' => 'LEFT',
            'conditions' => [
                'SurveySectionAnswers_2.survey_question_id' => new \Cake\Database\Expression\IdentifierExpression('SurveySectionAnswers_2.survey_question_id'),
                'SurveySectionAnswers.id <' => 'SurveySectionAnswers_2.id'
            ]
        ]
    ])
    ->where([
        'SurveySectionAnswers.survey_response_id IN' => $response_ids,
        'SurveySectionAnswers_2 IS ' => null
    ])
    ->hydrate(false)
    ->toArray();
$users\u all\u answers=$this->SurveySectionAnswers->find()
->加入([
‘SurveySectionAnswers_2’=>[
“表”=>“调查部分答案”,
'类型'=>'左',
“条件”=>[
“SurveySectionAnswers\u 2.survey\u question\u id”=>new\Cake\Database\Expression\IdentifierExpression(“SurveySectionAnswers\u 2.survey\u question\u id”),

'SurveySectionAnswers.id另一种选择是使用或groupBy

这将对性能产生影响,但在代码中可能更清晰

获取答案列表。这将返回一个带有集合接口的对象

$users_all_answers = $this->SurveySectionAnswers->find('all')
                         ->where(['survey_response_id IN'=>$response_ids])
                         ->order(['survey_response_id'=>'asc'])
                         ->hydrate(false);
需要注意的是,您必须以相反的顺序对查询进行排序,因为indexBy和groupBy将返回组中的最后一项

在上面的查询中,我将顺序
survey\u response\u id
desc
更改为
asc
,以完成此操作

然后,您可以在有序查询中调用groupBy或indexBy。这将立即调用您的查询

$users_grouped_by_id = $users_all_answers->groupBy('survey_question_id')
或者,如果每个组只需要一个结果

$users_indexed_by_id = $users_all_answers->indexBy('survey_question_id')

groupBy
indexBy
是集合接口函数。不要与
group
相混淆,后者是查询生成器函数。每个查询都是集合,但集合不是查询。

mysql
中不能这样做,您可以使用max/min函数并将其与group-by函数混合,或者使用se子查询以获取最新答案,然后对其排序,或者在获取数据后使用php it self对其排序;