web-dev-qa-db-fra.com

SQL Server (2017?) Index Lat / Long et Query

TLDR: Étant donné un ensemble d'index Lat/Lon => Index et retour "à proximité".

Je travaille à travers un livre moyen Node.js/MongoDB/Express/Angulaire. Ce n'est certainement pas quelque chose que je suis à l'aise - je suis plus à l'aise avec SQL Server. Je regarde également SQL Server 2017 dans Docker Conteners.

L'exercice sur lequel je travaille a une application de type Yelp: Compte tenu d'un emplacement, montrez à proximité des entreprises et donnez à l'utilisateur la possibilité d'évaluer ces entreprises.

Où je suis à l'intention de déplacer la base de données/API de Backend de Mongodb/Express/Nœud dans SQL Server, ASP.NET MVC.

Compte tenu de la disposition de l'échantillon

Est ceci où je devrais regarder? Je ne vois pas exactement ce que je cherche ...

  • Créer une table avec des coordonnées Lat/Long
  • indexer les coordonnées
  • requête à proximité

Je cherche toujours, mais je ne trouve pas ce que je cherche ...

edit: proche question ici , mais pas de cigare

edit: se rapprocher (principalement de - ce blog post ... J'essaie maintenant de déterminer comment indexer et trouver rapidement des points "fermer"

USE master
GO

IF EXISTS(select * from sys.databases where name='MEAN')
    DROP DATABASE MEAN
GO

CREATE DATABASE MEAN
GO

USE MEAN;
GO


CREATE TABLE [dbo].[Landmark] (
    [ID]                INT IDENTITY(1, 1),
    [LandmarkName]      VARCHAR(100),
    [Location]          VARCHAR(50),
    [Latitude]          FLOAT,
    [Longitude]         FLOAT
)
GO

INSERT INTO [dbo].[Landmark] ( [LandmarkName], [Location], [Latitude], [Longitude] )
VALUES ( 'Statue of Liberty', 'New York, USA', 40.689168,-74.044563 ),
       ( 'Eiffel Tower', 'Paris, France', 48.858454, 2.294694),
       ( 'Leaning Tower of Pisa', 'Pisa, Italy', 43.72294, 10.396604 ),
       ( 'Great Pyramids of Giza', 'Cairo, Egypt', 29.978989, 31.134632 ),
       ( 'Sydney Opera House', 'Syndey, Australia', -33.856651, 151.214967 ),
       ( 'Taj Mahal', 'Agra, India', 27.175047, 78.042042 ),
       ( 'Colosseum', 'Rome, Italy', 41.890178, 12.492378 )
GO

ALTER TABLE [dbo].[Landmark]
ADD [GeoLocation] GEOGRAPHY
GO

UPDATE [dbo].[Landmark]
SET [GeoLocation] = geography::Point([Latitude], [Longitude], 4326);

GO

DECLARE @source geography = geography::Point(40.689168,y    -74.044563, 4326); 

SELECT *, @source.STDistance([GeoLocation])
FROM [dbo].[Landmark]
2
WernerCD

Il y a quelques approches pouvant être utilisées ici en fonction des exigences exactes.

Tout d'abord, vous devrez créer un index spatial sur la table historique.

CREATE SPATIAL INDEX Landmark_GeoLocation_SDX 
ON [dbo].[Landmark] ([GeoLocation])
USING GEOGRAPHY_AUTO_GRID;

Ensuite, pour interroger pour tous les points dans une distance spécifiée, vous pouvez faire une requête similaire à celle suivante.

DECLARE @withinDistance float = 500.0; -- This is specified in metres
DECLARE @source geography = geography::Point(40.689168, -74.044563, 4326);    

SELECT *, @source.STDistance([GeoLocation])
FROM [dbo].[Landmark]
WHERE @source.STBuffer(@withinDistance).STContains([GeoLocation]) = 1;

L'autre requête commune pour ce type de chose est de renvoyer le N les points les plus proches, autrement connu sous le nom de voisin le plus proche ou Knn mettre en doute.

DECLARE @neighbourCount int = 5; -- This is specified in metres
DECLARE @source geography = geography::Point(40.689168, -74.044563, 4326);    

SELECT TOP (@neighbourCount) *, @source.STDistance([GeoLocation])
FROM [dbo].[Landmark]
WHERE @source.STDistance([GeoLocation]) IS NOT NULL
ORDER BY @source.STDistance([GeoLocation])
2
MickyT