Ich habe die Oberfläche von Artenverteilungen berechnet (Zusammenführen von Polygonen aus Shapefiles), aber da diese Fläche aus ziemlich weit entfernten Polygonen bestehen kann, möchte ich ein Maß für die Dispersion berechnen. Was ich bisher getan habe, ist, die Schwerpunkte jedes Polygons abzurufen, den Abstand zwischen diesen zu berechnen und diese zur Berechnung des Variationskoeffizienten zu verwenden, wie im folgenden Dummy-Beispiel;
require(sp)
require(ggplot2)
require(mapdata)
require(gridExtra)
require(scales)
require(rgeos)
require(spatstat)
# Create the coordinates for 3 squares
ls.coords <- list()
ls.coords <- list()
ls.coords[[1]] <- c(15.7, 42.3, # a list of coordinates
16.7, 42.3,
16.7, 41.6,
15.7, 41.6,
15.7, 42.3)
ls.coords[[2]] <- ls.coords[[1]]+0.5 # use simple offset
ls.coords[[3]] <- c(13.8, 45.4, # a list of coordinates
15.6, 45.4,
15.6, 43.7,
13.8, 43.7,
13.8, 45.4)
# Prepare lists to receive the sp objects and data frames
ls.polys <- list()
ls.sp.polys <- list()
for (ii in seq_along(ls.coords)) {
crs.args <- "+proj=longlat +datum=WGS84 +no_defs +ellps=WGS84 +towgs84=0,0,0"
my.rows <- length(ls.coords[[ii]])/2
# create matrix of pairs
my.coords <- matrix(ls.coords[[ii]],nrow = my.rows,ncol = 2,byrow = TRUE)
# now build sp objects from scratch...
poly = Polygon(my.coords)
# layer by layer...
polys = Polygons(list(poly),1)
spolys = SpatialPolygons(list(polys))
# projection is important
proj4string(spolys) <- crs.args
# Now save sp objects for later use
ls.sp.polys[[ii]] <- spolys
# Then create data frames for ggplot()
poly.df <- fortify(spolys)
poly.df$id <- ii
ls.polys[[ii]] <- poly.df
}
# Convert the list of polygons to a list of owins
w <- lapply(ls.sp.polys, as.owin)
# Calculate the centroids and get the output to a matrix
centroid <- lapply(w, centroid.owin)
centroid <- lapply(centroid, rbind)
centroid <- lapply(centroid, function(x) rbind(unlist(x)))
centroid <- do.call('rbind', centroid)
# Create a new df and use fortify for ggplot
centroid_df <- fortify(as.data.frame(centroid))
# Add a group column
centroid_df$V3 <- rownames(centroid_df)
ggplot(data = italy, aes(x = long, y = lat, group = group)) +
geom_polygon(fill = "grey50") +
# Constrain the scale to 'zoom in'
coord_cartesian(xlim = c(13, 19), ylim = c(41, 46)) +
geom_polygon(data = ls.polys[[1]], aes(x = long, y = lat, group = group), fill = alpha("red", 0.3)) +
geom_polygon(data = ls.polys[[2]], aes(x = long, y = lat, group = group), fill = alpha("green", 0.3)) +
geom_polygon(data = ls.polys[[3]], aes(x = long, y = lat, group = group), fill = alpha("lightblue", 0.8)) +
coord_equal() +
# Plot the centroids
geom_point(data=centroid_points, aes(x = V1, y = V2, group = V3))
# Calculate the centroid distances using spDists {sp}
centroid_dists <- spDists(x=centroid, y=centroid, longlat=TRUE)
centroid_dists
[,1] [,2] [,3]
[1,] 0.00000 69.16756 313.2383
[2,] 69.16756 0.00000 283.7120
[3,] 313.23834 283.71202 0.0000
# Calculate the coefficient of variation as a measure of polygon dispersion
cv <- sd(centroid_dist)/mean(centroid_dist)
[1] 0.9835782
Darstellung der drei Polygone und ihrer Schwerpunkte
Ich bin mir nicht sicher, ob dieser Ansatz sehr nützlich ist, da in einigen Fällen einige der Polygone (wie das blaue im obigen Beispiel) im Vergleich zu den anderen ziemlich groß sind, wodurch der Abstand noch weiter vergrößert wird. Zum Beispiel hat der Schwerpunkt Australiens fast die gleiche Entfernung zu seinen westlichen Grenzen wie nach Papau.
Was ich gerne bekommen würde, ist ein Beitrag zu alternativen Ansätzen. Wie oder mit welcher Funktion kann ich beispielsweise den Abstand zwischen Polygonen berechnen?
Ich habe getestet, ob der obige SpatialPolygon-Datenrahmen in PointPatterns (ppp) konvertiert werden {spatstat}
soll nndist() {spatstat}
, um den Abstand zwischen allen Punkten berechnen zu können . Aber da ich es mit ziemlich großen Flächen zu tun habe (viele Polygone und große), wird die Matrix riesig und ich bin mir nicht sicher, wie ich weiterhin zum minimalen Abstand zwischen den Polygonen gelangen soll .
Ich habe mir auch die Funktion angesehen gDistance {rgeos}
, aber ich denke, sie funktioniert nur mit projizierten Daten, was für mich ein Problem sein kann, da meine Bereiche mehrere Bereiche überschreiten können EPSG areas
. Das gleiche Problem würde für die Funktion auftreten crossdist {spatstat}
.
postgres/postgis
zusätzlich verwendenR
? Ich habe einen Workflow verwendet, in dem ich den größten Teil meiner Arbeit ausführeR
, die Daten jedoch in einer Datenbank speichere, auf die ich mit zugegriffen habesqldf
. Dies ermöglicht es Ihnen, allepostgis
Funktionen zu verwenden (deren Abstand zwischen Polygonen direkt ist)postgres
versuchen :) Ich habe mit dem Aufbau einer Datenbank begonnen, aber aufgehört, als ich nicht wusste (nicht sah), wie ich den Workflow / die Geostaten zwischen der Datenbank undR
...Antworten:
Sie können diese Analyse im Paket "spdep" durchführen. Wenn Sie in den relevanten Nachbarfunktionen "longlat = TRUE" verwenden, berechnet die Funktion die Großkreisentfernung und gibt Kilometer als Entfernungseinheit zurück. Im folgenden Beispiel können Sie das resultierende Entfernungslistenobjekt ("dist.list") in eine Matrix oder einen data.frame zwingen. Die Berechnung von Zusammenfassungsstatistiken mit lapply ist jedoch recht effizient.
quelle
spdeb
Paket. Nur zur Verdeutlichung liefert dieser Ansatz die gleiche Ausgabe wie in meinem Beispiel, oder?