【Python】世界各国の人口データをスクレイピングして取得する

Pythonで世界各国の人口データを取得する

先日株価分析に人口データを用いたいと思いまして、pandas-datareaderとかでうまいこと取得できないかなーと色々検索していたのですが、国別にうまく取得できるサイトが中々見つからず苦労していたのですが、先日目途が立ったのでとりあえずまとめてみました。

今回は世界経済のネタ帳というサイトからPythonを使ったスクレイピングでアジア各国の人口データとGDPを取得してみます。

流れとしては、requestsでスクレイピングしてBeautifulSoupでHTMLから必要なデータを抽出。Pandasで整形してMatplotlibで描画といった感じになります。

関連記事:PythonでのWebスクレイピングには「requests」がめっちゃ便利という話

関連記事:【Python】「Beautiful Soup」でスクレイピングしたhtmlデータを解析する

関連記事:【Python】Matplotlibでのグラフ作成の基本をわかりやすく解説する

<実行環境>

  • Windows10
  • Python3.7
  • JupyterLab

# ライブラリの呼び出し
import requests
import json
from bs4 import BeautifulSoup
import pandas as pd
import matplotlib.pyplot as plt
%matplotlib inline

def get_tabledata(url='https://ecodb.net/ranking/old/area/A/imf_ngdpd', start=1980, end=2018):
    """
    世界経済のネタ帳からスクレイピングでデータを取得する関数
    url{str} : forでループさせる大元のURL
    start {int/str} : 開始年数(1980年がより前のデータはなさそう)
    end {int/str} : 終了年数(現在の年数-2、前年のデータはURLの仕様が少し違うので、別でスクレピングする必要あり)
    """
    data_dict = {}
    for year in range(start, end):
        # 対象ページのHTMLデータを取得&BS4形式に変換
        res = requests.get(f'{url}_{year}.html')
        data = BeautifulSoup(res.text,'html.parser')
        # htmlの中からtableタグを抽出する
        data_table = data.find('table')
        # テーブルから1列ずつ国名と数値を抜き出す
        country_dict = {}
        for row in range(len(data_table.find_all('tr'))):
            country = data_table.find_all('tr')[row]
            # 最初の1と2はアジア合計と世界合計の列で他とタグが若干異なっているのでIF文で処理
            if row == 1:
                asia_sum_ = country.find('td', class_='value').text.replace(',', '').replace("'", '')
                # 辞書にKEYと値を追加する
                country_dict['アジア合計'] = float(asia_sum_)
            if row == 2:
                world_sum_ = country.find('td', class_='value').text.replace(',', '').replace("'", '')
                # 辞書にKEYと値を追加する
                country_dict['世界合計'] = world_sum_
            # それ以外の国名の列は同じように処理
            else:
                try:
                    # 国名とGDPを取得して辞書に追加していく
                    country_name = country.find('td', class_='name tap').text.replace('\n', '').replace('\xa0', '')
                    gdp = country.find('td', class_='value value_bar_chart').text.replace(',', '')
                    country_dict[country_name] = float(gdp)
                except Exception as e:
                    pass
        # 各年代のアジア各国のデータ数値({国名:数値}の辞書データを辞書の中に追加する
        data_dict[str(year)] = country_dict
    return data_dict


# 関数を実行してデータを取得する
people_data = get_tabledata(url='https://ecodb.net/ranking/old/area/A/imf_lp_', start=1980, end=2018)
gdp_data = get_tabledata(url='https://ecodb.net/ranking/old/area/A/imf_ngdpd_', start=1980, end=2018)

このコードだとfor文で回しているURLの仕様上で最新の年のデータが取得できません。いずれgitに完成版をアップロードするつもりですが、これでも40年分くらいのデータは集められるので、十分使えると思います。

<実行結果>は↓のような感じ

これをデータフレームに整形します

# アジアの国のリストを作成する
asia_list = list(gdp_data['1980'].keys())

people_dict = {}
gdp_dict = {}

for country in asia_list:
    p_data, g_data = [], []
    for year in people_data.keys():
        try:
            p_data.append(people_data[year][country])
        except:
            p_data.append('NaN')
    people_dict[country] = p_data
    for year in gdp_data.keys():
        try:
            g_data.append(gdp_data[year][country])
        except:
            g_data.append('NaN')
    gdp_dict[country] = g_data


