python-pandas และฐานข้อมูลเช่น mysql


97

เอกสารสำหรับ Pandas มีตัวอย่างแนวทางปฏิบัติที่ดีที่สุดมากมายสำหรับการทำงานกับข้อมูลที่จัดเก็บในรูปแบบต่างๆ

อย่างไรก็ตามฉันไม่พบตัวอย่างที่ดีสำหรับการทำงานกับฐานข้อมูลเช่น MySQL เป็นต้น

ใครสามารถชี้ฉันไปที่ลิงก์หรือให้ข้อมูลโค้ดเกี่ยวกับวิธีการแปลงผลลัพธ์การสืบค้นโดยใช้mysql-pythonเป็น data frames ใน Pandas ได้อย่างมีประสิทธิภาพ



ดูเพิ่มเติม: stackoverflow.com/questions/15231646/…
Mechanical snail

ลองดูที่Blazeด้วย
Sergey Orshanskiy

หากคุณยินดีจ่ายเงินฉันเชื่อว่าหนังสือของ Wes McKinney ("Python for Data Analysis") มีตัวอย่างที่เป็นประโยชน์
MTrenfield

คำตอบ:


102

ดังที่ Wes กล่าวว่า read_sql ของ io / sql จะทำเมื่อคุณได้รับการเชื่อมต่อฐานข้อมูลโดยใช้ไลบรารีที่เข้ากันได้กับ DBI เราสามารถดูสองตัวอย่างสั้น ๆ โดยใช้MySQLdbและcx_Oracleไลบรารีเพื่อเชื่อมต่อกับ Oracle และ MySQL และสืบค้นพจนานุกรมข้อมูล นี่คือตัวอย่างสำหรับcx_Oracle:

import pandas as pd
import cx_Oracle

ora_conn = cx_Oracle.connect('your_connection_string')
df_ora = pd.read_sql('select * from user_objects', con=ora_conn)    
print 'loaded dataframe from Oracle. # Records: ', len(df_ora)
ora_conn.close()

และนี่คือตัวอย่างที่เทียบเท่าสำหรับMySQLdb:

import MySQLdb
mysql_cn= MySQLdb.connect(host='myhost', 
                port=3306,user='myusername', passwd='mypassword', 
                db='information_schema')
df_mysql = pd.read_sql('select * from VIEWS;', con=mysql_cn)    
print 'loaded dataframe from MySQL. records:', len(df_mysql)
mysql_cn.close()

57

สำหรับผู้อ่านคำถามนี้ล่าสุด: หมีแพนด้ามีคำเตือนต่อไปนี้ในเอกสารสำหรับเวอร์ชัน 14.0 :

คำเตือน: บางฟังก์ชันหรือชื่อแทนฟังก์ชันที่มีอยู่ได้เลิกใช้งานแล้วและจะถูกลบออกในเวอร์ชันต่อ ๆ ไป ซึ่งรวมถึง: tquery, uquery, read_frame, frame_query, write_frame

และ:

คำเตือน: การรองรับรสชาติ 'mysql' เมื่อใช้ออบเจ็กต์การเชื่อมต่อ DBAPI ถูกเลิกใช้แล้ว MySQL จะรองรับเพิ่มเติมกับเอ็นจิ้น SQLAlchemy (GH6900)

ทำให้หลายคำตอบที่นี่ล้าสมัย คุณควรใช้sqlalchemy:

from sqlalchemy import create_engine
import pandas as pd
engine = create_engine('dialect://user:pass@host:port/schema', echo=False)
f = pd.read_sql_query('SELECT * FROM mytable', engine, index_col = 'ID')

การโหลดตารางที่มี 133 แถวและ 7 คอลัมน์ใช้เวลาประมาณ 30 วินาที .. คุณสามารถให้ข้อมูลเชิงลึกเกี่ยวกับสาเหตุนั้นได้หรือไม่
idoda

@idoda [โดยทั่วไปนี่ไม่ใช่หัวข้อของคำถามและควรถามคำถามใหม่เพื่อที่คุณจะได้รับความคิดเห็นเพิ่มเติม] แน่ใจหรือว่านี่ไม่ใช่เรื่องของการขอล่าช้า เพียงแค่ส่งแบบสอบถามและดึงผลลัพธ์เร็วขึ้นอย่างมาก?
Korem

@Korem ฉันคิดเกี่ยวกับการเปิดใหม่ แต่ฉันต้องการให้แน่ใจว่ามันไม่ใช่เรื่องเล็กน้อยก่อน เมื่อฉันใช้ไคลเอนต์ mySql (Sequel pro) และสืบค้นฐานข้อมูล reuslts จะเร็วขึ้นมาก เมื่อคุณพูดว่า "เพียงแค่ส่งแล้วดึงข้อมูล" คุณหมายถึงอะไร? (ใช้ไคลเอนต์)
idoda

@idoda ฉันหมายถึงการเปรียบเทียบเวลาที่ใช้ในการดำเนินการengine.execute("select * FROM mytable")กับเวลาที่ใช้ในการดำเนินการpd.read_sql_query('SELECT * FROM mytable', engine)
Korem

เราสามารถส่งแบบสอบถาม sqlalchemy (session.query ตามคำตอบของฉันด้านล่าง) โดยตรงไปยังวิธีการแพนด้าได้หรือไม่ นั่นจะเป็นการฉีก!
dmvianna

23

สำหรับบันทึกนี่คือตัวอย่างการใช้ฐานข้อมูล sqlite:

import pandas as pd
import sqlite3

with sqlite3.connect("whatever.sqlite") as con:
    sql = "SELECT * FROM table_name"
    df = pd.read_sql_query(sql, con)
    print df.shape

