いま再びのPython入門

辻 真吾(@tsjshg)

2015.12.9 みんなのPython勉強会 #7

自己紹介

  • 東京大学先端科学技術研究センター 特任助教
  • 工学部(応用数学)
  • 修士出て当時社員5人のIT系ベンチャー
  • 博士課程にもどって、バイオインフォマティクス
  • 40歳にして道に惑う
  • C++やJavaが好きだった頃もありますが、最近はほぼすべてPython

Pythonには、勢いがある!

この1年は上昇トレンドだった。

なぜ勢いが?

Pythonの良いところ

  • There should be one-- and preferably only one --obvious way to do it.(import this)
  • なにかするとき、選択肢が1つ、出来ればそれが唯一の方法であること
  • 他人(玄人)が書いたコードがあまり苦労無く読める
  • バッテリー同梱(標準モジュールが充実)

さらに

ビッグデータ、機械学習、統計処理といった分野で、フリーではRとの2択になりつつある点

Pythonのインストール

https://www.continuum.io/ からAnacondaを入れて一気に環境を整え、conda update conda; conda update anacondaで定期的にupdate。Anacondaになければ、pipで。仮想環境の構築(virtualenvやpyenv)もcondaで管理できます。

2 or 3

  • はじめるなら3で、理由があるなら2でもいいですが、2.7系が良いです。
  • 混乱がありましたが、マルチバイト文字を最初から考慮している3は良いです。

Jupyter notebook

  • 旧IPython notebookがおすすめ
  • コマンドラインから ipython notebook(jupyter notebook)で起動
  • Webブラウザ内にコードと結果(画像を含む)などを一括管理できる
  • このスライドはipython notebookで作っています。

実際にコードを見ていきます

In [10]:
# 好評の便利な標準モジュールから
from collections import Counter
c = Counter(['cat','cat','snake','fox','cat','lion','cat','fox'])
print('Cat is {}'.format(c['cat']))
print('Dog is {}'.format(c['dog']))

# 頻出するものをとってこられる
c.most_common(3)
Cat is 4
Dog is 0
Out[10]:
[('cat', 4), ('fox', 2), ('snake', 1)]
In [13]:
# 条件にあったファイルの一覧を取得
import glob
glob.glob('*.png')
Out[13]:
['CFnzV5cW0AA36JB.png',
 'continuum.png',
 'data_1.png',
 'encode1.png',
 'encode2.png',
 'excel_sample.png',
 'hc.png',
 'mini_japan.png',
 'num_data.png',
 'py_tiobe.png',
 'pypl.png',
 'temp.png',
 'tiobe.png',
 'tiobe_head.png',
 'top_header_logo.png']
