我每天都会将大约2至250万条记录加载到Postgres数据库中。将熊猫数据框转换为内存中类似文件的对象?
然后我用pd.read_sql读取这个数据,将它变成一个数据帧,然后我做一些列操作和一些次要的合并。我将这些修改后的数据保存为一个单独的表格供其他人使用。
当我做pd.to_sql它需要永远。如果我在Postgres中保存一个csv文件并使用COPY FROM,整个过程只需要几分钟,但服务器位于另一台机器上,并且在那里传输文件是一件痛苦的事情。
使用psycopg2,它看起来像我可以使用copy_expert从批量复制中受益,但仍然使用python。如果可能,我想尽量避免写一个实际的csv文件。我可以用熊猫数据框在内存中执行此操作吗?
这是我的熊猫代码的一个例子。如果可能的话,我想添加copy_expert或其他东西以使数据保存得更快。
for date in required_date_range:
df = pd.read_sql(sql=query, con=pg_engine, params={'x' : date})
...
do stuff to the columns
...
df.to_sql('table_name', pg_engine, index=False, if_exists='append', dtype=final_table_dtypes)
有人可以帮助我的例子代码?我宁愿仍然使用熊猫,这将是很好的记忆。如果不是的话,我只会写一个csv临时文件并且这样做。
编辑 - 这里是我的最终代码,它的工作原理。每个日期(数百万行)只需要几百秒而不是几个小时。
to_sql = “” “COPY%S FROM STDIN WITH CSV HEADER” “”
def process_file(conn, table_name, file_object):
fake_conn = cms_dtypes.pg_engine.raw_connection()
fake_cur = fake_conn.cursor()
fake_cur.copy_expert(sql=to_sql % table_name, file=file_object)
fake_conn.commit()
fake_cur.close()
#after doing stuff to the dataframe
s_buf = io.StringIO()
df.to_csv(s_buf)
process_file(cms_dtypes.pg_engine, 'fact_cms_employee', s_buf)
我不知道psycopg2,但你可以尝试如下:'s_buf = io.StringIO()','df.to_csv(s_buf)',它会将你的df存储在类似文件的缓冲区中。那么也许'cur.copy_from(s_buf,...)'而不是'copy_expert'。 – ptrj
强壮的工作!尽管我仍然保留着复制专家。当我使用普通的pandas.to_sql时,它只花费了100秒而不是10000秒。做一个真实的答案,所以我可以接受 – trench
很高兴我能帮上忙。 – ptrj