st_distance to replace dist in pipes - help needed

classic Classic list List threaded Threaded
2 messages Options
Reply | Threaded
Open this post in threaded view
|

st_distance to replace dist in pipes - help needed

Bannar-Martin, Katherine
Hello!

Problem:
I need to take the following code and replace dist in the "created distance matrix" pipe stream (producing object 'res') with st_distance. I'm stuck on how to play with the geometry section so that it reproduces the same distance matrix as dist.mat. (The numbers will be different because of the calculations employed, I know, but the structure of the matrices should be the same). Any help is greatly appreciated. Thanks! Katherine

Code using stats::dist:

###Dependencies####
require(tidyverse)
require(sf)

####Create sample data in decimal degrees:####

START_LONG<-round(runif(n=10,min=-135.7, max=-123.3),digits=4)
START_LAT<-round(runif(n=10,min=48.26, max=55.80),digits=4)
END_LONG<-round(runif(n=10,min=-135.7, max=-123.3),digits=4)
END_LAT<-round(runif(n=10,min=48.28, max=55.82),digits=4)
df<-as.data.frame(cbind(START_LONG,START_LAT,END_LONG,END_LAT))

###convert to utm with package sf
xy1<-df[,c("START_LONG","START_LAT")] #start locations
colnames(xy1)<-c("X", "Y")
xy2<-df[,c("END_LONG","END_LAT")] #end locations
colnames(xy2)<-c("X", "Y")
xy12 <- rbind(as.matrix(xy1), as.matrix(xy2))
df12 <- data.frame(data.frame(xy12, Attribute = rep(c("start","end"),each=nrow(df)), ID = rep(1:(nrow(df)),2)))

df.SP <- st_as_sf(df12, coords = c("X", "Y"), crs = 4326) #wgs84 long lat
df.SP<-st_transform(x = df.SP, crs = 32609) #convert to wgs84 utm zone 9
df.SP$utm_x<-st_coordinates(df.SP)[,1] # get utm coordinates
df.SP$utm_y<-st_coordinates(df.SP)[,2] # get utm coordinates
df.SP<-st_set_geometry(df.SP, NULL)# coerce back to data.frame

###create distance matrix###
res<- df.SP %>%
  dplyr::group_by(Attribute) %>%
  mutate(rows = row_number()) %>%
  left_join(df.SP, by = c('Attribute')) %>%
  rowwise() %>%
  mutate(Distance = ifelse(dist(rbind(c(utm_x.x, utm_y.x), c(utm_x.y, utm_y.y))) != 0,
                           dist(rbind(c(utm_x.x, utm_y.x), c(utm_x.y, utm_y.y))), NA))

dist.mat<-matrix(res$Distance,nrow = 20,ncol = 20)

Data prep for eventually using sf::st_distance:
pts.utm.sf <- df12 %>%
  st_as_sf(coords=c('X','Y'), crs=4326) %>% #wgs84 long lat
  st_transform(32609) #wgs84 utm zone9

#distance matrix without groups (note using group_by "Attribute" does not get me the matrix I want):
dist.utm<- pts.utm.sf %>% st_distance() #calculate distances on utm in m

        [[alternative HTML version deleted]]

_______________________________________________
R-sig-Geo mailing list
[hidden email]
https://stat.ethz.ch/mailman/listinfo/r-sig-geo
Reply | Threaded
Open this post in threaded view
|

Re: st_distance to replace dist in pipes - help needed

Vijay Lulla
Maybe like this?

dist.utm <- matrix(c(st_distance(pts.utm.sf %>%
filter(Attribute=="start")),
                     st_distance(pts.utm.sf %>% filter(Attribute=="end"))),
                     nrow=20,ncol=20)
all.equal(dist.utm, dist.mat)

On Thu, Aug 16, 2018 at 4:53 PM Bannar-Martin, Katherine <
[hidden email]> wrote:

> Hello!
>
> Problem:
> I need to take the following code and replace dist in the "created
> distance matrix" pipe stream (producing object 'res') with st_distance. I'm
> stuck on how to play with the geometry section so that it reproduces the
> same distance matrix as dist.mat. (The numbers will be different because of
> the calculations employed, I know, but the structure of the matrices should
> be the same). Any help is greatly appreciated. Thanks! Katherine
>
> Code using stats::dist:
>
> ###Dependencies####
> require(tidyverse)
> require(sf)
>
> ####Create sample data in decimal degrees:####
>
> START_LONG<-round(runif(n=10,min=-135.7, max=-123.3),digits=4)
> START_LAT<-round(runif(n=10,min=48.26, max=55.80),digits=4)
> END_LONG<-round(runif(n=10,min=-135.7, max=-123.3),digits=4)
> END_LAT<-round(runif(n=10,min=48.28, max=55.82),digits=4)
> df<-as.data.frame(cbind(START_LONG,START_LAT,END_LONG,END_LAT))
>
> ###convert to utm with package sf
> xy1<-df[,c("START_LONG","START_LAT")] #start locations
> colnames(xy1)<-c("X", "Y")
> xy2<-df[,c("END_LONG","END_LAT")] #end locations
> colnames(xy2)<-c("X", "Y")
> xy12 <- rbind(as.matrix(xy1), as.matrix(xy2))
> df12 <- data.frame(data.frame(xy12, Attribute =
> rep(c("start","end"),each=nrow(df)), ID = rep(1:(nrow(df)),2)))
>
> df.SP <- st_as_sf(df12, coords = c("X", "Y"), crs = 4326) #wgs84 long lat
> df.SP<-st_transform(x = df.SP, crs = 32609) #convert to wgs84 utm zone 9
> df.SP$utm_x<-st_coordinates(df.SP)[,1] # get utm coordinates
> df.SP$utm_y<-st_coordinates(df.SP)[,2] # get utm coordinates
> df.SP<-st_set_geometry(df.SP, NULL)# coerce back to data.frame
>
> ###create distance matrix###
> res<- df.SP %>%
>   dplyr::group_by(Attribute) %>%
>   mutate(rows = row_number()) %>%
>   left_join(df.SP, by = c('Attribute')) %>%
>   rowwise() %>%
>   mutate(Distance = ifelse(dist(rbind(c(utm_x.x, utm_y.x), c(utm_x.y,
> utm_y.y))) != 0,
>                            dist(rbind(c(utm_x.x, utm_y.x), c(utm_x.y,
> utm_y.y))), NA))
>
> dist.mat<-matrix(res$Distance,nrow = 20,ncol = 20)
>
> Data prep for eventually using sf::st_distance:
> pts.utm.sf <- df12 %>%
>   st_as_sf(coords=c('X','Y'), crs=4326) %>% #wgs84 long lat
>   st_transform(32609) #wgs84 utm zone9
>
> #distance matrix without groups (note using group_by "Attribute" does not
> get me the matrix I want):
> dist.utm<- pts.utm.sf %>% st_distance() #calculate distances on utm in m
>
>         [[alternative HTML version deleted]]
>
> _______________________________________________
> R-sig-Geo mailing list
> [hidden email]
> https://stat.ethz.ch/mailman/listinfo/r-sig-geo
>


--
Vijay Lulla

Assistant Professor,
Dept. of Geography, IUPUI
425 University Blvd, CA-207C.
Indianapolis, IN-46202
[hidden email]
ORCID: https://orcid.org/0000-0002-0823-2522
Webpage: http://vijaylulla.com

        [[alternative HTML version deleted]]

_______________________________________________
R-sig-Geo mailing list
[hidden email]
https://stat.ethz.ch/mailman/listinfo/r-sig-geo