次元の海で溺れる

Rとデータ解析と統計手法たちとわたし

【maptools】小さいPolygonを結合するだけじゃ足りない、王国を作りたい

「たまにはシムシティじゃなくてCivilizationがやりたい」

そんな自分のためのただのメモ。

今回のテーマ

1.小さな都市をつくる(うそ)
2.小さな都市をさらに繋げて大きな国にする(うそ)

データ

小さな都市を作るための小さな町を集めます。
例のごとく以下のe-statから、シェープファイルをダウンロード。
政府統計の総合窓口 GL01010101
「地図で見る統計(統計GIS)」→「データダウンロード」→「平成22年度国勢調査(小地域)」

1. 札幌市中央区
2. 札幌市北区
3. 札幌市東区
4. 札幌市白石区
5. 札幌市豊平区
6. 札幌市南区
7. 札幌市西区
8. 札幌市厚別区
9. 札幌市手稲区
10.札幌市清田区

全て世界測地系緯度経度・shape形式です。

データの読み込み

とりあえず10ファイル全てを読み込みます。なんか汚い。

#shapefile
pj<-CRS("+proj=longlat +datum=WGS84")
Chuo_row<- readShapePoly("data/A002005212010DDSWC01101/h22ka01101",proj4string = pj)
kita_row<-readShapePoly("data/A002005212010DDSWC01102/h22ka01102",proj4string = pj)
higashi_row<-readShapePoly("data/A002005212010DDSWC01103/h22ka01103",proj4string = pj)
shiroishi_row<-readShapePoly("data/A002005212010DDSWC01104/h22ka01104",proj4string = pj)
toyohira_row<-readShapePoly("data/A002005212010DDSWC01105/h22ka01105",proj4string = pj)
minami_row<-readShapePoly("data/A002005212010DDSWC01106/h22ka01106",proj4string = pj)
nishi_row<-readShapePoly("data/A002005212010DDSWC01107/h22ka01107",proj4string = pj)
atsubetsu_row<-readShapePoly("data/A002005212010DDSWC01108/h22ka01108",proj4string = pj)
teine_row<-readShapePoly("data/A002005212010DDSWC01109/h22ka01109",proj4string = pj)
kiyota_row<-readShapePoly("data/A002005212010DDSWC01110/h22ka01110",proj4string = pj)

元のシェープファイルには各小地域の人口等、属性テーブルが含まれるのでSpatialPolygonsDataFrameとして読み込まれます。
10個のオブジェクトは完全にバラバラなのでこんな感じ。
小地域データなので各区の中の番地ごとにPolygonが分かれ、ID付与されています。

f:id:WAFkw:20161025194358p:plain

小さな都市を作る

前も同じようなことをしたので割愛。
wafdata.hatenablog.com

何のことはない、これを
f:id:WAFkw:20161025194358p:plain

こうするだけ。
f:id:WAFkw:20161025194703p:plain

maptools::gpclibPermit()
Chuo_u<-maptools::unionSpatialPolygons(Chuo_row,IDs=rep(1,times=nrow(Chuo@data)))
kita_u<-maptools::unionSpatialPolygons(kita_row,IDs=rep(2,times=nrow(kita_row@data)))
higashi_u<-maptools::unionSpatialPolygons(higashi_row,IDs=rep(3,times=nrow(higashi_row@data)))
shiroishi_u<-maptools::unionSpatialPolygons(shiroishi_row,IDs=rep(4,times=nrow(shiroishi_row@data)))
toyohira_u<-maptools::unionSpatialPolygons(toyohira_row,IDs=rep(5,times=nrow(toyohira_row@data)))
minami_u<-maptools::unionSpatialPolygons(minami_row,IDs=rep(6,times=nrow(minami_row@data)))
nishi_u<-maptools::unionSpatialPolygons(nishi_row,IDs=rep(7,times=nrow(nishi_row@data)))
atsubetsu_u<-maptools::unionSpatialPolygons(atsubetsu_row,IDs=rep(8,times=nrow(atsubetsu_row@data)))
teine_u<-maptools::unionSpatialPolygons(teine_row,IDs=rep(9,times=nrow(teine_row@data)))
kiyota_u<-maptools::unionSpatialPolygons(kiyota_row,IDs=rep(10,times=nrow(kiyota_row@data)))

王国を作るという野望のため、
結合後のIDは各区ごとにユニークになるように振っておく。
ここで各オブジェクトはSpatialPolygonsになる。

王国をつくる

いざバラバラのオブジェクトを一つのSpatialPolygonに。
これを

f:id:WAFkw:20161025194703p:plain


こうする。

f:id:WAFkw:20161025195753p:plain

これをやるためには、Spatialオブジェクトのrbind、ことmaptools::spRbind()を使う。
今回はSpatialPolygonsとSpatialPolygonsの合わせ技だけど、関数としては以下の組み合わせに対応出来るらしい。

引数1 引数2
SpatialPoints SpatialPoints
SpatialPointsDataFrame SpatialPointsDataFrame
SpatialLines SpatialLines
SpatialLinesDataFrame SpatialLinesDataFrame
SpatialPolygons SpatialPolygons
SpatialPolygonsDataFrame SpatialPolygonsDataFrame

