新型コロナの感染状況(2020/4/25)

前回の記事では、新型コロナの感染状況データをPythonでスクレイピングしてPostGISへ収容し、OpenJUMP上の地図にグラフ表示しました。
今回は、オラクルデータベースを使って今週分のデータを処理します。

今回実現する仕組み

今回は、Pythonでスクレイピングしたデータをオラクルへ取り込みSQLで結合します。
今回実現する仕組みを以下に図示します。

今回実現する仕組み

オラクルへのインポート

世界地図のシェープファイルを、”Oracle Map Builder”ユーティリティを使ってオラクルへ取り込みます。
”Oracle Map Builder”のインストールや取り込みの詳細は、以下の記事を参考にしてください。

”Oracle Map Builder”ユーティリティを起動しオラクルへ接続後、世界地図のシェープファイルをインポートします。SRID(EPSGコードと同じ)は、”4326”(WGS84緯度経度)を指定してください。

取り込みは1分足らずで終了します。OpenJUMPの”DB Query”を使って地図表示すると、以下のようになります。

オラクルに取り込んだ世界地図をOpenJUMPに表示

WHOデータをオラクルへインポート

PythonでスクレイピングしたWHOデータ(CSV)をオラクルへインポートします。
前回のPostGISと同様、週ごとにテーブルを分ける方法としました。
Pythonによるスクレイピングの詳細は以下の記事を参考にしてください。

WHOデータをインポートするテーブルの作成は、SQL*Plusなどから以下のSQLを発行します。

(4月26日のWHOデータ収容テーブルの作成SQL)
create table who0426(
Country varchar2(50),
TCases number,
NCases number,
TDeaths number,
NDeaths number,
TRecovered number,
ACases number,
Critical number,
TC1Mpop number,
D1Mpop number,
TTests number,
T1Mpop number,
Continent varchar2(50)
);

今回は、CSVファイルをSQL*Loaderを使ってオラクルへ読み込みます。(SQL DeveloperやA5SQLなどのGUIツールでも可能です。)
SQL*Loaderの制御ファイルは、以下のようになります。

OPTIONS(SKIP=1)
LOAD DATA
INFILE ‘stat0426.csv’
BADFILE ‘stat0426.bad’
TRUNCATE
INTO TABLE WHO0426
FIELDS TERMINATED BY “,”
TRAILING NULLCOLS(
 COUNTRY,TCASES,NCASES,TDEATHS,NDEATHS,TRECOVERED,ACASES,
 CRITICAL,TC1MPOP,D1MPOP,TTESTS,T1MPOP,CONTINENT
)

作成したテーブルにCSVファイルのデータを取り込みには、sqlloaderコマンドを使います。コマンドのイメージは以下になります。

>sqlldr takamoto/takamoto@sakuradb control=.\who0426.ctl
SQL*Loader: Release 12.2.0.1.0 – Production on 日 4月 26 17:59:42 2020
Copyright (c) 1982, 2017, Oracle and/or its affiliates. All rights reserved.
使用パス: 従来型
コミット・ポイントに達しました – 論理レコード件数64
コミット・ポイントに達しました – 論理レコード件数128
コミット・ポイントに達しました – 論理レコード件数192
コミット・ポイントに達しました – 論理レコード件数212
表WHO0426:
212 行は正常にロードされました。
確認するログ・ファイル:
who0426.log
ロードの詳細を参照してください。

A5SQLでデータを確認すると、以下のようになります。うまく取り込めました。

A5SQLで取り込んだテーブルを表示

同様にして、残り3週間分のWHOデータをオラクルへ読み込みました。

SQL> select * from tab;
TNAME TABTYPE CLUSTERID
——————— ———- ——————
GAIKU TABLE
KOKUSEI TABLE
NATURALEARTH TABLE
WHO0404 TABLE
WHO0411 TABLE
WHO0418 TABLE
WHO0426 TABLE

OpenJUMPを使ってグラフ表示

ここからが本題のグラフ表示です。
3週間分のグラフをOpenJUMPのDB Query(SQL)を使って表示します。
地図と発行SQLの両方を見ていきます。

