相邻城市对质心与共同边界的距离及共同边界矢量数据

上次给大家分享了相邻县对的质心与共同边界的距离及共同边界矢量数据,今天再给大家分享一个城市的~非常适合进行城市级别政策的效应评估。

数据概览

首先我们找到了中国所有的相邻城市对(基于 2019 年中国城市级行政区划),一共是 973 组:

  • 2019年中国相邻市对.xlsx

附件中的 commonline-shp 文件夹为相邻市对的共同边界矢量数据,据此我们可以绘制不同城市间的共同边界:

通过计算每个相邻城市对的质心与共同边界的距离就可以得到这个数据包了:

  • 相邻城市对质心与共同边界的距离_km.dta

例如天津市与北京市质心与共同边界的最小距离:

图中的散点表示各城市质心,散点越小表示距离共同边界越近,图中的蓝色粗线表示两个城市的共同边界。

希望这份数据包能够帮助大家发论文~

绘图展示

附件中的 main.R 文件是用来绘制相邻城市对质心与共同边界距离的,使用类似下面的绘图语句就可以绘制了:

library(tidyverse)
library(sf)

# 读取城市
read_sf("2019行政区划/市.shp") %>%
st_transform(4326) %>%
dplyr::filter(!is.na(市)) %>%
st_make_valid() -> city

# 获取所有的相邻市对
st_intersects(st_make_valid(city), st_make_valid(city), sparse = F) -> touchmat
touchmat %>%
as_tibble() %>%
mutate_all(as.numeric) %>%
mutate(市代码 = city$市代码) %>%
select(市代码, everything()) %>%
set_names(c("市代码", city$市代码)) %>%
gather(2:372, key = "key", value = "value") %>%
dplyr::filter(市代码 != key & value == 1) -> pairdf

pairdf

# 去除反向重复的(比较大小,仅仅保留前面的大于后面的)
pairdf %>%
mutate(key = as.numeric(key)) %>%
dplyr::filter(市代码 > key) %>%
rename(相邻市 = key) %>%
select(-value) -> pairdf

pairdf %>%
slice(1) -> pair1

city %>%
dplyr::filter(市代码 == pair1$市代码) -> maincity
city %>%
dplyr::filter(市代码 == pair1$相邻市) -> touchcity

# 共同市界
st_intersection(st_cast(maincity$geometry, "MULTILINESTRING"),
st_cast(touchcity$geometry, "MULTILINESTRING")) %>%
st_collection_extract("LINESTRING") -> commonline

# 两个城市的质心
bind_rows(maincity, touchcity) %>%
select(-contains("类型")) %>%
st_centroid() -> twocity

# twocity 距离这条共同边界的距离
twocity %>%
mutate(
距离相邻市对共同边界的最小距离 = twocity %>%
st_distance(commonline) %>%
units::set_units("km")
) %>%
mutate(距离相邻市对共同边界的最小距离 = as.numeric(距离相邻市对共同边界的最小距离)) -> citycentroid

citycentroid %>%
st_drop_geometry() %>%
mutate(pair = paste0(市代码[1], "-", 市代码[2]))

# 绘图
ggplot() +
geom_sf(data = maincity, aes(fill = 市), alpha = 0.3) +
geom_sf(data = touchcity, aes(fill = 市), alpha = 0.5) +
geom_sf(data = commonline, color = "#709ae1", size = 2) +
geom_sf(data = citycentroid,
aes(size = 距离相邻市对共同边界的最小距离),
color = "gray20", shape = 16) +
scale_fill_manual(values = c("#ff847c", "#99b898"), name = "") +
scale_size_continuous(range = c(1, 4),
name = "距离相邻市对共同边界\n的最小距离(km)") +
labs(title = paste0(maincity$市, "与", touchcity$市,
"质心与共同边界的最小距离"),
subtitle = "数据计算&绘图:微信公众号 RStata",
caption = "注:散点大小表示质心距离两个共同市界的最小距离,图中的蓝色粗线表示两个市的共同市界") +
scale_x_continuous(limits = c(115, 120)) +
theme(legend.position.inside = c(0.9, 0.5),
legend.position = "inside")

点击这里跳转到 RStata 短书平台获取附件:相邻城市对质心与共同边界的距离及共同边界矢量数据

评论