YII框架中根据经纬度查距离并用距离排序的方法

WPing丶

2022-12-17 17:32

public function actionRecGoodsList()
    {
        $latitude = \Yii::$app->request->get('latitude');
        $longitude = \Yii::$app->request->get('longitude');
        $page = \Yii::$app->request->get('page');
        $cat_id = \Yii::$app->request->get('cat_id');
        $sort = \Yii::$app->request->get('sort');
        $keyword = \Yii::$app->request->get('keyword');

        //查出最近的20家商家的id
        $form = Mch::find()->alias('m')
            ->where(['is_open'=>1, 'is_delete' => 0])
            ->select(['m.id', 'distance' => '(2 * 6378.137 * ASIN(SQRT(POW(SIN(PI() * (' . $longitude . ' - m.longitude) / 360),2) + COS(PI() * 39.916527 / 180) * COS(latitude * PI() / 180) * POW(SIN(PI() * (' . $latitude . ' - m.latitude) / 360),
            2))))'])
            ->orderBy('distance ASC')
            ->limit(20)
            ->asArray()
            ->all();
        $mch_ids = [];
        foreach($form as $v) {
            $mch_ids[] = $v['id'];
        }
        //查商品
        $query = Goods::find()->alias('g')
            ->leftJoin(['m' => Mch::tableName()], 'm.id=g.mch_id')
            ->where(['g.is_delete' => 0, 'g.status' => 1])
            ->andWhere(['g.mch_id' => $mch_ids])
            ->andWhere(['>', 'g.rec_end_time', time()])
            ->select(['g.*', 'distance' => '(2 * 6378.137 * ASIN(SQRT(POW(SIN(PI() * (' . $longitude . ' - m.longitude) / 360),2) + COS(PI() * 39.916527 / 180) * COS(latitude * PI() / 180) * POW(SIN(PI() * (' . $latitude . ' - m.latitude) / 360),
        2))))']);
        if($sort) {
            $query->orderBy('distance');
        }
        if($cat_id) {
            $query->andWhere(['m.mch_common_cat_id' => $cat_id]);
        }
        if($keyword) {
            $query->andWhere(['LIKE','g.name',$keyword]);
        }
        // $sql = $query->createCommand()->getRawSql();
        $count = $query->count();
        $pagination = new Pagination(['totalCount' => $count, 'pageSize' => 10, 'page' => $page - 1]);
        $list = $query->limit($pagination->limit)->offset($pagination->offset)->asArray()->all();
        foreach ($list as &$item) {
            $item['distance'] = bcmul($item['distance'], 1, 2) . 'km';
        }
        $cat_list = MchCommonCat::find()->where(['is_delete' => 0, 'store_id' => $this->store->id])->select('id,name')->asArray()->all();
        return new BaseApiResponse([
            'code' => 0,
            'msg' => "success",
            'list' => $list,
            'cat_list' => $cat_list,
            'page' => $page
        ]);
    }


0 条评论

评论:

发送
0.087590s