1
คุณสามารถระบุคอลัมน์ที่จะใช้เป็นดัชนีได้โดยระบุindex_col='timestamp'ในframe_query.
หอยทาก

19

ฉันชอบสร้างแบบสอบถามด้วยSQLAlchemyแล้วสร้าง DataFrame จากมัน SQLAlchemyทำให้ง่ายต่อการรวมเงื่อนไขSQL Pythonically หากคุณตั้งใจจะผสมและจับคู่สิ่งต่างๆซ้ำแล้วซ้ำอีก

from sqlalchemy.ext.declarative import declarative_base
from sqlalchemy import Table
from sqlalchemy import create_engine
from sqlalchemy.orm import sessionmaker
from pandas import DataFrame
import datetime

# We are connecting to an existing service
engine = create_engine('dialect://user:pwd@host:port/db', echo=False)
Session = sessionmaker(bind=engine)
session = Session()
Base = declarative_base()

# And we want to query an existing table
tablename = Table('tablename', 
    Base.metadata, 
    autoload=True, 
    autoload_with=engine, 
    schema='ownername')

# These are the "Where" parameters, but I could as easily 
# create joins and limit results
us = tablename.c.country_code.in_(['US','MX'])
dc = tablename.c.locn_name.like('%DC%')
dt = tablename.c.arr_date >= datetime.date.today() # Give me convenience or...

q = session.query(tablename).\
            filter(us & dc & dt) # That's where the magic happens!!!

def querydb(query):
    """
    Function to execute query and return DataFrame.
    """
    df = DataFrame(query.all());
    df.columns = [x['name'] for x in query.column_descriptions]
    return df

querydb(q)

นอกจากนี้คุณต้องระบุไดรเวอร์หากไม่เหมือนกับค่าเริ่มต้นของ SQLAlchemy :dialect+driver://user:pwd@host:port/db
Nuno André

11

ตัวอย่าง MySQL:

import MySQLdb as db
from pandas import DataFrame
from pandas.io.sql import frame_query

database = db.connect('localhost','username','password','database')
data     = frame_query("SELECT * FROM data", database)

7
frame_queryเลิกใช้งานแล้ว ตอนนี้ใช้pd.read_sql(query, db)แทน.
Robert Smith

8

ไวยากรณ์เดียวกันใช้ได้กับเซิร์ฟเวอร์ Ms SQL ที่ใช้ podbc ด้วย

import pyodbc
import pandas.io.sql as psql

cnxn = pyodbc.connect('DRIVER={SQL Server};SERVER=servername;DATABASE=mydb;UID=username;PWD=password') 
cursor = cnxn.cursor()
sql = ("""select * from mytable""")

df = psql.frame_query(sql, cnxn)
cnxn.close()

5

และนี่คือวิธีที่คุณเชื่อมต่อกับ PostgreSQL โดยใช้ไดรเวอร์ psycopg2 (ติดตั้งด้วย "apt-get install python-psycopg2" หากคุณใช้ Debian Linux derivative OS)

import pandas.io.sql as psql
import psycopg2

conn = psycopg2.connect("dbname='datawarehouse' user='user1' host='localhost' password='uberdba'")

q = """select month_idx, sum(payment) from bi_some_table"""

df3 = psql.frame_query(q, conn)



1

นำเข้าโมดูล

import pandas as pd
import oursql

เชื่อมต่อ

conn=oursql.connect(host="localhost",user="me",passwd="mypassword",db="classicmodels")
sql="Select customerName, city,country from customers order by customerName,country,city"
df_mysql = pd.read_sql(sql,conn)
print df_mysql

ใช้งานได้ดีและใช้ pandas.io.sql frame_works (พร้อมคำเตือนการเลิกใช้งาน) ฐานข้อมูลที่ใช้คือฐานข้อมูลตัวอย่างจากการสอน mysql


0

สิ่งนี้ควรใช้งานได้ดี

import MySQLdb as mdb
import pandas as pd
con = mdb.connect(‘127.0.0.1’, ‘root’, ‘password’, ‘database_name’);
with con:
 cur = con.cursor()
 cur.execute(“select random_number_one, random_number_two, random_number_three from randomness.a_random_table”)
 rows = cur.fetchall()
 df = pd.DataFrame( [[ij for ij in i] for i in rows] )
 df.rename(columns={0: ‘Random Number One’, 1: ‘Random Number Two’, 2: ‘Random Number Three’}, inplace=True);
 print(df.head(20))

0

นี้จะช่วยให้ฉันสำหรับเชื่อมต่อกับAWS MYSQL (RDS)จากหลาม 3.xตามฟังก์ชั่นแลมบ์ดาและโหลดลงในหมีแพนด้า DataFrame

import json
import boto3
import pymysql
import pandas as pd
user = 'username'
password = 'XXXXXXX'
client = boto3.client('rds')
def lambda_handler(event, context):
    conn = pymysql.connect(host='xxx.xxxxus-west-2.rds.amazonaws.com', port=3306, user=user, passwd=password, db='database name', connect_timeout=5)
    df= pd.read_sql('select * from TableName limit 10',con=conn)
    print(df)
    # TODO implement
    #return {
    #    'statusCode': 200,
    #    'df': df
    #}

0

สำหรับผู้ใช้ Postgres

import psycopg2
import pandas as pd

conn = psycopg2.connect("database='datawarehouse' user='user1' host='localhost' password='uberdba'")

customers = 'select * from customers'

customers_df = pd.read_sql(customers,conn)

customers_df

1
คุณช่วยชี้ให้เห็นความแตกต่างของคำตอบของ @Will และเหตุใดจึงควรเลือกโซลูชัน
Sebastian
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.