In [14]:
# 正規表現も使えます
glob.glob('[e,n]*.png')
Out[14]:
['encode1.png', 'encode2.png', 'excel_sample.png', 'num_data.png']
In [34]:
# この表をとってきます。
import pandas as pd
_data = pd.read_html('https://ja.wikipedia.org/wiki/%E7%B5%8C%E6%B8%88%E5%8D%94%E5%8A%9B%E9%96%8B%E7%99%BA%E6%A9%9F%E6%A7%8B')
print('_dataは {}\n要素は {}\n長さは{}'.format( type(_data), type(_data[0]), len(_data) ))
_dataは <class 'list'>
要素は <class 'pandas.core.frame.DataFrame'>
長さは3
In [31]:
# 戻り値のリストの2つ目に目的の表が入っています。
print(type(_data[1]))
_data[1]
<class 'pandas.core.frame.DataFrame'>
Out[31]:
0 1 2 3 4 5 6 7 8 9 10 11 12
0 面積[5] (km2) 2010 人口[5] 2011 国内総生産 (PPT)[5] (Intl. $) 2011 国内総生産 (一人当りPPT)[5] (Intl. $) 2011 所得不平等[5] 1993-2009 (直近値) 人間開発[6] 2011 失敗国家 (FSI)[7] 2012 腐敗認識[8] 2011 経済自由指数[9] 2011 世界平和度[10] 2012 世界報道自由[11] 2011/2012 民主主義[12] 2011
1 オーストラリア 7741220 22620600 892739612442 39466 35.2 0.929 29.2 8.8 82.5 1.494 4.00 9.22
2 オーストリア 83870 8419000 354628026975 42122 29.2 0.885 27.5 7.8 71.9 1.328 -8.00 8.49
3 ベルギー 30530 11008000 425276544386 38633 33.0 0.886 33.5 7.5 70.2 1.376 -2.00 8.05
4 カナダ 9984670 34482779 1397983465565 40541 32.6 0.908 26.8 8.7 80.8 1.317 -5.67 9.08
5 チリ 756090 17269525 295740683117 17125 52.1 0.805 43.5 7.2 77.4 1.616 29.00 7.54
6 チェコ 78870 10546000 273662146638 25949 25.8 0.865 39.5 4.4 70.4 1.396 -5.00 8.19
7 デンマーク 43090 5574000 228616450630 41015 24.7 0.895 23.0 9.4 78.6 1.239 -5.67 9.52
8 エストニア 45230 1340000 30024533557 22406 36.0 0.835 47.5 6.4 75.2 1.715 -9.00 7.61
9 フィンランド 338420 5387000 202446166977 37581 26.9 0.882 20.0 9.4 74.0 1.348 -10.00 9.06
10 フランス 549190 65436552 2302945703407 35194 32.7 0.884 33.6 7.0 64.6 1.710 9.50 7.77
11 ドイツ 357120 81726000 3221135411591 39414 28.3 0.905 31.7 8.0 71.8 1.424 -3.00 8.34
12 ギリシャ 131960 11304000 303987090775 26892 34.3 0.861 50.4 3.4 60.3 1.976 24.00 7.65
13 ハンガリー 93030 9971000 216752108474 21738 31.2 0.816 48.3 4.6 66.6 1.476 10.00 7.04
14 アイスランド 103000 319000 11839614943 37115 NaN 0.898 29.1 8.3 68.2 1.113 -7.00 9.65
15 アイルランド 70280 4487000 186848293971 41642 34.3 0.908 26.5 7.5 78.7 1.328 -4.00 8.56
16 イスラエル 22070 7765700 217492394269 28007 39.2 0.888 N/Aa 5.8 68.5 2.842 31.25 7.53
17 イタリア 301340 60770000 1979219444356 32569 36.0 0.874 45.8 3.9 60.3 1.690 19.67 7.74
18 日本 377940 127817277 4381290159229 34278 24.9 0.901 43.5 8.0 72.8 1.326 -1.00 8.08
19 韓国 99900 49779000 1503604062678 30206 31.6 0.897 37.6 5.4 69.8 1.734 12.67 8.06
20 ルクセンブルク 2590 517000 45902664436 88787 30.8 0.867 25.5 8.5 76.2 1.341c -7.00 8.88
21 メキシコ 1964380 114793341 1760946368455 15340 48.3 0.770 73.6 3.0 67.8 2.445 72.67 6.93
22 オランダ 41540 16696000 723585287472 43339 30.9 0.910 28.1 8.9 74.7 1.606 -9.00 8.99
23 ニュージーランド 267710 4405200 131,507,519,463c 30,108c 36.2 0.908 25.6 9.5 82.3 1.239 -5.33 9.26
24 ノルウェー 323780 4952000 282720915051 57092 25.8 0.943 23.9 9.0 70.3 1.480 -10.00 9.80
25 ポーランド 312680 38216000 813292967101 21281 34.1 0.813 44.3 5.5 64.1 1.524 -0.67 7.12
26 ポルトガル 92090 10637000 270649574742 25444 38.5 0.809 34.2 6.1 64.0 1.470 5.33 7.81
27 スロバキア 49040 5440000 132919954401 24434 26.0 0.834 47.4 4.0 69.5 1.590 0.00 7.35
28 スロベニア 20270 2052000 56573135942 27570 31.2 0.884 34.0 5.9 64.6 1.330 9.14 7.76
29 スペイン 505370 46235000 1511951580566 32701 34.7 0.878 42.8 6.2 70.2 1.548 9.75 8.02
30 スウェーデン 450300 9453000 391800201817 41447 25.0 0.904 21.3 9.3 71.9 1.419 -5.50 9.50
31 スイス 41280 7907000 378088821911 47817 33.7 0.903 23.3 8.8 81.9 1.349 -6.20 9.09
32 トルコ 783560 73639596 1243426691409 16885 39.0 0.699 76.6 4.2 64.2 2.344 70.00 5.72
33 イギリス 243610 62641000 2287071689227 36511 36.0 0.863 35.3 7.8 74.5 1.609 2.00 8.16
34 アメリカ合衆国 9831510 311591917 15094000000000 48442 40.8 0.910 34.8 7.1 77.8 2.058 14.00 8.11
35 zzzOECDb 36137530 1245198487 43550669285973 34,993d 33.3 0.871 36.6 6.9 71.7 1.590 6.44 8.23
In [30]:
# 整形しましょう。
# 表の本体(数値データ部分)のDataFrameを切り出す
data = _data[1].loc[1:,1:] 