1.感染者数(総数)
感染者数は、ヨーロッパが落ち着きアメリカが伸びていることに変化はないようです。ロシアやブラジルも伸びています。
メディアの報道通り、感染者数というのは、検査数との相関も強いので、このグラフが感染の実態を表しているかについては疑問もあります。

感染者数の推移

発行したSQLは、世界地図に3週間分のWHOデータ(3テーブル)を外部結合しています。

(発行SQL)
select na.name_en en_name,na.name_ja ja_name,w1.tcases w1,w2.tcases w2,w3.tcases w3,w4.tcases w4,na.geometry geom
from naturalearth na
left outer join who0404 w1 on (na.name_en=w1.country)
left outer join who0411 w2 on (na.name_en=w2.country)
left outer join who0418 w3 on (na.name_en=w3.country)
left outer join who0426 w4 on (na.name_en=w4.country);

2.100万人あたりの感染者数
100万人あたりの感染者数を確認すると、ヨーロッパも終息しておらず周辺諸国へ広がっているように見えます。
先週からの傾向ですが、中東、南米が増加率、増加エリアともに増加傾向が明確になってきています。

100万人あたりの感染者数

SQLは、オラクルの方言を使ってみました。結合側のカラム名に(+)を記述することで、外部結合となります。

(発行SQL)
select na.name_en en_name,na.name_ja ja_name,w1.tc1mpop w1,w2.tc1mpop w2,w3.tc1mpop w3,w4.tc1mpop w4,na.geometry geom
from naturalearth na,who0404 w1,who0411 w2,who0418 w3,who0426 w4
where na.name_en=w1.country(+) and
na.name_en=w2.country(+) and
na.name_en=w3.country(+) and
na.name_en=w4.country(+);

3.100万人あたりの死亡者数
次に、100万人あたりの死亡者数を確認しましょう。
ヨーロッパ、北米を中心に収束しているとはいえないように見えます。

ヨーロッパ中心部にフォーカスします。先週報告したベルギーの伸びには変化がないように見えます。
医療体制や感染者の絶対数などの要素があるので一概にはいえませんが、死亡率に関してはヨーロッパ中心部からの広がりは確認できません。

ヨーロッパ周辺国への広がりは著しくはない

(発行SQL)
select na.name_en en_name,na.name_ja ja_name,w1.d1mpop w1,w2.d1mpop w2,w3.d1mpop w3,w4.d1mpop w4,na.geometry geom
from naturalearth na,who0404 w1,who0411 w2,who0418 w3,who0426 w4
where na.name_en=w1.country(+) and
na.name_en=w2.country(+) and
na.name_en=w3.country(+) and
na.name_en=w4.country(+);

アジアに絞ってみてみましょう。
中東、特にイランが圧倒的でトルコやイスラエルなどヨーロッパに近い国々の死亡率が高くなっています。
メディアでも流れていますが、ヨーロッパとアジアンではウィルスの種類が異なる可能性もあります。

アジア西部の死亡率が高い

(発行SQL)
select na.name_en en_name,na.name_ja ja_name,w1.t1mpop w1,w2.t1mpop w2,w3.t1mpop w3,na.geom geom
from naturalearth na
left outer join who0404 w1 on (na.name_en=w1.country)
left outer join who0411 w2 on (na.name_en=w2.country)
left outer join who0418 w3 on (na.name_en=w3.country)
where na.region_un=’Asia’;

4.100万人あたりの検査数
最後に100万人あたりの検査数を確認しましょう。
人口の少ない国以外は検査数が高いとはいえないようです。

100万人あたりの検査数は人口の少ない国以外は高くない

まとめ

今回は、以下を試してみました。
1.世界地図とスクレイピングしたデータのオラクルへの取り込み
2.OpenJUMPによるグラフ表示(先週までとの比較)

グラフを見ていると、感染はまだまだ収束していないように見えます。
巷では在宅ワークやWeb会議など、変化に適応した動きも多く見られます。
ただ、この状況があと2か月続くと、様々な事業での資金ショートが深刻になってくると感じています。

1日も早い収束を祈るばかりです。