Haversine запрос в Oracle - PullRequest
       9

Haversine запрос в Oracle

2 голосов
/ 14 сентября 2011

В настоящее время мне нужно пройти через мои запросы и перенести их на использование Oracle вместо SQLSERVER, и я немного застрял с этим запросом, который я использую с здесь

SELECT TOP 1 * FROM ( SELECT o.outcode AS lead_postcode, v.location, 
v.location_name, v.outcode AS venue_postcode, 6371.0E * 
( 2.0E *asin(case when 1.0E < (sqrt(square(sin(((RADIANS(CAST(o.lat AS FLOAT)))-
(RADIANS(CAST(v.lat AS FLOAT))))/2.0E)) + (cos(RADIANS(CAST(v.lat AS FLOAT))) 
* cos(RADIANS(CAST(o.lat AS FLOAT))) * square(sin(((RADIANS(CAST(o.lng AS FLOAT)))-
(RADIANS(CAST(v.lng AS FLOAT))))/2.0E))))) then 1.0E else 
(sqrt(square(sin(((RADIANS(CAST(o.lat AS FLOAT)))-(RADIANS(CAST(v.lat AS FLOAT))))
/2.0E)) + (cos(RADIANS(CAST(v.lat AS FLOAT))) * cos(RADIANS(CAST(o.lat AS FLOAT)))
* square(sin(((RADIANS(CAST(o.lng AS FLOAT)))-(RADIANS(CAST(v.lng AS FLOAT))))
/2.0E))))) end )) AS distance FROM venue_postcodes v, uk_postcodes o 
WHERE o.outcode = @nrpostcode ) i WHERE distance<100 ORDER BY distance

Теперь я знаю, что это ужасный запрос, но у Oracle, похоже, много проблем с ним.

Во-первых, ему не нравятся E в 6371E и все последующие E

.

Во-вторых, ей не нравится функция square, поэтому я решил использовать функцию power, но это все равно дало мне ошибки.

В-третьих, ей не нравится функция radians

В-четвертых, ему не нравится часть TOP 1, поэтому я изменил ее, чтобы использовать ROWNUM в предложении WHERE

Я совершенно потерян, что делать здесь.

Есть какие-нибудь идеи относительно того, что я могу сделать, чтобы это работало?

Заранее спасибо

Ответы [ 2 ]

5 голосов
/ 14 сентября 2011

Я бы порекомендовал вам использовать немного другой подход.

Посетите этот сайт: http://psoug.org/reference/functions.html

Найдите часть, относящуюся к "расстоянию расчета"

0 голосов
/ 14 сентября 2011

Я знаю, как это сделать в SQL Server, который должен быть достаточно простым для переноса на Oracle:

Вот UDF, который я создал, чтобы получить приблизительный полет ворон расстояние между двумя почтовыми индексами по формуле Хаверсайна:

ALTER FUNCTION [dbo].[fn_GetZipDistanceMiles](
    @ZipFrom VARCHAR(20),
    @ZipTo VARCHAR(20)
)
RETURNS FLOAT 
AS  
BEGIN 

    DECLARE @Latitude1 FLOAT
    DECLARE @Longitude1 FLOAT
    DECLARE @Latitude2 FLOAT
    DECLARE @Longitude2 FLOAT

    SELECT  @Latitude1 = Latitude,
            @Longitude1 = Longitude
    FROM    ZipCode
    WHERE   ZipCode = @ZipFrom


    SELECT  @Latitude2 = Latitude,
            @Longitude2 = Longitude
    FROM    ZipCode
    WHERE   ZipCode = @ZipTo

    -- CONSTANTS
    DECLARE @EarthRadiusInMiles FLOAT
    SET @EarthRadiusInMiles = 3963.1

    -- RADIANS conversion
    DECLARE @Lat1Radians FLOAT
    DECLARE @Long1Radians FLOAT
    DECLARE @Lat2Radians FLOAT
    DECLARE @Long2Radians FLOAT

    SET @Lat1Radians = @Latitude1 * PI() / 180
    SET @Long1Radians = @Longitude1 * PI() / 180
    SET @Lat2Radians = @Latitude2 * PI() / 180
    SET @Long2Radians = @Longitude2 * PI() / 180

    RETURN ACOS(COS(@Lat1Radians) * COS(@Long1Radians) * COS(@Lat2Radians) * COS(@Long2Radians) + COS(@Lat1Radians) * SIN(@Long1Radians) * COS(@Lat2Radians) * SIN(@Long2Radians) + SIN(@Lat1Radians) * SIN(@Lat2Radians)) * @EarthRadiusInMiles

END
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...