# 列名(最初の1行)を付ける
data.columns = _data[1].loc[0,1:] 

# 行の名前(index)を付ける(valuesにしなくてもOK)
data.index = _data[1].loc[1:,0].values 
data
Out[30]:
面積[5] (km2) 2010 人口[5] 2011 国内総生産 (PPT)[5] (Intl. $) 2011 国内総生産 (一人当りPPT)[5] (Intl. $) 2011 所得不平等[5] 1993-2009 (直近値) 人間開発[6] 2011 失敗国家 (FSI)[7] 2012 腐敗認識[8] 2011 経済自由指数[9] 2011 世界平和度[10] 2012 世界報道自由[11] 2011/2012 民主主義[12] 2011
オーストラリア 7741220 22620600 892739612442 39466 35.2 0.929 29.2 8.8 82.5 1.494 4.00 9.22
オーストリア 83870 8419000 354628026975 42122 29.2 0.885 27.5 7.8 71.9 1.328 -8.00 8.49
ベルギー 30530 11008000 425276544386 38633 33.0 0.886 33.5 7.5 70.2 1.376 -2.00 8.05
カナダ 9984670 34482779 1397983465565 40541 32.6 0.908 26.8 8.7 80.8 1.317 -5.67 9.08
チリ 756090 17269525 295740683117 17125 52.1 0.805 43.5 7.2 77.4 1.616 29.00 7.54
チェコ 78870 10546000 273662146638 25949 25.8 0.865 39.5 4.4 70.4 1.396 -5.00 8.19
デンマーク 43090 5574000 228616450630 41015 24.7 0.895 23.0 9.4 78.6 1.239 -5.67 9.52
エストニア 45230 1340000 30024533557 22406 36.0 0.835 47.5 6.4 75.2 1.715 -9.00 7.61
フィンランド 338420 5387000 202446166977 37581 26.9 0.882 20.0 9.4 74.0 1.348 -10.00 9.06
フランス 549190 65436552 2302945703407 35194 32.7 0.884 33.6 7.0 64.6 1.710 9.50 7.77
ドイツ 357120 81726000 3221135411591 39414 28.3 0.905 31.7 8.0 71.8 1.424 -3.00 8.34
ギリシャ 131960 11304000 303987090775 26892 34.3 0.861 50.4 3.4 60.3 1.976 24.00 7.65
ハンガリー 93030 9971000 216752108474 21738 31.2 0.816 48.3 4.6 66.6 1.476 10.00 7.04
アイスランド 103000 319000 11839614943 37115 NaN 0.898 29.1 8.3 68.2 1.113 -7.00 9.65
アイルランド 70280 4487000 186848293971 41642 34.3 0.908 26.5 7.5 78.7 1.328 -4.00 8.56
イスラエル 22070 7765700 217492394269 28007 39.2 0.888 N/Aa 5.8 68.5 2.842 31.25 7.53
イタリア 301340 60770000 1979219444356 32569 36.0 0.874 45.8 3.9 60.3 1.690 19.67 7.74
日本 377940 127817277 4381290159229 34278 24.9 0.901 43.5 8.0 72.8 1.326 -1.00 8.08
韓国 99900 49779000 1503604062678 30206 31.6 0.897 37.6 5.4 69.8 1.734 12.67 8.06
ルクセンブルク 2590 517000 45902664436 88787 30.8 0.867 25.5 8.5 76.2 1.341c -7.00 8.88
メキシコ 1964380 114793341 1760946368455 15340 48.3 0.770 73.6 3.0 67.8 2.445 72.67 6.93
オランダ 41540 16696000 723585287472 43339 30.9 0.910 28.1 8.9 74.7 1.606 -9.00 8.99
ニュージーランド 267710 4405200 131,507,519,463c 30,108c 36.2 0.908 25.6 9.5 82.3 1.239 -5.33 9.26
ノルウェー 323780 4952000 282720915051 57092 25.8 0.943 23.9 9.0 70.3 1.480 -10.00 9.80
ポーランド 312680 38216000 813292967101 21281 34.1 0.813 44.3 5.5 64.1 1.524 -0.67 7.12
ポルトガル 92090 10637000 270649574742 25444 38.5 0.809 34.2 6.1 64.0 1.470 5.33 7.81
スロバキア 49040 5440000 132919954401 24434 26.0 0.834 47.4 4.0 69.5 1.590 0.00 7.35
スロベニア 20270 2052000 56573135942 27570 31.2 0.884 34.0 5.9 64.6 1.330 9.14 7.76
スペイン 505370 46235000 1511951580566 32701 34.7 0.878 42.8 6.2 70.2 1.548 9.75 8.02
スウェーデン 450300 9453000 391800201817 41447 25.0 0.904 21.3 9.3 71.9 1.419 -5.50 9.50
スイス 41280 7907000 378088821911 47817 33.7 0.903 23.3 8.8 81.9 1.349 -6.20 9.09
トルコ 783560 73639596 1243426691409 16885 39.0 0.699 76.6 4.2 64.2 2.344 70.00 5.72
イギリス 243610 62641000 2287071689227 36511 36.0 0.863 35.3 7.8 74.5 1.609 2.00 8.16
アメリカ合衆国 9831510 311591917 15094000000000 48442 40.8 0.910 34.8 7.1 77.8 2.058 14.00 8.11
zzzOECDb 36137530 1245198487 43550669285973 34,993d 33.3 0.871 36.6 6.9 71.7 1.590 6.44 8.23
In [28]:
data.sort('腐敗認識[8] 2011')
Out[28]:
面積[5] (km2) 2010 人口[5] 2011 国内総生産 (PPT)[5] (Intl. $) 2011 国内総生産 (一人当りPPT)[5] (Intl. $) 2011 所得不平等[5] 1993-2009 (直近値) 人間開発[6] 2011 失敗国家 (FSI)[7] 2012 腐敗認識[8] 2011 経済自由指数[9] 2011 世界平和度[10] 2012 世界報道自由[11] 2011/2012 民主主義[12] 2011
メキシコ 1964380 114793341 1760946368455 15340 48.3 0.770 73.6 3.0 67.8 2.445 72.67 6.93
ギリシャ 131960 11304000 303987090775 26892 34.3 0.861 50.4 3.4 60.3 1.976 24.00 7.65
イタリア 301340 60770000 1979219444356 32569 36.0 0.874 45.8 3.9 60.3 1.690 19.67 7.74
スロバキア 49040 5440000 132919954401 24434 26.0 0.834 47.4 4.0 69.5 1.590 0.00 7.35
トルコ 783560 73639596 1243426691409 16885 39.0 0.699 76.6 4.2 64.2 2.344 70.00 5.72
チェコ 78870 10546000 273662146638 25949 25.8 0.865 39.5 4.4 70.4 1.396 -5.00 8.19
ハンガリー 93030 9971000 216752108474 21738 31.2 0.816 48.3 4.6 66.6 1.476 10.00 7.04
韓国 99900 49779000 1503604062678 30206 31.6 0.897 37.6 5.4 69.8 1.734 12.67 8.06
ポーランド 312680 38216000 813292967101 21281 34.1 0.813 44.3 5.5 64.1 1.524 -0.67 7.12
イスラエル 22070 7765700 217492394269 28007 39.2 0.888 N/Aa 5.8 68.5 2.842 31.25 7.53
スロベニア 20270 2052000 56573135942 27570 31.2 0.884 34.0 5.9 64.6 1.330 9.14 7.76
ポルトガル 92090 10637000 270649574742 25444 38.5 0.809 34.2 6.1 64.0 1.470 5.33 7.81
スペイン 505370 46235000 1511951580566 32701 34.7 0.878 42.8 6.2 70.2 1.548 9.75 8.02
エストニア 45230 1340000 30024533557 22406 36.0 0.835 47.5 6.4 75.2 1.715 -9.00 7.61
zzzOECDb 36137530 1245198487 43550669285973 34,993d 33.3 0.871 36.6 6.9 71.7 1.590 6.44 8.23
フランス 549190 65436552 2302945703407 35194 32.7 0.884 33.6 7.0 64.6 1.710 9.50 7.77
アメリカ合衆国 9831510 311591917 15094000000000 48442 40.8 0.910 34.8 7.1 77.8 2.058 14.00 8.11
チリ 756090 17269525 295740683117 17125 52.1 0.805 43.5 7.2 77.4 1.616 29.00 7.54
アイルランド 70280 4487000 186848293971 41642 34.3 0.908 26.5 7.5 78.7 1.328 -4.00 8.56
ベルギー 30530 11008000 425276544386 38633 33.0 0.886 33.5 7.5 70.2 1.376 -2.00 8.05
イギリス 243610 62641000 2287071689227 36511 36.0 0.863 35.3 7.8 74.5 1.609 2.00 8.16
オーストリア 83870 8419000 354628026975 42122 29.2 0.885 27.5 7.8 71.9 1.328 -8.00 8.49
日本 377940 127817277 4381290159229 34278 24.9 0.901 43.5 8.0 72.8 1.326 -1.00 8.08
ドイツ 357120 81726000 3221135411591 39414 28.3 0.905 31.7 8.0 71.8 1.424 -3.00 8.34
アイスランド 103000 319000 11839614943 37115 NaN 0.898 29.1 8.3 68.2 1.113 -7.00 9.65
ルクセンブルク 2590 517000 45902664436 88787 30.8 0.867 25.5 8.5 76.2 1.341c -7.00 8.88
カナダ 9984670 34482779 1397983465565 40541 32.6 0.908 26.8 8.7 80.8 1.317 -5.67 9.08
スイス 41280 7907000 378088821911 47817 33.7 0.903 23.3 8.8 81.9 1.349 -6.20 9.09
オーストラリア 7741220 22620600 892739612442 39466 35.2 0.929 29.2 8.8 82.5 1.494 4.00 9.22
オランダ 41540 16696000 723585287472 43339 30.9 0.910 28.1 8.9 74.7 1.606 -9.00 8.99
ノルウェー 323780 4952000 282720915051 57092 25.8 0.943 23.9 9.0 70.3 1.480 -10.00 9.80
スウェーデン 450300 9453000 391800201817 41447 25.0 0.904 21.3 9.3 71.9 1.419 -5.50 9.50
フィンランド 338420 5387000 202446166977 37581 26.9 0.882 20.0 9.4 74.0 1.348 -10.00 9.06
デンマーク 43090 5574000 228616450630 41015 24.7 0.895 23.0 9.4 78.6 1.239 -5.67 9.52
ニュージーランド 267710 4405200 131,507,519,463c 30,108c 36.2 0.908 25.6 9.5 82.3 1.239 -5.33 9.26
In [36]:
%matplotlib inline
# 画像をブラウザに埋め込むため

