【问题标题】:Update panda dataframe to SQL Server though SQLAlchemy engine using python通过使用 python 的 SQLAlchemy 引擎将 panda 数据框更新到 SQL Server
【发布时间】:2019-12-12 21:23:06
【问题描述】:

我有一个现有的 SQL Server 数据库。我想使用 python 从 CSV 文件中读取并将与 TIMEID 列匹配的列值更新到 SQL Server 表中

如果我在 SQL Server 中执行此操作,我会将新的 CSV 加载到新表中,然后使用以下命令进行更新:

UPDATE R 
SET R.[PA]=P.[PA]
FROM [DATABASE_TABLE] AS R
INNER JOIN [NEW_CSV] AS P 
       ON R.[TIMEID] = P.[TIMEID] 
WHERE R.[TIMEID] like '20180201%' //i can survive now without the where, and update everything from the CSV. 

对 python 很陌生,所以请原谅我。我已成功将 CSV 文件加载到 panda 数据框中,并且我能够将新行插入 SQL Server,但我无法管理更新(现有列或空列)。

import pandas as pd 
from sqlalchemy import create_engine
engine = create_engine("BLOCKOUTFOR PASSWORD")
query="SELECT * FROM [DATABASE].[TABLE]"
df = pd.read_sql_query(query, engine)
display(df) #This is just to display the current data

    TIMEID  DATEID  HOUR    DOW FESTIVAL    PA  PB  PC  P31A    PX  PY  P_TOT
0   20180101H01 2018-01-01  01  2   N   0.4615  0.0570  0.4427  0.0153  None    None    0.9765
1   20180101H02 2018-01-01  02  2   N   0.4112  0.0516  0.4074  0.0154  None    None    0.8856

#Convert Type and Load CSV into df3
def dfReadCSV( Path, Ind):
    df =pd.read_csv(Path,dtype={'DATEID':str,'Hour':str},parse_dates= ['DATEID'])
    df1=df[Ind:]
    return df1
df3=dfReadCSV("C5Liq_2018Test.csv",0)

display(df3) #if there is a neater way to do this it be appreciated, but not critical 

    Attribute   TIMEID  DATEID  Hour    DOW 20A 20DHA   21A 21DHA   30A 31A PA  PB  PC  P31A    P_TOT
0   H01 20180101H01 2018-01-01  01  1   0.2953  0.0158  0.1662  0.0412  0.4427  0.0153  0.4615  0.0570  0.4427  0.0153  0.9765
1   H02 20180101H02 2018-01-01  02  1   0.2711  0.0160  0.1401  0.0356  0.4074  0.0154  0.4112  0.0516  0.4074  0.0154  0.8856

#Insert Function
connStr= engine.connect().connection
cursor = connStr.cursor()

for index,row in df3.iterrows():
    cursor.execute('INSERT INTO [DATABASE].[TABLE]([TIMEID],[DATEID],[Hour],[DOW]) values (?,?,?,?)', row['TIMEID'], row['DATEID'], row['Hour'], row['DOW']) 
    connStr.commit()

cursor.close()
connStr.close()

#Update Function. This is where i have problem.
connStr= engine.connect().connection
cursor = connStr.cursor()

for row in df3.iterrows():
    #sql = 'UPDATE [DATABASE].[TABLE] SET [DATEID]=? WHERE [TIMEID]=?'.format(tbl=[DATABASE].[TABLE])
   cursor.execute("UPDATE [DATABASE].[TABLE]  SET [DATEID] = ? WHERE [TIMEID] = ?", row[:,0],row[;,0])  

cursor.close()
connStr.close()

语法错误,我无法弄清楚。最好我喜欢有与上述类似的更新方法。CSV 中的数据得到更新,我想将这些信息更新到我的 SQL Server 表中。

我找到了一个类似的帖子,但也没有找到答案: Update MSSQL table through SQLAlchemy using dataframes

作为那里的线程启动器,我也无法删除表,因为我加载到新数据列(例如 PX)中的新 CSV 可能没有之前插入 (PA) 的一些信息。

【问题讨论】:

    标签: python sql-server dataframe sqlalchemy


    【解决方案1】:

    有两种方法可以进行所需的更新:

    1) 直接在数据库上:

    upd = (session.query(TABLE)
           .filter(TIMEID = row[:,0])
           .update({"DATEID": row[:,0]})
           )
    print("# of updated rows = {}".format(upd))
    # session.commit()
    

    2) 加载对象、更新值并提交会话

    upd = (session.query(TABLE)
           .filter(TIMEID = row[:,0])
           )
    
    # assuming there should be exactly one object for given TIMEID
    DATEID= upd.one()
    DATEID.time_out = datetime.datetime.now()
    session.commit()
    

    你可以得到更多info

    我不推荐使用 sqlachemy 进行更新。它适合批量插入

    对于 sqlalchemy

    import pandas as pd
    from sqlalchemy import create_engine
    engine = create_engine('postgresql+psycopg2://postgres:password@host:port/database')
    print(engine)
    truncate_query = "SELECT * from something.something"
    df = pd.read_sql_query(truncate_query , engine)
    

    【讨论】:

    • 您好,感谢您的帮助。我开始使用 SQLACHEMY 只是因为 import create_engine,希望找到类似于使用 Cursor.excute 函数的解决方案。我尝试了您的解决方案,并且坦率地对使用会话等知之甚少。除了您建议的代码之外,我在查看链接后将以下内容添加到定义中 //from sqlalchemy.orm import sessionmaker Session=sessionmaker(bind=engine ) session = Session() // 第一种解决方案 1) 直接在数据库上://NameError: name 'TABLE' is not defined// 我很难定义 session.query()?
    • 我知道这可能是一个新手 qns,但我只是对归档同一事物的不同方式感到困惑。我想了解如何同时使 queerry.session 工作我在想是否存在(也许不可能?):在以下行中插入类似的更新: // connStr= engine.connect().connection cursor = connStr.cursor() for index,row in df3 .iterrows(): cursor.execute(SOME UPDATE STATEMENT) connStr.commit() cursor.close() connStr.close() // 感谢大家提供的任何信息,问候
    • NameError: name 'TABLE' is not defined//这里你必须用你的表名替换
    • index 用于行数据的索引我没有说为什么没有索引循环会失败,因为它不应该。
    【解决方案2】:

    经过数小时的搜索,我找到了解决方案的答案:

    更新功能

    connStr= engine.connect().connection
    cursor = connStr.cursor()
    
    for index, row in df3.iterrows():
        cursor.execute('''UPDATE [DATABASE].[TABLE] SET [Hour] = ? WHERE [TIMEID] = ?''', (row['Hour'],row['TIMEID']))  
        connStr.commit()
        
    
    cursor.close()
    connStr.close()
    

    经过数小时的尝试,这是一个直接的语法错误。

    我仍然想听听如何使用 session.query 方法获得解决方案。

    而且我确信如果进行一些错误检查,我上面的代码是否会更好。 同时,如果有人可以解释为什么没有“索引”而循环失败以及这意味着什么?

    for index, row in df3.iterrows():
    

    很累但很兴奋。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-10-03
      • 2019-12-17
      • 2018-11-29
      • 2017-01-16
      • 1970-01-01
      • 2016-05-27
      • 2020-06-23
      • 1970-01-01
      相关资源
      最近更新 更多