Here is the Excel file in question:
上下文:我正在编写一个程序,它可以从PDF中提取值并将它们放在Excel文件中的相应单元格中。
问题:我想编写一个函数,它将一个列值(例如2014)和一个行值(例如' COGS')作为参数,并返回那两个相交的单元格引用(例如&# 39; C3' 2014年COGS)。
def find_correct_cell(year=2014, item='COGS'):
#do something similar to what the =match function in Excel does
return cell_reference #returns 'C3'
col_num = '=match(2014, A1:E1)'
row_num = '=match("COGS", A1:A5)'
但我想抓住这些值,而不必随意写入那些随机的空单元格。另外,即使使用这种方法,当我读取这些单元格(F5和F6)时,它会读取这些单元格中的公式而不是3的面值。
感谢任何帮助,谢谢。
答案 0 :(得分:1)
使用openpyxl以这种方式操作Excel文件所需的细节数量惊人。首先,值得知道xlsx文件包含每个单元格的两个表示 - 公式和公式的当前值。 openpyxl也可以返回,如果你想要值,你应该在打开文件时指定data_only=True
。此外,更改单元格的公式时,openpyxl无法计算新值 - 只有Excel本身才能这样做。因此,插入MATCH()工作表函数不会解决您的问题。
下面的代码可以满足您的需求,主要是在Python中。它使用" A1"引用样式,并进行一些计算以将列号转换为列字母。如果超过Z列,这将不会很好。在这种情况下,您可能希望切换到行和列的编号引用。有关here和here的更多信息。但希望这会让你顺利上路。
注意:此代码假设您正在阅读名为' test.xlsx'的工作簿,以及' COGS'是在' Sheet1!A2:A5'中的项目列表中。和2014年的年份列表在Sheet1!B1:E1'。
import openpyxl
def get_xlsx_region(xlsx_file, sheet, region):
""" Return a rectangular region from the specified file.
The data are returned as a list of rows, where each row contains a list
of cell values"""
# 'data_only=True' tells openpyxl to return values instead of formulas
# 'read_only=True' makes openpyxl much faster (fast enough that it
# doesn't hurt to open the file once for each region).
wb = openpyxl.load_workbook(xlsx_file, data_only=True, read_only=True)
reg = wb[sheet][region]
return [[cell.value for cell in row] for row in reg]
# cache the lists of years and items
# get the first (only) row of the 'B1:F1' region
years = get_xlsx_region('test.xlsx', 'Sheet1', 'B1:E1')[0]
# get the first (only) column of the 'A2:A6' region
items = [r[0] for r in get_xlsx_region('test.xlsx', 'Sheet1', 'A2:A5')]
def find_correct_cell(year, item):
# find the indexes for 'COGS' and 2014
year_col = chr(ord('B') + years.index(year)) # only works in A:Z range
item_row = 2 + items.index(item)
cell_reference = year_col + str(item_row)
return cell_reference
print find_correct_cell(year=2014, item='COGS')
# C3
答案 1 :(得分:1)
考虑翻译的VBA解决方案,因为Match功能可以充分满足您的需求。 Python可以使用带有win32com
模块的COM接口访问Excel VBA对象库。请注意,此解决方案假定您使用的是Excel for PC。下面包括对应的VBA功能。
VBA 功能(原生界面)
如果以下功能放在Excel标准模块中,则可以在电子表格单元格=FindCell(..., ###)
' MATCHES ROW AND COL INPUT FOR CELL ADDRESS OUTPUT
Function FindCell(item As String, year As Integer) As String
FindCell = Cells(Application.Match(item, Range("A1:A5"), 0), _
Application.Match(year, Range("A1:E1"), 0)).Address
End Function
debug.Print FindCell("COGS", 2014)
' $C$3
Python 脚本(外部接口,要求声明所有对象)
Try / Except / Finally用于正确关闭Excel进程,无论脚本成功还是失败。
import win32com.client
# MATCHES ROW AND COL INPUT FOR CELL ADDRESS OUTPUT
def FindCell(item, year):
return(xlWks.Cells(xlApp.WorksheetFunction.Match(item, xlWks.Range("A1:A5"), 0),
xlApp.WorksheetFunction.Match(year, xlWks.Range("A1:E1"), 0)).Address)
try:
xlApp = win32com.client.Dispatch("Excel.Application")
xlWbk = xlApp.Workbooks.Open('C:/Path/To/Workbook.xlsx')
xlWks = xlWbk.Worksheets("SHEETNAME")
print(FindCell("COGS", 2014))
# $C$3
except Exception as e:
print(e)
finally:
xlWbk.Close(False)
xlApp.Quit
xlWks = None
xlWbk = None
xlApp = None