import seaborn as sns

flights_data = sns.load_dataset("flights")
flights_data
Out[36]:
year month passengers
0 1949 January 112
1 1949 February 118
2 1949 March 132
3 1949 April 129
4 1949 May 121
5 1949 June 135
6 1949 July 148
7 1949 August 148
8 1949 September 136
9 1949 October 119
10 1949 November 104
11 1949 December 118
12 1950 January 115
13 1950 February 126
14 1950 March 141
15 1950 April 135
16 1950 May 125
17 1950 June 149
18 1950 July 170
19 1950 August 170
20 1950 September 158
21 1950 October 133
22 1950 November 114
23 1950 December 140
24 1951 January 145
25 1951 February 150
26 1951 March 178
27 1951 April 163
28 1951 May 172
29 1951 June 178
... ... ... ...
114 1958 July 491
115 1958 August 505
116 1958 September 404
117 1958 October 359
118 1958 November 310
119 1958 December 337
120 1959 January 360
121 1959 February 342
122 1959 March 406
123 1959 April 396
124 1959 May 420
125 1959 June 472
126 1959 July 548
127 1959 August 559
128 1959 September 463
129 1959 October 407
130 1959 November 362
131 1959 December 405
132 1960 January 417
133 1960 February 391
134 1960 March 419
135 1960 April 461
136 1960 May 472
137 1960 June 535
138 1960 July 622
139 1960 August 606
140 1960 September 508
141 1960 October 461
142 1960 November 390
143 1960 December 432