# 辞書からデータフレームに変換する
df_people = pd.DataFrame(people_dict.values(), index=people_dict.keys())
df_people.columns = range(1980, 2018)
df_gdp = pd.DataFrame(gdp_dict.values(), index=gdp_dict.keys())
df_gdp.columns = range(1980, 2018)

# csv出力
df_people.to_csv('asia_population.csv', encoding='SJIS')
df_gdp.to_csv('asia_gdp.csv', encoding='SJIS')

次はこれをMatplotlibでプロットします。

# データをJupyterNotebookでプロットする場合 #
from pylab import rcParams
rcParams['figure.figsize'] = 10, 20

for i in df_gdp.index[2:]:
    try:
        plt.plot(df_gdp.loc[i], label=i)
    except:
        pass
plt.title('アジア各国の年代別GDP推移')
plt.grid(which='both')
plt.legend()
plt.show()

<実行結果>

人口とGDP共に中国の伸びがすごいですね(小並感)

他にもインド・インドネシア・タイ・ベトナム辺りも伸びてきています。

関連記事:【Python】CoinGeckoのAPIからビットコイン・アルトコインの価格データを取得する

関連記事:【Python】TwitterのAPIを簡単操作できる「Tweepy」の使い方

関連記事:【Python】Quandlから上場企業の株価データを取得する

関連記事:【Python】pandasで日経平均の株価データをスクレイピングする

プログラミングの独学はとても難しい


プログラミングは小学校の義務教育にも導入され始めており、これから社会人として生きていく上でプログラミングはもはや出来て当たり前、出来なれば論外というエクセルレベルの必須スキルになりつつあります。そしてそういう話を聞いて参考書なりを購入して独学でプログラミング勉強しようと思っている人も少なくないでしょう。しかしプログラミングを独学で勉強し始めようと思うものの



・「分からない箇所で詰まって挫折してしまった」

・「勉強する時間が足りない」

・「ネットの記事だと情報が断片的でよくわからない」

・「コードのエラーの原因が分からない」



という壁にぶち当たって、プログラミングの勉強を止めてしまう方が少なくありません。独学でプログラミングを勉強してる時間のほとんどはつまづいている時間です。実際僕も最初のころ独学でプログラミングを勉強していた頃はエラーの原因が分からず丸1日を不意にしてしまった・・・そんな苦い経験がありました。それで僕は一度はプログラミングの学習を諦めてしまいましたが、就活で現実を知る中で



「プログラミングを勉強して、いずれフリーランスとして自由な生き方がしたい」

「エンジニアとして若いうちから高収入を得たい」



という強い気持ちから一念発起して「侍エンジニアのwebサービスコース」に申し込み、プロのエンジニアの方に対面でマンツーマンでPythonによるWebサービス作り方とWeb技術の基本を教えてもらい、ようやくプログラミングが理解でき、今ではエンジニアとしてそこそこの暮らしができるようになりました。





侍エンジニアでは、とりあえずプログラミングやインターネットの基本を知っておきたい人から、HTML・cssなどでWebサイトやWebアプリを作ってみたい人やPythonを勉強してデータサイエンティストやAIエンジニアになりたい人まで幅広いニーズに応えた様々なコースが用意されています。



IT業界と言ってもエンジニアの仕事はプログラミング言語次第でサーバーから機械学習・ディープラーニングまで多種多様ですし、侍エンジニアの無料レッスン(カウンセリング)を受けてみて、自分のやりたいITの仕事は何なのか?を見つけるのがエンジニアへの第一歩になります。ちなみに今侍エンジニアの無料レッスンを受けると1000円分のAmazonギフト券がもらえるので、試しに受けてみるだけもお得です。


自分は半端に独学やオンラインスクールで勉強して金と時間を無駄にするくらいなら、リアルのプログラミングスクールに通ってしっかりプログラミングを勉強した方がいいと思います。ちなみに今、侍エンジニアに申し込むと、25歳以下の学生の方であれば、受講料が20%OFFになるので超お得です。


そして、プログラミングは大勢で授業を受けたり漫然とオンライン学習をするよりも自分が分からない箇所をピンポイントでプロの講師に直接質問して、ちゃんと納得するというスタイルの方がお金は確かに少し掛かりますが、独学で学ぶよりも絶対にモノになります。


シェアする

  • このエントリーをはてなブックマークに追加

フォローする

   侍エンジニア塾       
侍エンジニアの無料体験レッスンを予約する -->