在添加公式后使用pandas / xslxwriter对列进行排序

问题描述 投票:1回答:1

我的数据框只有很少的列,实际上与这个问题无关,但是我想按特定顺序对列进行排序。

现在,问题是我有很多引用excel表的公式(例如,我正在使用xslxwriter worksheet.add_table创建的公式):

planned_units = '=Table1[@[Spend]]/Table1[@[CP]]'

因此,如果我要通过简单地在pandas中添加一列来添加这些公式:

df['newformula'] = planned_units

这是行不通的,我想是因为我在实际添加表格之前添加了引用表格的公式。因此,在添加公式之前对这些列进行排序将不起作用,因为:]

  • 我稍后(在创建表之后)添加公式,但我也想对刚添加的列进行排序
  • 如果我在add_table之前添加引用excel表的公式,则这些公式将无法在excel中使用

似乎xslxwriter不允许我以任何方式对列进行排序(也许是我错了?),所以我在获得最终的“产品”之后(在将所有列都添加了公式之后)看不到对列进行排序的任何可能性。 。

最好使用工作公式而不是已排序的列,但是我很乐意欢迎任何有关如何对它们进行排序的想法。

谢谢!

PS代码示例:

import pandas as pd
import xlsxwriter


# simple dataframe with 3 columns

input_df = pd.DataFrame({'column_a': ['x', 'y', 'z'],
                         'column_b': ['red', 'white', 'blue'],
                         'column_c': ['a', 'e', 'i'],
                         })

output_file = 'output.xlsx'

# formula I want to add
column_concatenation = '=CONCATENATE(Table1[@[column_a]], " ", Table1[@[column_b]])'

# now if adding formulas with pandas would be possible, I would do it like this:

# input_df['concatenation'] = column_concatenation
# but its not possible since excel gives you errors while opening!

# adding excel table with xlsxwriter:

workbook = xlsxwriter.Workbook(output_file)
worksheet = workbook.add_worksheet("Sheet with formula")

# here I would change column order only IF formulas added with pandas would work! so no-no
'''
desired_column_order = ['columnB', 'concatenation', 'columnC', 'columnA']
input_df = input_df[desired_column_order]
'''
data = input_df

worksheet.add_table('A1:D4', {'data': data.values.tolist(),
                              'columns': [{'header': c} for c in data.columns.tolist()] +
                                         [{'header': 'concatenation',
                                           'formula': column_concatenation}
                                          ],
                              'style': 'Table Style Medium 9'})

workbook.close()

现在在workbook.close()之前,我很乐意使用该表'desired_column_order'在添加公式后对列进行重新排序。

感谢:)

python pandas xlsxwriter
1个回答
1
投票

看来这里有两个问题:排序和表公式。

排序是Excel在运行时在Excel应用程序中执行的操作,不是文件格式的属性,也不是文件格式可以触发的内容。由于XlsxWriter仅处理文件格式,因此无法进行任何排序。但是,在使用XlsxWriter编写数据之前,可以在Python / Pandas中对数据进行排序。

公式问题是由于Excel具有原始[#This Row]语法(Excel 2007)和更高的@语法(Excel 2010+)。请参阅Working with Worksheet Tables - Columns上的XlsxWriter文档:

Excel 2007样式[#This Row]和Excel 2010样式@结构引用在公式中受支持。但是,不支持其他Excel 2010对结构参考的添加,并且公式应符合Excel 2007样式公式。

因此,基本上,您需要使用Excel 2007语法,因为即使文件在外部显示Excel 2010+语法,它也以文件格式存储。

当您通过add_table()方法添加公式时,XlsxWriter会为您进行转换,但是如果您以其他方式(例如通过Pandas)添加公式,则需要使用Excel 2007语法。因此,而不是像这样的公式:

=CONCATENATE(Table1[@[column_a]], " ", Table1[@[column_b]])

您需要添加此内容:

=CONCATENATE(Table1[[#This Row],[column_a]], " ", Table1[[#This Row],[column_b]])

((您可以看到为什么在更高版本的Excel版本中移至较短的语法。)

然后您的程序将按预期运行:

import pandas as pd
import xlsxwriter

input_df = pd.DataFrame({'column_a': ['x', 'y', 'z'],
                         'column_b': ['red', 'white', 'blue'],
                         'column_c': ['a', 'e', 'i'],
                         })

output_file = 'output.xlsx'

column_concatenation = '=CONCATENATE(Table1[[#This Row],[column_a]], " ", Table1[[#This Row],[column_b]])'

input_df['concatenation'] = column_concatenation


workbook = xlsxwriter.Workbook(output_file)
worksheet = workbook.add_worksheet("Sheet with formula")

desired_column_order = ['column_b', 'concatenation', 'column_c', 'column_a']
input_df = input_df[desired_column_order]
data = input_df

# Make the columns wider for clarity.
worksheet.set_column(0, 3, 16)

worksheet.add_table('A1:D4', {'data': data.values.tolist(),
                              'columns': [{'header': c} for c in data.columns.tolist()] +
                                         [{'header': 'concatenation'}],
                              'style': 'Table Style Medium 9'})

workbook.close()

输出:

enter image description here

© www.soinside.com 2019 - 2024. All rights reserved.