4

特定の郵便番号の特定の範囲内の郵便番号のリストを判別するためのphp関数を作成することができました。ただし、次のタスクはもう少し複雑です。

テーブルに次の列があるとします。

id,
username
info
latitude
longitude
range

各レコードには、一意の行ID、いくつかの情報、緯度、経度、およびこのエントリを検索する座標からの最大範囲があります。したがって、座標が-20、50で範囲が15のエントリを作成する場合、つまり、座標-20、50から15マイル以内のユーザーだけが自分のエントリを表示できるようにする必要があります。検索を実行しているユーザーの緯度と経度を把握するのは簡単なことです。

ユーザーがデータベースを検索しているときは、すべてのレコードを取得して、ユーザーの緯度/経度からの範囲の値内の緯度と経度の座標を取得する必要があります。

したがって、これを説明するために距離式を使用するコードの非機能的な例は、次のようになります。

$userLat=検索を実行しているユーザーの緯度

$userLong=検索を実行しているユーザーの経度

SELECT info FROM table 
WHERE sqrt(($userLat - lat)^2 - ($userLong - long)^2) <= range 
ORDER BY username ASC

それは理想的ですが、コーディングの観点からは有効ではありません。1つのクエリでPHPとMySQLを使用して上記の比較を実行する方法はありますか?これには、特定の行の複数の列値を使用して操作を実行できることが含まれます。


更新と解決策

この問題に対処し、この質問が望んでいたことを実行するための非常にコンパクトな機能を備えた別の質問エントリを作成しました。coderprosによって提供された関数は、そのインスピレーションとして役立ちました(彼の関数は、特定の状況ではるかに優れた処理を行います)。ただし、入力を高度に制御して関数を使用しているため、別の関数を作成しました。以下のリンクで見つけることができます:

緯度経度構文用のMySQLユーザー定義関数

4

1 に答える 1

6

私が書いたこの気の利いたlilmySQL関数は、間違いなくあなたのためにトリックを行うはずです。

BEGIN
   DECLARE x decimal(18,15);
   DECLARE EarthRadius decimal(7,3);
   DECLARE distInSelectedUnit decimal(18, 10);

   IF originLatitude = relativeLatitude AND originLongitude = relativeLongitude THEN
          RETURN 0; -- same lat/lon points, 0 distance
   END IF;

   -- default unit of measurement will be miles
   IF measure != 'Miles' AND measure != 'Kilometers' THEN
          SET measure = 'Miles';
   END IF;

   -- lat and lon values must be within -180 and 180.
   IF originLatitude < -180 OR relativeLatitude < -180 OR originLongitude < -180 OR relativeLongitude < -180 THEN
          RETURN 0;
   END IF;

   IF originLatitude > 180 OR relativeLatitude > 180 OR originLongitude > 180 OR relativeLongitude > 180 THEN
         RETURN 0;
   END IF;

   SET x = 0.0;

   -- convert from degrees to radians
   SET originLatitude = originLatitude * PI() / 180.0,
       originLongitude = originLongitude * PI() / 180.0,
       relativeLatitude = relativeLatitude * PI() / 180.0,
       relativeLongitude = relativeLongitude * PI() / 180.0;

   -- distance formula, accurate to within 30 feet
   SET x = Sin(originLatitude) * Sin(relativeLatitude) + Cos(originLatitude) * Cos(relativeLatitude) * Cos(relativeLongitude - originLongitude);

   IF 1 = x THEN
          SET distInSelectedUnit = 0; -- same lat/long points
          -- not enough precision in MySQL to detect this earlier in the function
   END IF;

   SET EarthRadius = 3963.189;
   SET distInSelectedUnit = EarthRadius * (-1 * Atan(x / Sqrt(1 - x * x)) + PI() / 2);

   -- convert the result to kilometers if desired
   IF measure = 'Kilometers' THEN
          SET distInSelectedUnit = MilesToKilometers(distInSelectedUnit);
   END IF;

   RETURN distInSelectedUnit;
END

これは、originLatitude、originLongitude、relativeLatitude、relativeLongitudeを取り、パラメーターとして測定します。メジャーは単純にMilesまたはKilometers

お役に立てば幸いです。

于 2010-08-22T23:35:21.737 に答える