Unstack `DataFrames` corresponding to entities indexed over multiple sets
gomfy opened this issue · comments
Description
If I attempt to add the lines below to the unit commitment notebook:
units = ampl.get_data("ngen").to_pandas()
units_unstacked = units['ngen'].unstack(level=1)
print(units_unstacked)
I get the following error:
Question
I was wondering if there is a way to convert the DataFrame
to a multi-index one?
That is a Pandas dataframe with tuples as index that you can convert to multi-index as follows:
units = ampl.get_data("ngen").to_pandas()
units.index = pd.MultiIndex.from_tuples(units.index)
print(units)
By default we are returning tuples as index, but that could be changed in a future release. Meanwhile, you can use the workaround above.
Great, thank you! I update the relevant notebook cell accordingly.
FYI unstack()
messes with the ordering of columns (possibly rows too).
Here is what worked to maintain the original ordering of columns:
start_units = ampl.get_data("nstart").to_pandas()
start_units.index = pd.MultiIndex.from_tuples(start_units.index)
# Capture the original order b/c unstack will mess-up the original ordering
original_order = start_units.index.get_level_values(1).unique()
start_units = start_units.unstack(level=1)
# Convert multi-index to simple index
start_units.columns = start_units.columns.get_level_values(1)
# Reindex using the original order
start_units = start_units.reindex(columns=original_order)
display(start_units)
Starting from amplpy v0.11.0, which has just been released, DataFrame.to_pandas uses multi-index by default (f21ee67). The conversion start_units.index = pd.MultiIndex.from_tuples(start_units.index)
is not necessary anymore.