1

原貼:Changing integer to floating point and adding decimal pointSQL使用Long/Latitude和Converting Int計算距離。爲十進制

所以這裏的背景故事:我與接收GPS從車輛座標數據庫工作,我需要弄清楚基礎上的經度和緯度值這些車輛的行駛里程。但是,在數據庫中,「經度/緯度」兩列均爲「Int/Not null」,並且沒有小數位。因此,他們是這樣的:

Latitude Longitude 
36158500 115949833 
36340000 115914667 
36153488 115944875 

,我需要它看起來像這樣:

Latitude Longitude 
36.158500 115.949833 
36.340000 115.914667 
36.153488 115.944875 

與蒂姆萊納的幫助下,我們找到了如何讓小數點,但我不能使用我已經創建了公式來計算里程數。我必須能夠根據radio_name搜索long/lat值,以便我可以單獨查看每輛車的里程數,這就是爲什麼我創建了一個名爲CTE和CTE2的臨時表。但是,如果我調用臨時表,代碼將不起作用,因爲它表示它是無效的對象。現在,如果我在下面的最後一條語句中插入「AVL」(原始表格的名稱)與使用CTE2,則代碼工作正常。但是,里程數不是使用新的經緯度值計算的。

所以就像一個概括:列是緯度,經度。我們需要將這些列轉換爲在緯度2個字符後和經度3個字符後放置小數點。然後我們需要一個名爲Miles的列,它可以計算出給定的緯度和經度值之間的里程數。

任何提示,幫助,指針等,都非常感謝!謝謝!

USE [system] 
GO 
With CTE as 
(SELECT * FROM AVL 
WHERE (DATE_TIME between '01/30/2013 00:00:00' AND 
'01/30/2013 23:59:59') AND radio_name = 'MAS7'), 
CTE2 as 
(select *,row_number() over(partition by Vehicle_ID order by Date_Time) as RN 
FROM CTE) 

SELECT *, sqrt((69.1*(previous.Latitude - next.Latitude))* 
    (69.1*(previous.Latitude-next.Latitude)) + 
    (69.1*(previous.Longitude-next.Longitude)) * 
    cos(next.Latitude/57.3) * (69.1*(previous.longitude-next.Longitude)) * 
    cos(next.Latitude/57.3)) as Miles 
From CTE2 as Previous 
Join CTE2 as Next 
On previous.Vehicle_ID = Next.Vehicle_ID 
AND Previous.RN = 
Next.RN - 1 
select cast(Latitude/1000000.0 as decimal(10, 6)) as Latitude 
    , cast(Longitude/1000000.0 as decimal(10, 6)) as Longitude 
from cte2 

**** ****編輯
期望的結果看起來類似這樣:

Latitude Longitude Mileage Radio_Name 
36.158500 115.949833 3.444 MAS7 
36.340000 115.914667 3.443 MAS7 
36.153488 115.944875 4.544 MAS7 

(這是不正確的里程,但它只是一個例子什麼我正在尋找結果。)

+1

你能舉一個你想要的輸出的例子嗎? –

+0

請參閱上面的內容。 –

回答

2

請注意the difference between tamp tables, table variables and CTEs

您目前正在使用Common Table Expressions或CTE,它們更類似於derived tables,因爲它們只能用於直接跟隨它們的一條select(或insert,update等)語句(儘管您可以聲明多於一個CTE的聲明,如你所做的那樣)。因此,當你到達你的第二選擇語句時,你的CTE已經超出了範圍,你不能再引用它們(或者你必須再次聲明它們)。在這種情況下,您可能需要使用table variabletemp table

-- Make a temp table 
SELECT * 
INTO #TempTableName -- Create a new temp table 
FROM AVL 
WHERE DATE_TIME between '01/30/2013 00:00:00' AND '01/30/2013 23:59:59' 
    AND radio_name = 'MAS7' 

-- Check out our new temp table 
SELECT * FROM #TempTableName 

-- Clean up our temp table, though this will automatically happen once the connection is dropped 
DROP TABLE #TempTableName 

此外,與臨時表工作時,我會經常檢查並在開始和結束拖放:

你可能很容易地通過轉換你的CTE定義像下面創建一個臨時表我的過程如下所示:

if object_id('tempdb..#TempTableName') is not null begin 
    drop table #TempTableName 
end 

在代碼中包含這些東西,如果您在執行實際距離計算時遇到困難,請告訴我們。

+0

我嘗試將代碼插入臨時表中,但仍無法設置實際的里程公式。 –