如何解决当 Access 具有使用 python 的“Nz”表达式时,从 MS Access 导出到 Excel
我有一个访问表,我试图将其导出到 excel,但访问表(以及它调用的一些表)使用“Nz”表达式。我试过用 IIf(IsNull( 甚至合并) 替换 Nz,但我似乎无法得到任何工作。我知道 pyodbc 访问驱动程序不支持他的 Nz 表达式,所以我试图找出解决方法。此外,我无权对 Access 数据库进行任何更改(这可能是最简单的解决方案。
另一个问题是连接中的一些列也有 NZ 表达式。也许某些东西会给脚本遇到的任何 Nz 表达式提供 0 的总值?我不太会使用 sql,所以这可能很容易,但我一直无法弄清楚如何。
我已经在没有 Nz 表达式的表上运行了代码并且它可以工作,所以我知道驱动程序/cnxn 是正确的。
import pyodbc
import pandas as pd
ly_rep_temp_path = r"C:\examplePath\msAccessFile.accdb"
temp_path = r"C:\example\temoraryStorage"
driver = '{Microsoft Access Driver (*.mdb,*.accdb)}'
cnxn = pyodbc.connect(Driver=driver,DBQ=ly_rep_temp_path)
sql = """
SELECT rep.old,rep.new,Left(Nz([oldI].[mName],""),10) AS oldM,Left(Nz([newI].[mName],10) AS newM,oldI.primary AS oldS,newI.primary AS newS,oldI.primaryMR AS oldR,newI.primaryM AS newR,FROM export_byI INNER JOIN ((rep INNER JOIN availableI AS oldI ON rep.olIs = oldI.isI) INNER JOIN availableI AS newI ON rep.nIsI = newI.isI) ON export_byI.IstI = rep.nwIsI
ORDER BY rep.nwIsI;
"""
crsr = cnxn.execute(sql)
for row in crsr.fetchall():
lpd_df = pd.read_sql(sql,cnxn)
print(lpd_df.columns)
lpd_df.to_excel(temp_path + '/zFinal.xlsx')
full_export_path = (temp_path + '/zFinal.xlsx')
# return full_export_path
crsr.close()
cnxn.close()
运行代码时出现以下错误: "pyodbc.ProgrammingError: ('42000',"[42000] [Microsoft][ODBC Microsoft Access Driver] 表达式中未定义函数 'Nz'。(-3102) (sqlExecDirectW)")"
解决方法
所以如果我们有一个名为 [Donor] 的表
DonorID DonorName Comments
------- --------- -------------
1 Gord cheapskate
2 Bill
3 Marsha Jan's nemesis
以及使用 Nz()
SELECT Donor.DonorID,Donor.DonorName,Nz([Comments],"(no comment)") AS txt
FROM Donor;
在 Microsoft Access 应用程序本身中产生以下内容
DonorID DonorName txt
------- --------- -------------
1 Gord cheapskate
2 Bill (no comment)
3 Marsha Jan's nemesis
如果我们尝试在 pyodbc 中执行 crsr.execute("SELECT * FROM query1")
,我们会得到
"pyodbc.ProgrammingError: ('42000',"[42000] [Microsoft][ODBC Microsoft Access Driver] 表达式中未定义函数 'Nz'。(-3102)
因为 Nz()
不是 Access 数据库引擎 (ACE) 的内置函数;它是 VBA 表达式引擎的一部分。因此,为了从 Python 执行该查询,我们需要使用 pywin32 和 COM 自动化来运行 MSACCESS.EXE 的实例并以这种方式执行查询:
"""
requires: pip install pywin32
"""
import win32com.client
# ACE.DAO constants
dbOpenDynaset = 2
msa = win32com.client.Dispatch("Access.Application")
msa.OpenCurrentDatabase(r"C:\Users\Public\Database1.accdb")
db = msa.CurrentDb()
rst = db.OpenRecordset("SELECT * FROM query1",dbOpenDynaset)
while not rst.EOF:
print(rst.Fields("txt").Value)
rst.MoveNext()
"""console output:
cheapskate
(no comment)
Jan's nemesis
"""
msa.Quit()
编辑:如果您想将查询导出到 Excel,您可以直接从 Access.Application
实例执行此操作:
acExport = 1
acSpreadsheetTypeExcel12Xml = 10
msa.DoCmd.TransferSpreadsheet(
acExport,acSpreadsheetTypeExcel12Xml,"query1",r"C:\__tmp\test.xlsx"
)
msa.Quit()
版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。