spatial sql

56
An Introduction to spatial queries in SQL Server 2008 VBUG Manchester 24 th July 2008

Upload: philwinstanley

Post on 27-Jan-2015

162 views

Category:

Business


12 download

DESCRIPTION

 

TRANSCRIPT

Page 1: Spatial SQL

An Introduction to spatial queries in SQL Server 2008

VBUG Manchester 24th July 2008

Page 2: Spatial SQL

New data types geometry and geography

Spatial references Spatial operations Spatial indexes Case study

Page 3: Spatial SQL

80-90% of all data has a spatial element Where are your customers? Where are your assets? Where are potential customers? Where are the flood risks? Where are your complaints coming from? Where are the accident black-spots? Where are crimes happening?

Page 4: Spatial SQL

Postcodes in Glasgow

Zoned Historical reasons G5 adjacent to G42 G40 in an island Postcodes

designed for delivering letters

Page 5: Spatial SQL

The data analysis engine No rendering engine

Virtual Earth Map Point Other GIS systems

OGC Standards compliance Plus some “extension” methods of their

own

Page 6: Spatial SQL

Currently at Release Candidate 0 Some features won’t be introduced until

RTM Feature Pack (RC0) also now available

Contains CLR Types Editions

Spatial querying available from Express edition up

Page 7: Spatial SQL

Basic rendering engine for query results SQL Server Management Studio

Page 8: Spatial SQL

X/Y coordinate on a planar grid

British National Grid Works well to

~750,000km2 Different projections

Page 9: Spatial SQL

Historically easier to use

Distorts shape, size or position Greenland Vs. USA

More distortion towards the edges

Planar model based on the Mercator projection

Lat/Long lines every 10o

Page 10: Spatial SQL

Geodetic coordinates Covers larger areas International datasets Approximation

Earth actually flattened sphere (oblate spheroid)

Different models Airy 1830 (used by OS) WGS84 (used by GPS)

Page 11: Spatial SQL

Spatial Reference Identifier All spatial data has an SRID SRIDs must match for spatial

operations Null returned if SRIDs don’t match

Geometry can have an SRID of 0

Page 12: Spatial SQL

SRID Authority

WKT Units Factor