144 rows × 3 columns

In [49]:
# これはpandas.DataFrameの威力です
flights_data[flights_data.year==1949]
Out[49]:
year month passengers
0 1949 January 112
1 1949 February 118
2 1949 March 132
3 1949 April 129
4 1949 May 121
5 1949 June 135
6 1949 July 148
7 1949 August 148
8 1949 September 136
9 1949 October 119
10 1949 November 104
11 1949 December 118
In [55]:
# 同じことをですが、こんな機能も
flights_data.groupby('year').get_group(1950)
Out[55]:
year month passengers
12 1950 January 115
13 1950 February 126
14 1950 March 141
15 1950 April 135
16 1950 May 125
17 1950 June 149
18 1950 July 170
19 1950 August 170
20 1950 September 158
21 1950 October 133
22 1950 November 114
23 1950 December 140
In [38]:
# ピボットテーブルの作成
flights_pivot = flights_data.pivot("month", "year", "passengers")
In [39]:
flights_pivot
Out[39]:
year 1949 1950 1951 1952 1953 1954 1955 1956 1957 1958 1959 1960
month
January 112 115 145 171 196 204 242 284 315 340 360 417
February 118 126 150 180 196 188 233 277 301 318 342 391
March 132 141 178 193 236 235 267 317 356 362 406 419
April 129 135 163 181 235 227 269 313 348 348 396 461
May 121 125 172 183 229 234 270 318 355 363 420 472
June 135 149 178 218 243 264 315 374 422 435 472 535
July 148 170 199 230 264 302 364 413 465 491 548 622
August 148 170 199 242 272 293 347 405 467 505 559 606
September 136 158 184 209 237 259 312 355 404 404 463 508
October 119 133 162 191 211 229 274 306 347 359 407 461
November 104 114 146 172 180 203 237 271 305 310 362 390
December 118 140 166 194 201 229 278 306 336 337 405 432
In [41]:
# 数値入りのヒートマップを描く
sns.heatmap(flights_pivot, annot=True, fmt='d')
Out[41]:
<matplotlib.axes._subplots.AxesSubplot at 0x10d19d9e8>
In [45]:
#  なんと双方向の階層的クラスタリングまでやってくれる
sns.clustermap(flights_pivot)
Out[45]:
<seaborn.matrix.ClusterGrid at 0x109bb5e80>

