pypyodbc与PLSQL

时间:2018-02-07 14:17:08

标签: python oracle execute cx-oracle pypyodbc

我在PLSQL和Python / pypyodbc中测试了相同的Oracle查询。我拉~30k行,在PLSQL中需要27秒,而Python需要大约8分钟。我的python / pypyodbc代码在这里:

import pandas as pd
import pypyodbc

q0 = '''
    select *
    from weatherview x
    where x.WeatherNodeRCIKey IN (481, 562, 563, 561, 564, 565, 560, 658)
    and x.WeatherDate >= '01-jan-2016'
   '''
try:
con = pypyodbc.connect(driver='{Oracle in OraClient11g_home1}', 
    server='oracle', uid='acct', pwd='Pass', dbq='table')

with con:
    cur = con.cursor()
    cur.execute(q0)
    q0_rows = cur.fetchall()
    q0_hdnm = [i[0] for i in cur.description]

except Exception as e:
    print("Error: " + str(e))

df0 = pd.DataFrame(q0_rows, columns=q0_hdnm)
df0.head()

我很难相信Python会慢得多。我很好奇这是服务器端/客户端问题,还是内存问题。我不相信这与代码的数据帧/ pandas部分有关,因为我运行的代码没有最后几行,结果相同。

我90%确定问题与fetchall()缓慢有关。

如果有人能指出,我会很高兴:

  • 如何解决速度问题(数据库连接时间等)
  • 使用其他程序包来提取更快的查询
  • 使用pypyodbc更改此代码以更有效地工作

    编辑:我更改了标签,移除了[服务器端],并根据我在下面找到的答案添加了[cx_Oracle]

2 个答案:

答案 0 :(得分:0)

我通过我的#34发现了一个答案;使用不同的包#34;上面的选项,使用cx_Oracle。代码如下:

import pandas as pd
import cx_Oracle

q0 = '''
    select *
    from weatherview_historical x
    where x.WeatherNodeRCIKey IN (481, 562, 563, 561, 564, 565, 560, 658)
    and x.WeatherDate >= '01-jan-2016'
    and x.WeatherTypeLu in (6436,6439)
   '''
try:
    #establish connection with profit (oracle) db
    con = cx_Oracle.connect(user='uid', password='pass', dsn='dsn_name')
    df0 = pd.read_sql_query(q0, con) 

except Exception as e:
    #return error message
    print("Error: " + str(e))

关键是cx_Oracle包,它在20秒内获取结果,而pypyodbc获取8分钟(如上所述,PLSQL为27秒)。我还能通过.read_sql_query

将行直接输入到pandas中的数据帧中

我仍然非常感兴趣为什么pypyodbc与其他选项相比如此之慢。如果有人有任何关于让它运行得更快的想法,那就是:

  • 在sql级别更改编码,因此python不必处理
  • 每次调用更改数据库返回的项目数(数组大小/块大小)
  • 更改为服务器端
  • 跳过.execute或.fetchall步骤(这些步骤仍然适用于cx_Oracle)

请告诉我

答案 1 :(得分:0)

使用turbodbc库,这是快速上传的唯一方法:https://turbodbc.readthedocs.io/en/latest/pages/getting_started.html