4157 EPSG GEOGCS["Mount Dillon", DATUM["Mount Dillon", ELLIPSOID["Clarke 1858", 6378293.64520876, 294.260676369261]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

Clarke's foot 0.304797265

4243 EPSG GEOGCS["Kalianpur 1880", DATUM["Kalianpur 1880", ELLIPSOID["Everest (1830 Definition)", 6377299.36559538, 300.8017]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

Indian foot 0.304799518

4268 EPSG GEOGCS["NAD27 Michigan", DATUM["NAD Michigan", ELLIPSOID["Clarke 1866 Michigan", 6378450.0475489, 294.978697164674]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

US survey foot

0.30480061

4277 EPSG GEOGCS["OSGB 1936", DATUM["OSGB 1936", ELLIPSOID["Airy 1830", 6377563.396, 299.3249646]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

metre 1

4293 EPSG GEOGCS["Schwarzeck", DATUM["Schwarzeck", ELLIPSOID["Bessel Namibia (GLM)", 6377483.86528042, 299.1528128]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

German legal metre

1.000013597

4326 EPSG GEOGCS["WGS 84", DATUM["World Geodetic System 1984", ELLIPSOID["WGS 84", 6378137, 298.257223563]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

metre 1

4748 EPSG GEOGCS["Vanua Levu 1915", DATUM["Vanua Levu 1915", ELLIPSOID["Clarke 1880 (international foot)", 6378306.3696, 293.46630765563]], PRIMEM["Greenwich", 0], UNIT["Degree", 0.0174532925199433]]

foot 0.3048

Page 13: Spatial SQL

Point LineString Polygon GeomCollection MultiPolygon MultiLineString MultiPoint

From BOL

Page 14: Spatial SQL

Two spatial types Geometry Geography

CREATE TABLE Venue( Id INT IDENTITY(1,1) NOT NULL,

Name NVARCHAR(256),

Location GEOGRAPHY)

Page 15: Spatial SQL

A single coordinate 0 dimensions

Page 16: Spatial SQL

INSERT INTO Venue VALUES( 'HBOS', geography::STGeomFromText( 'POINT(-3.29431266523898 ◊ 55.9271035250276)',4326));

Page 17: Spatial SQL

INSERT INTO VenueVALUES( 'Glasgow Caledonian University', geography::Parse( 'POINT(-4.25072511658072 ◊ 55.8659449685365)'));

Page 18: Spatial SQL

INSERT INTO Venue VALUES( ‘Dundee University', geography::STGeomFromWKB( 0x01010000000700ECFAD03A4C4001008000 ◊ B5DF07C0,

4326));

Page 19: Spatial SQL

INSERT INTO VenueVALUES( 'Microsoft Campus, TVP', geography::Point(-0.926690306514502, 51.4618933852762, 4326));

Page 20: Spatial SQL

INSERT INTO VenueVALUES( Microsoft Edinburgh Office', geography::STPointFromText( 'POINT(-3.2051030639559 ◊

55.9523783996701)', 4326));

STPointFromWKB also available

Page 21: Spatial SQL

SELECT Id, Name, Location.ToString() As LocationTextFROM Venue

Page 22: Spatial SQL

Very similar – Same methods available

Page 23: Spatial SQL

SELECT a.Name AS StartVenue, b.Name AS EndVenue, a.Location.STDistance(b.Location) / 1000.0 As DistanceFROM Venue AS aCROSS JOIN Venue AS bWHERE a.Id < b.IdORDER BY a.Id, b.Id

GCU 60

Dundee U

62 102

MS TVP 520 537 572

MS Edin’

6 66 58 521

HBOS GCU Dundee U

MS TVP

Page 24: Spatial SQL

A linestring is a series of coordinates 1 dimension Defines a linear object

Road Railway line River

Page 25: Spatial SQL

Can use STGeomFromText STGeomFromWKB STLineFromText STLineFromWKB Parse

Page 26: Spatial SQL

geography::STGeomFromText('LINESTRING (2.54223106428981 49.0170682501048, 4.7684115730226 52.3141136672348, -3.36429820396006 55.9505973290652, -0.444141207262874 51.4748916216195, -3.56782372109592 40.4884308949113)', 4326);

Charles de GaulleSchipholTurnhouseHeathrowBarajas

Page 27: Spatial SQL

DECLARE @g geographySELECT @g = geography::Parse('LINESTRING (2.54223106428981 49.0170682501048,

4.7684115730226 52.3141136672348, -3.36429820396006 55.9505973290652, -0.444141207262874 51.4748916216195, -3.56782372109592 40.4884308949113)');

SELECT @g.STLength()----------------------2845161.34954758

Result in SI Units (Metres)

Page 28: Spatial SQL

Geography uses SI Units Geometry uses the units of the planar

system

The square of the The square of the hypotenuse is equal hypotenuse is equal to the sum of the to the sum of the square of the other square of the other two sidestwo sides

The square of the The square of the hypotenuse is equal hypotenuse is equal to the sum of the to the sum of the square of the other square of the other two sidestwo sides

Not to scale

3 units

4 units

? units

Distance from A to B:√(32+42) = 5

A

B

Page 29: Spatial SQL

STIntersection The points at which two objects intersect Returns a geometry / geography

STIntersects Whether a two objects intersect Returns 1 or 0

Page 30: Spatial SQL

DECLARE @a geometry, @b geometry, @c geometry

SELECT @a = geometry::Parse('LINESTRING(0 0, 10 10)'),@b = geometry::Parse('LINESTRING(10 0, 0 10)'),@c = geometry::Parse('LINESTRING(20 20, 30 30)');

SELECT @a.STIntersection(@b).ToString() AS [first], @a.STIntersection(@c).ToString() AS [second],@a.STIntersects(@c) AS [third]

first second third-----------------------------------------------------POINT (5 5) GEOMETRYCOLLECTION EMPTY 0

Page 31: Spatial SQL

A series of coordinates in a closed ring First and last coordinate are the same

2 dimensions Defines an area

Page 32: Spatial SQL

Interior is everything inside an anti-clockwise ring Everything on the

left-hand side of the perimeter line.

Page 33: Spatial SQL

The specified input does not represent a valid geography instance because it exceeds a single hemisphere. Each geography instance must fit inside a single hemisphere. A common reason for this error is that a polygon has the wrong ring orientation.

Page 34: Spatial SQL

Can use STGeomFromText STGeomFromWKB STPolygonFromText STPolygonFromWKB Parse

Page 35: Spatial SQL

geography::STGeomFromText('POLYGON ((-4.23691584728658 55.8676369395107, -4.25517079420388 55.8703819289804, -4.27013483829796 55.8681968506426, -4.26963351666927 55.8562753535807, -4.25607042387128 55.8552713692188, -4.24729574471712 55.8528072573245, -4.23971313983202 55.8606443367898, -4.23691584728658 55.8676369395107))',

4326);

Page 36: Spatial SQL

DECLARE @g geography;SELECT @g = geography::STGeomFromText('POLYGON ((-4.23691584728658 55.8676369395107,

-4.25517079420388 55.8703819289804, -4.27013483829796 55.8681968506426, -4.26963351666927 55.8562753535807, -4.25607042387128 55.8552713692188, -4.24729574471712 55.8528072573245, -4.23971313983202 55.8606443367898, -4.23691584728658 55.8676369395107))', 4326);

SELECT @g.STLength()/1000.0 AS [Length (km)], @g.STArea()/1000000.0 AS [Area (km^2)]

Length (km) Area (km^2)---------------------- ----------------------6.74090984542709 2.96444752890813

Page 37: Spatial SQL

DECLARE @g geography;SELECT @g = geography::STGeomFromText('POLYGON ((-4.23691584728658

55.8676369395107, -4.25517079420388 55.8703819289804, -4.27013483829796 55.8681968506426, -4.26963351666927 55.8562753535807, -4.25607042387128 55.8552713692188, -4.24729574471712 55.8528072573245,

-4.23971313983202 55.8606443367898, -4.23691584728658 55.8676369395107))', 4326);

SELECT Name FROM VenueWHERE Location.STIntersects(@g) = 1

Name------------------------------Glasgow Caledonian University

Page 38: Spatial SQL

Coming up in part 2 Spatial Indexes Estate Agent case study

Page 39: Spatial SQL

Estate Agent Filter by price, # bedrooms, type – EASY! Filter by location?

Until now very vague

Page 40: Spatial SQL

I want a home that is… Near a railway station In the catchment for a good school Near my work Near a motorway junction Outside the city In the city

Page 41: Spatial SQL

Railway data Stations Routes

Page 42: Spatial SQL

SELECT rs.Name, rs.Operator, s.Name AS StationNameFROM RailService AS rsINNER JOIN Station AS s ON INNER JOIN Station AS s ON

s.Location.STIntersects(rs.Route) = 1s.Location.STIntersects(rs.Route) = 1WHERE rs.Name='Edinburgh - Queen Street'

Name Operator StationName------------------------- --------------- ---------------------------Edinburgh - Queen Street FirstScotRail CroyEdinburgh - Queen Street FirstScotRail BishopbriggsEdinburgh - Queen Street FirstScotRail Falkirk HighEdinburgh - Queen Street FirstScotRail Edinburgh Waverley StationEdinburgh - Queen Street FirstScotRail LinlithgowEdinburgh - Queen Street FirstScotRail LenzieEdinburgh - Queen Street FirstScotRail HaymarketEdinburgh - Queen Street FirstScotRail PolmontEdinburgh - Queen Street FirstScotRail Queen Street

Page 43: Spatial SQL

SELECT s.Name, s.Location.STDistance(st.Location)s.Location.STDistance(st.Location) / 1000.0 AS DistKM

FROM RailService AS rsINNER JOIN Station AS s ON s.Location.STIntersects(rs.Route) = 1s.Location.STIntersects(rs.Route) = 1INNER JOIN Station AS st ON rs.EndPoint1StationId = st.IdWHERE rs.Name='Edinburgh - Queen Street'ORDER BY s.Location.STDistance(st.Location)s.Location.STDistance(st.Location)

Name DistKM-------------------------- -----------------Edinburgh Waverley Station 0Haymarket 1.89298770395887Linlithgow 25.330363556826Polmont 32.9442879992987Falkirk High 37.8121663726382Croy 52.7800190223697Lenzie 60.3440166609702Bishopbriggs 64.8149950514336Queen Street 67.0874880660717

Page 44: Spatial SQL

Edinburgh - Glenrothes (via Kirkcaldy)

Name DistKM-------------------------- ----------------Edinburgh Waverley Station 0Haymarket 1.89298770395887South Gyle 6.95446540329848Burntisland 12.086984317701Dalmeny 12.49585147351Kinghorn 13.1439998546632Aberdour 13.3392361220632North Queensferry 14.3833962761344Dalgety Bay 15.0082794626365Inverkeithing 15.7316327831032Kirkcaldy 17.9484646860063Glenrothes With Thornton 23.7022936117453

Page 45: Spatial SQL

Works close to Queen Street Station Wants to take the

train to work

SELECT rs.Name, rs.Operator

FROM RailService AS rs

INNER JOIN Station AS s ON INNER JOIN Station AS s ON rs.Route.STIntersects(rs.Route.STIntersects(s.Location) = 1s.Location) = 1

WHERE s.Name = 'Queen Street'

Name Operator-----------------------------------

-------------Edinburgh - Queen Street

FirstScotRailQueen Street - Perth

FirstScotRailQueen Street - Alloa

FirstScotRailQueen Street - Inverness

FirstScotRailKirkcaldy - Glasgow Queen Street

FirstScotRailQueen Street - Mallaig

FirstScotRailDalmuir - Springburn SPTBalloch - Airdrie SPTHelensburgh Central - Drumgelloch SPTQueen Street - Anniesland SPT

Page 46: Spatial SQL

Get all the stations on routes that have a stop at Queen Street

SELECT DISTINCT ps.NameFROM RailService AS rsINNER JOIN Station AS s ON

rs.Route.STIntersects(s.Location) = 1

INNER JOIN Station AS ps ON INNER JOIN Station AS ps ON rs.Route.STIntersects(ps.Location) rs.Route.STIntersects(ps.Location) = 1= 1

WHERE s.Name = 'Queen Street'

Page 47: Spatial SQL

Buffer 500m around relevant stations

Need to aggregate the buffered points Not built in CLR Aggregator? Cursor ?!?

STBuffer(double) Param is the

distance in metres.

Page 48: Spatial SQL
Page 49: Spatial SQL

Decomposes space into 4 levels of grid

Level 1 is the top Cells are uniform in

a level A level can be a

4x4, 8x8 or 16x16 grid 8x8 by default

Page 50: Spatial SQL

Table must have a primary key Primary key cannot subsequently be

changed. Not on views Maximum of 249 Spatial indexes per

column

Page 51: Spatial SQL

Supports STIntersects STEquals STDistance

One Geography must be a point

Both sides of the spatial operation must have the same SRID

Page 52: Spatial SQL

Must specify boundary of spatial area Additional methods supported

STContains STOverlaps STTouches STWithin

Page 53: Spatial SQL

GML Import and export

M and Z Can store Cannot operate.

Other spatial Operations Geometry has more!

Visualisation .NET application

integration Data Importing Demos

Page 54: Spatial SQL

I want to know What additional things you’d like covered

Page 55: Spatial SQL

Slide Deck on my website http://www.colinmackay.net

Blog posts on Spatial Data http://blog.colinmackay.net

Page 56: Spatial SQL