postgresqlのデータをpandasで分析したかったので、pandas.io.sqlを使って読み込んでみる。
あと、書き込みの方もやってみる。こちらはsqliteで。
mysqlやsqliteについてはstackoverflowの下記記事参照
http://stackoverflow.com/questions/10065051/python-pandas-and-databases-like-mysql
尚、上記で使っているframe_queryはdeprecatedになっていて、現在ではread_queryを使うらしい。
psycopg2を使う
pip install psycopg2
SELECTする際の適当なサンプルコード
import psycopg2 as pg
with pg.connect(database='db_name',
user='user_name',
host='host_name',
port=5432) as conn, conn.cursor() as cur:
cur.execute( 'SELECT * FROM foo' )
print( cur.fetchall() )
pandas.io.sqlを使えば良いらしい。
import pandas.io.sql as psql
import psycopg2 as pg
with pg.connect(database='db_name',
user='user_name',
host='host_name',
port=5432) as conn:
sql = 'SELECT * FROM foo'
df = psql.read_sql(sql, conn)
これだけでカラム名もちゃんと認識したdataframeを作ってくれる。便利。
# 登録するデータを作る
import pandas as pd
df = pd.DataFrame( [ [1, 2, 3], [4, 5, 6] ], columns=[ 'a', 'b', 'c' ] )
# 登録実行(CREATEも行われるよ)
import sqlite3
import pandas.io.sql as psql
with sqlite3.connect("tmp.db") as conn:
# これでINSERTされる
psql.to_sql( df, 'foo', conn )
# 中身確認
with sqlite3.connect("tmp.db") as conn:
cur = conn.execute("select * from foo")
print( cur.fetchall() )
cur.close()
実行結果
[(0, 1, 2, 3), (1, 4, 5, 6)]
先頭にindexが付いた状態で登録される。indexはいらないという場合は、index=False を設定する。
import pandas.io.sql as psql
with sqlite3.connect("tmp.db") as conn:
# DROPしておく
conn.execute( 'DROP TABLE foo' )
# ここでindex=Falseを設定
psql.to_sql( df, 'foo', conn, index=False )
cur = conn.execute("select * from foo")
print( cur.fetchall() )
これでindexが消える。普通にデータを出し入れする場合はこちらの方が良いかも。
実行結果
[(1, 2, 3), (4, 5, 6)]
あとは既にテーブルができている場合は、if_exists='replace' で置き換えたり
import pandas as pd
df = pd.DataFrame( [ [7, 8, 9], [10, 11, 12] ], columns=[ 'a', 'b', 'c' ] )
import pandas.io.sql as psql
with sqlite3.connect("tmp.db") as conn:
psql.to_sql( df, 'foo', conn, index=False, if_exists='replace' )
cur = conn.execute("select * from foo")
print( cur.fetchall() )
実行結果
[(7, 8, 9), (10, 11, 12)]