Szukam algorytmu klastrowania przestrzennego do używania go w bazie danych obsługującej PostGIS dla obiektów punktowych. Zamierzam napisać funkcję plpgsql, która pobiera odległość między punktami w tym samym klastrze co dane wejściowe. Na wyjściu funkcja zwraca tablicę klastrów. Najbardziej oczywistym rozwiązaniem jest zbudowanie określonych stref buforowych wokół obiektu i poszukiwanie funkcji do tego bufora. Jeśli takie funkcje istnieją, nadal buduj wokół nich bufor itp. Jeśli takie funkcje nie istnieją, oznacza to, że tworzenie klastrów zostało zakończone. Może są jakieś sprytne rozwiązania?
postgis
clustering
drnextgis
źródło
źródło
Odpowiedzi:
Istnieją co najmniej dwie dobre metody grupowania dla PostGIS: k- oznacza (poprzez
kmeans-postgresql
rozszerzenie) lub geometrie grupowania w odległości progowej (PostGIS 2.2)1) k- oznacza z
kmeans-postgresql
Instalacja: Musisz mieć PostgreSQL 8.4 lub nowszy na systemie hosta POSIX (nie wiedziałbym od czego zacząć dla MS Windows). Jeśli masz to zainstalowane z pakietów, upewnij się, że masz również pakiety programistyczne (np.
postgresql-devel
Dla CentOS). Pobierz i rozpakuj:Przed budowaniem musisz ustawić
USE_PGXS
zmienną środowiskową (mój poprzedni post polecił usunąć tę częśćMakefile
, która nie była najlepsza z opcji). Jedno z tych dwóch poleceń powinno działać dla twojej powłoki Unix:Teraz skompiluj i zainstaluj rozszerzenie:
(Uwaga: próbowałem tego również z Ubuntu 10.10, ale bez powodzenia, ponieważ ścieżka
pg_config --pgxs
nie istnieje! To prawdopodobnie błąd pakowania Ubuntu)Zastosowanie / przykład: Powinieneś gdzieś mieć tabelę punktów (narysowałem kilka pseudolosowych punktów w QGIS). Oto przykład tego, co zrobiłem:
5
, że znajduje się w drugim argumenciekmeans
funkcji okna jest K całkowitą produkować pięciu klastrów. Możesz zmienić to na dowolną liczbę całkowitą, którą chcesz.Poniżej znajduje się 31 pseudolosowych punktów, które narysowałem i pięć centroidów z etykietą pokazującą liczbę w każdej grupie. Zostało to utworzone przy użyciu powyższego zapytania SQL.
Możesz także spróbować zilustrować położenie tych klastrów za pomocą ST_MinimumBoundingCircle :
2) Grupowanie w odległości progowej za pomocą
ST_ClusterWithin
Ta funkcja agregująca jest zawarta w PostGIS 2.2 i zwraca tablicę GeometryCollections, w której wszystkie komponenty znajdują się w pewnej odległości od siebie.
Oto przykład zastosowania, w którym odległość 100,0 to próg, który daje 5 różnych klastrów:
Największa środkowa gromada ma promień otaczającego okręgu wynoszący 65,3 jednostki lub około 130, czyli więcej niż próg. Wynika to z faktu, że indywidualne odległości między geometriami prętów są mniejsze niż próg, więc wiąże je razem jako jedna większa gromada.
źródło
Napisałem funkcję, która oblicza skupienia cech na podstawie odległości między nimi i buduje wypukły kadłub nad tymi cechami:
Przykład użycia tej funkcji:
„poi” - nazwa warstwy, „wkb_geometry” - nazwa kolumny geometrii, „ogc_fid” - klucz podstawowy tabeli, 14000 - odległość klastra.
Wynik użycia tej funkcji:
źródło
geometry
kolumnę w tabeli, a nie przechowywać osobno lonlat i stworzyć kolumnę z unikalnymi wartościami (identyfikatorami).Jak dotąd najbardziej obiecujące jest to rozszerzenie dla K-oznacza klastrowanie jako funkcja okna: http://pgxn.org/dist/kmeans/
Nie udało mi się jednak zainstalować go pomyślnie.
W przeciwnym razie do podstawowego grupowania siatki można użyć SnapToGrid .
źródło
Uzupełnienie odpowiedzi @MikeT ...
W przypadku MS Windows:
Wymagania:
Co będziesz robić:
cl.exe
kompilatora, aby wygenerować bibliotekę DLL zkmeans
funkcją.Kroki:
Otwórz
kmeans.c
w dowolnym edytorze:Po
#include
wierszach zdefiniuj makro DLLEXPORT za pomocą:Umieść
DLLEXPORT
przed każdą z tych linii:Otwórz wiersz poleceń Visual C ++.
W wierszu poleceń:
kmeans-postgresql
.SET POSTGRESPATH=C:\Program Files\PostgreSQL\9.5
Biegać
Skopiuj
kmeans.dll
do%POSTGRESPATH%\lib
Teraz uruchom polecenie SQL w bazie danych, aby „UTWÓRZ” funkcję.
źródło
Oto sposób wyświetlenia w QGIS wyniku zapytania PostGIS podanego w 2) w tej odpowiedzi
Ponieważ QGIS nie obsługuje ani kolekcji geometrycznych, ani różnych typów danych w tej samej kolumnie geometrii, stworzyłem dwie warstwy, jedną dla klastrów i jedną dla punktów skupionych.
Po pierwsze dla klastrów potrzebujesz tylko wielokątów, inne wyniki to samotne punkty:
Następnie dla punktów klastrowych musisz przekształcić geometrycollection w wielopunktowe:
Niektóre punkty mają te same współrzędne, więc etykieta może być myląca.
źródło
Możesz łatwiej używać rozwiązania Kmeans dzięki metodzie ST_ClusterKMeans dostępnej w Postgis od 2.3 Przykład:
Obwiednia elementów jest używana jako geometria skupienia w powyższym przykładzie. Pierwszy obraz pokazuje oryginalne geometrie, a drugi jest wynikiem wyboru powyżej.
źródło
Oddolne rozwiązanie klastrowe od Uzyskaj pojedynczy klaster z chmury punktów o maksymalnej średnicy w postgis, który nie wymaga dynamicznych zapytań.
i typ z identyfikatorem klastra
Następnie funkcja algorytmu
Stosowanie:
źródło