(ちなみに*DataFlame系の場合は同じ属性テーブルを有する場合に限る。ちょっと試せてはいない。)


でも....うっすら気付いてたけどこれって.....と思って関数ヘルプを眺めていたら

spRbind-methods can bind 2 objects, whereas rbind-methods can bind multiple object

10個一気に繋げたいんだけど....なあ.....
ごにゃごにゃやってみたけど結局以下で愚直に王国を作った。

Sapporo<-spRbind(Chuo_u,kita_u) %>% 
  spRbind(.,higashi_u) %>% 
  spRbind(.,shiroishi_u) %>% 
  spRbind(.,toyohira_u) %>% 
  spRbind(.,minami_u) %>% 
  spRbind(.,nishi_u) %>% 
  spRbind(.,atsubetsu_u) %>%
  spRbind(.,teine_u) %>%
  spRbind(.,kiyota_u)

最終的に、1つのSpatialPolygons(内部に区ごとの10個のPolygonを有する)が出来た。

str(Sapporo)

>Formal class 'SpatialPolygons' [package "sp"] with 4 slots
  ..@ polygons   :List of 10
  .. ..$ :Formal class 'Polygons' [package "sp"] with 5 slots
  .. .. .. ..@ Polygons :List of 1
  .. .. .. .. ..$ :Formal class 'Polygon' [package "sp"] with 5 slots
  .. .. .. .. .. .. ..@ labpt  : num [1:2] 141 43
  .. .. .. .. .. .. ..@ area   : num 0.00513
  .. .. .. .. .. .. ..@ hole   : logi FALSE
  .. .. .. .. .. .. ..@ ringDir: int 1
  .. .. .. .. .. .. ..@ coords : num [1:1267, 1:2] 141 141 141 141 141 ...
  .. .. .. .. .. .. .. ..- attr(*, "dimnames")=List of 2
  .. .. .. .. .. .. .. .. ..$ : NULL
  .. .. .. .. .. .. .. .. ..$ : chr [1:2] "x" "y"
  .. .. .. ..@ plotOrder: int 1
  .. .. .. ..@ labpt    : num [1:2] 141 43
  .. .. .. ..@ ID       : chr "1"
  .. .. .. ..@ area     : num 0.00513
  .. ..$ :Formal class 'Polygons' [package "sp"] with 5 slots
  .. .. .. ..@ Polygons :List of 1
  .. .. .. .. ..$ :Formal class 'Polygon' [package "sp"] with 5 slots
  .. .. .. .. .. .. ..@ labpt  : num [1:2] 141.4 43.1
  .. .. .. .. .. .. ..@ area   : num 0.00701
  .. .. .. .. .. .. ..@ hole   : logi FALSE
  .. .. .. .. .. .. ..@ ringDir: int 1
  .. .. .. .. .. .. ..@ coords : num [1:1493, 1:2] 141 141 141 141 141 ...
  .. .. .. .. .. .. .. ..- attr(*, "dimnames")=List of 2
  .. .. .. .. .. .. .. .. ..$ : NULL
  .. .. .. .. .. .. .. .. ..$ : chr [1:2] "x" "y"
  .. .. .. ..@ plotOrder: int 1
  .. .. .. ..@ labpt    : num [1:2] 141.4 43.1
  .. .. .. ..@ ID       : chr "2"
  .. .. .. ..@ area     : num 0.00701
  .. ..$ :Formal class 'Polygons' [package "sp"] with 5 slots
  .. .. .. ..@ Polygons :List of 1
  .. .. .. .. ..$ :Formal class 'Polygon' [package "sp"] with 5 slots
  .. .. .. .. .. .. ..@ labpt  : num [1:2] 141.4 43.1
  .. .. .. .. .. .. ..@ area   : num 0.0063
  .. .. .. .. .. .. ..@ hole   : logi FALSE
  .. .. .. .. .. .. ..@ ringDir: int 1
  .. .. .. .. .. .. ..@ coords : num [1:744, 1:2] 141 141 141 141 141 ...
  .. .. .. .. .. .. .. ..- attr(*, "dimnames")=List of 2
  .. .. .. .. .. .. .. .. ..$ : NULL
  .. .. .. .. .. .. .. .. ..$ : chr [1:2] "x" "y"
  .. .. .. ..@ plotOrder: int 1
  .. .. .. ..@ labpt    : num [1:2] 141.4 43.1
  .. .. .. ..@ ID       : chr "3"
  .. .. .. ..@ area     : num 0.0063
#・・・長いので省略

これでどんどん領地を拡大していけばかのアッバース朝みたいな国を作れる。

おわり

  • 何に使うのかは秘密。
  • 出だし何も考えずに、各オブジェクト内結合で全部ID=1にしてたら"non-uniqueID"だよって怒られた。そりゃそうだ。
  • spCbind()もある。
  • 冷静に考えたらウマイヤ朝とかモンゴル帝国とかの方が大きいので目標として適切ではない。

札幌は雪が降ったので引きこもりには最適な環境です。