简体   繁体   中英

How to write pivot table values (columns) from pandas to excel using openpyxl?

I can write values to an existing excel worksheet but I am unable to export values from pivot table on pandas to excel sheet using openpyxl. Below are my code and what I am capable:

import pandas as pd
import openpyxl as op
import numpy as np
from openpyxl import Workbook, worksheet, load_workbook

wb = op.load_workbook("Table1.xlsx")
#ws = wb.active # selects active excel sheet

print(wb.sheetnames) # Shows all available sheet names

ws = wb['Sheet1'] # Select sheet name "Sheet1"
ws['B2'] = 40 # Input on cell B2
ws['B3'] = 18
ws['B4'] = 20
ws['B5'] = 20
ws['B6'] = 20
ws['C2'] = 8 # Input on cell C2
ws['C3'] = 30
ws['C4'] = 4
ws['C5'] = 10
ws['C6'] = 9
ws['D2'] = 89 # Input on cell D2
ws['D3'] = 300
ws['D4'] = 76
ws['D5'] = 20
ws['D6'] = 4

ws1 = wb['agua'] # Select sheet name "agua"
ws1['B2'] = 4 # Input on cell B2
ws1['B3'] = 60
ws1['B4'] = 0
ws1['C2'] = 90
ws1['C3'] = 23
ws1['C4'] = 20

wb.save("test.xlsx") # Saves to new excell worksheet to avoid mistakes

But I have this pivot table output that I need to fill each column of pivot table to that existing excel file sheet to be filled automatically. Look below:

df2 = pd.read_csv("https://www.dropbox.com/s/90y07129zn351z9/test_data.csv?dl=1",encoding="latin-1")

df2['received'] = pd.to_datetime(df2['received'])
df2['sent'] = pd.to_datetime(df2['sent'])

pvt_all = df2.dropna(axis=0, how='all', subset=['received', 'sent'])\
    .pivot_table(index=['site'], values=['received','sent'],\
    aggfunc='count', margins=True, dropna=False)
pvt_all['to_send']= pvt_all['received']-pvt_all['sent'] 
pvt_all=pvt_all[['received','sent','to_send']] 
pvt_all

received    sent    to_send
site            
2   32.0    27.0    5.0
3   20.0    17.0    3.0
4   33.0    31.0    2.0
5   40.0    31.0    9.0
All 125.0   106.0   19.0

Full dataset is in the link, I cant share (post) here because stackoverflow.com limits characters to 30000

What I want is to write these column values below:

received    sent    to_send
site            
2   32.0    27.0    5.0
3   20.0    17.0    3.0
4   33.0    31.0    2.0
5   40.0    31.0    9.0
All 125.0   106.0   19.0

To an existing excel workbook already with headers and index like below:

received    sent    to_send
site            
2       
3       
4   
5   
All 

I have more features for excel sheet but I just want to understand how to code to achieve desired result.

Simple way: After you have pvt_all , simply give a Excel filename to it:

pvt_all.to_excel("filename.xlsx")

See https://pandas.pydata.org/pandas-docs/stable/generated/pandas.DataFrame.to_excel.html for other options.

Harder way: You already have an excel and want to write this dataframe as a new sheet, do like this:

import pandas as pd
import openpyxl

excelfilename = "filename.xlsx"
with pd.ExcelWriter(excelfilename, engine="openpyxl") as writer:
    # above: I use openpyxl, you can change this
    writer.book = openpyxl.load_workbook(excelfilename)
    pvt_all.to_excel(writer, "pivot sheet name", index=False)
        # above: index=False to not write dataframe index

Even more complicated: You want to write to a particular cell range, one cell at a time:

import openpyxl
from openpyxl.utils import get_column_letter

wb = openpyxl.load_workbook(excelfilename)
ws = wb["my sheet"]
row = 3
col = 1
data = pvt_all.values
max_row, max_col = data.shape
for r in range(max_row):
   for c in range(max_col):
       ws[get_column_letter(col+c)+str(row+r)] = data[r][c]
# don't forget to save your workbook after this
import pandas as pd;
df_excel = pd.read_excel(".\Table1.xlsx"); #Import existing excel template
df_excel.index = df_excel.index + 2 #As we have 2 empty rows in pandas pivot \
#table, we need to start filling on excel row 2 (df_excel.index + 2)

received = pvt_all.received; #reading received column in pivot table
df_excel["received"] = received; #Copying received column from Pandas to received \
#column in excel

sent = pvt_all.sent; #reading sent column in pivot table
df_excel["sent"] = sent; #Copying sent column from Pandas to sent \
#column in excel

to_send = pvt_all.to_send; #reading to_send column in pivot table
df_excel["to_send"] = to_send; #Copying to_send column from Pandas to to_send \
#column in excel

df_excel.to_excel(".\MyNewExcel.xlsx",index=False); #Writing new excel file to \
#avoid mistakes on original excel template.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM