PostGIS — geografik ma'lumotlar, location based queries
Yaqin atrofdagi restoranlarni ko'rsatish kerak. Foydalanuvchi koordinatalari bor — 41.2995, 69.2401. 2 km doiradagi restoranlar kerak. Oddiy SQL bilan bu murakkab — lekin PostGIS bilan bir so'rov.
PostGIS o'rnatish
CREATE EXTENSION IF NOT EXISTS postgis;
CREATE EXTENSION IF NOT EXISTS postgis_topology; -- qo'shimcha
SELECT PostGIS_Version(); -- 3.x.x
Asosiy turlar
POINT — nuqta (lon, lat)
LINESTRING — chiziq
POLYGON — ko'pburchak (maydon)
GEOMETRY — istalgan geometrik tur
GEOGRAPHY — yer shari yuzasidagi (metrda hisoblash)
Jadval yaratish
CREATE TABLE restoranlar (
id SERIAL PRIMARY KEY,
nomi TEXT,
manzil TEXT,
koordinata GEOGRAPHY(POINT, 4326) -- 4326 = WGS84 (GPS)
);
Ma'lumot qo'shish:
INSERT INTO restoranlar (nomi, manzil, koordinata) VALUES
('Café Milano', 'Navoiy ko''cha', ST_MakePoint(69.2401, 41.2995)::geography),
('Samarkand Osh', 'Amir Temur xiyob', ST_MakePoint(69.2800, 41.3100)::geography),
('Pizza House', 'Chilonzor', ST_MakePoint(69.2150, 41.2850)::geography);
Yaqin joylar — ST_DWithin
-- Toshkent markazidan 2 km doiradagi restoranlar
SELECT nomi, manzil,
ST_Distance(koordinata, ST_MakePoint(69.2401, 41.2995)::geography) AS masofa
FROM restoranlar
WHERE ST_DWithin(
koordinata,
ST_MakePoint(69.2401, 41.2995)::geography,
2000 -- 2000 metr = 2 km
)
ORDER BY masofa;
nomi | manzil | masofa
─────────────── ────────────── ───────
Café Milano | Navoiy ko'cha | 0
Samarkand Osh | Amir Temur | 1823
Masofa hisoblash — ST_Distance
SELECT
nomi,
round(ST_Distance(
koordinata,
ST_MakePoint(69.2401, 41.2995)::geography
)::numeric) AS masofa_metr
FROM restoranlar
ORDER BY masofa_metr;
GiST Index — tez qidiruv
Geografik qidiruv uchun GiST index:
CREATE INDEX idx_restoranlar_geo ON restoranlar USING GIST (koordinata);
Indexsiz million qatorda ST_DWithin juda sekin. Index bilan — millisekundlar.
Boshqa foydali funksiyalar
-- Koordinatadan matn
ST_AsText(koordinata) -- 'POINT(69.24 41.30)'
ST_AsGeoJSON(koordinata) -- GeoJSON format
-- Maydon hisoblash
ST_Area(polygon::geography) -- metr kvadrat
-- Chegarada ekanligini tekshirish
ST_Contains(shahar_chegarasi, nuqta)
-- Masofaga qarab tartiblash
ORDER BY koordinata <-> ST_MakePoint(69.24, 41.30)::geography
Tez-tez uchraydigan xatolar
lon va lat tartibini almashtirish:
-- ❌ — (lat, lon) — noto'g'ri
ST_MakePoint(41.2995, 69.2401)
-- ✅ — (lon, lat) — to'g'ri tartib
ST_MakePoint(69.2401, 41.2995)
PostGIS da: ST_MakePoint(longitude, latitude) — uzunlik avval, kenglik keyin.
GEOMETRY vs GEOGRAPHY:
GEOMETRY — tekis koordinat tizimi, daraja hisoblaydi, tez
GEOGRAPHY — yer shari yuzasi, metr hisoblaydi, to'g'ri
Odatda GEOGRAPHY ishlatilsin — metr bilan ishlash mantiqli
Xulosa
-- O'rnatish
CREATE EXTENSION postgis;
-- Jadval
koordinata GEOGRAPHY(POINT, 4326)
-- Ma'lumot
ST_MakePoint(lon, lat)::geography
-- Qidiruv
ST_DWithin(koordinata, markaz, metr) -- doirada
ST_Distance(a, b) -- masofa
ST_Contains(maydon, nuqta) -- ichida
-- Index
CREATE INDEX ON jadval USING GIST (koordinata);
Keyingi dars
60-dars: pg_trgm — fuzzy search, ILIKE tezlashtirish