RでWebページ上のテーブルを読み込み(ウェブスクレイピング)
最近RでWebページ上のテーブルを読み込む方法を知ったのでメモします。
テストデータ
テストデータとして、気象庁が提供している過去の気象データを使います。
www.data.jma.go.jp
今回は2019年1月1日の東京都における気象データ(10分ごとの値)を読み込む対象にします。
テーブルの読み込み(失敗)
XMLパッケージのreadHTMLTable()関数で簡単に読み込めるということで試してみると…
> library(XML) > > url <- "https://www.data.jma.go.jp/obd/stats/etrn/view/10min_s1.php?prec_no=44&block_no=47662&year=2019&month=1&day=1&view=" > > #headerオプションでテーブルにヘッダーがあるかを指定 > #stringsAsFactorsオプションでcharacter列をfactor型で返すかを指定 > read <- readHTMLTable(url, header = TRUE, stringsAsFactors = FALSE) Warning message: XML content does not seem to be XML: 'https://www.data.jma.go.jp/obd/stats/etrn/view/10min_s1.php?prec_no=44&block_no=47662&year=2019&month=1&day=1&view='
失敗しました。何でだ!と思って調べるとURLの「https」部分を「http」に書き換える必要があるようです。
テーブルの読み込み(再挑戦)
「http」に書き換えて実行すると…
> library(XML) > > url <- "http://www.data.jma.go.jp/obd/stats/etrn/view/10min_s1.php?prec_no=44&block_no=47662&year=2019&month=1&day=1&view=" > > #headerオプションでテーブルにヘッダーがあるかを指定 > #stringsAsFactorsオプションでcharacter列をfactor型で返すかを指定 > read <- readHTMLTable(url, header = TRUE, stringsAsFactors = FALSE) > read $`NULL` NULL $`NULL` NULL $`NULL` NULL $`NULL` NULL $tablefix1 V1 V2 V3 V4 V5 V6 V7 V8 V9 V10 V11 1 現地 海面 平均 風向 最大瞬間 風向 <NA> <NA> <NA> <NA> <NA> 2 00:10 1023.4 1026.5 -- 2.3 57 1.2 北西 2.4 西北西 ~省略~ 90 14:50 1017.7 1020.7 -- 9.8 42 3.0 南南東 7.2 南南東 10 [ reached 'max' / getOption("max.print") -- omitted 55 rows ] $`NULL` NULL
読み込みはできましたがページ内に6つテーブルがあると認識されたため、欲しいテーブル(tablefix1)以外にも空テーブルが読み込まれています。
これはテーブルを指定して別の変数に代入する(例:table <- read$tablefix1)か、readHTMLTable()関数のwhichオプション(which = 整数値)であらかじめテーブルを指定しておくことで解決できます。
また、headerオプションを指定しましたが列名がうまく設定されていません。
これはこのデータの列名が複数行、複数列にまたがっていてうまく読み込めないためですが、今回は数が多くないので後で手動で設定します。
テーブルの読み込み(再再挑戦)
修正・追記して実行しました。
> library(XML) > library(dplyr) > > url <- "http://www.data.jma.go.jp/obd/stats/etrn/view/10min_s1.php?prec_no=44&block_no=47662&year=2019&month=1&day=1&view=" > > #headerオプションでテーブルにヘッダーがあるかを指定 > #stringsAsFactorsオプションでcharacter列をfactor型で返すかを指定 > #whichオプションで読み込むテーブルを指定 > #skip.rowsオプションで無視する行を指定 > read <- readHTMLTable(url, header = FALSE, stringsAsFactors = FALSE, which = 5, skip.rows = 1:2) > > table <- read %>% + rename(時分 = V1, 気圧_海面 = V2, 気圧_現地 = V3, + 降水量 = V4, 気温 = V5, 相対湿度 = V6, + 風速_平均 = V7, 風向_平均 =V8, 風速_最大 = V9, + 風向_最大 = V10, 日照時間 = V11) > table 時分 気圧_海面 気圧_現地 降水量 気温 相対湿度 風速_平均 風向_平均 風速_最大 風向_最大 日照時間 1 00:10 1023.4 1026.5 -- 2.3 57 1.2 北西 2.4 西北西 2 00:20 1023.5 1026.6 -- 1.8 59 1.1 西北西 2.3 西北西 ~省略~ 90 15:00 1017.7 1020.7 -- 9.2 45 4.2 南南東 7.0 南東 10 [ reached 'max' / getOption("max.print") -- omitted 54 rows ]
テーブルとして読み込めました。
一番のポイントは
> read <- readHTMLTable(url, header = FALSE, stringsAsFactors = FALSE, skip.rows = 1:2, which = 5)
ですね。
「header = FALSE」、「skip.rows = 1:2」で列名部分(1~2行目)を無視し、
「which = 5」でページ内の5番目のテーブルを読み込んでいます。
後はdplyrのrename()関数で列名を設定していますが、数値が入るはずの「降水量」に文字列「--」が入っていたりするのでもう少し加工は必要ですね。
まとめ
readHTMLTable()関数についてまとめると以下の通りです。
- XMLパッケージのreadHTMLTable()関数でWebページ上のテーブルを読み込み可能
- URLが「https」から始まっていると読み込めないため、「http」への書き換えが必要
- headerオプションでテーブルにヘッダーがあるかを指定可能
- stringsAsFactorsオプションでcharacter列をfactor型で返すかを指定可能
- whichオプションで読み込むテーブルを指定可能
- skip.rowsオプションで無視する行を指定可能
詳細は以下のページをご確認ください(英語です)。
readHTMLTable function | R Documentation
以上です。