PythonはWebを学ぶのにもいい

$ python -m http.server
Serving HTTP on 0.0.0.0 port 8000 ...

これだけで、カレントディレクトリをドキュメントルートにしたWebサーバがローカルで起動
--cgiオプションを付ければ、CGIスクリプトの実行も可能

しかもWebアプリケーションサーバにもなる

Pythonには、Webアプリケーションの標準仕様であるWSGI(Web Server Gateway Interface)があって、その参照実装が標準モジュールに入っている。

In [ ]:
# test_web_ap.py
from wsgiref import simple_server
import datetime as dt

def application(environ, start_response):
    start_response('200 OK', [('Content-type', 'text/html')])
    _now = dt.datetime.now()
    response_html = '''<html>
      <head>
       <title>TEST</title>
      </head>
       <body>
        <h1>{}:{} {}</h1>
       </body>
      </html>'''.format(_now.hour, _now.minute, _now.second)
    return [response_html.encode('UTF-8')]

if __name__ == '__main__':
    server = simple_server.make_server('', 8080, application)
    server.serve_forever()

$ python test_web_ap.py として実行し、ブラウザから http://localhost:8080

まとめ

  • Pythonには勢いがある
  • 充実の標準モジュール
  • データ解析関連のライブラリも「すごい」
  • Web開発にも向いている
  • Pythonをやらない理由があるだろうか?いや無い!

おしまい

引き続き、Web関連の話題でお楽しみください。