I'm trying to rename a single row of a pandas dataframe by it's tuple.
For example:
import pandas as pd
df = pd.DataFrame(data={'i1':[0,0,0,0,1,1,1,1],
'i2':[0,1,2,3,0,1,2,3],
'x':[1.,2.,3.,4.,5.,6.,7.,8.],
'y':[9,10,11,12,13,14,15,16]})
df.set_index(['i1','i2'], inplace=True)
Creates df:
x y
i1 i2
0 0 1.0 9
1 2.0 10
2 3.0 11
3 4.0 12
1 0 5.0 13
1 6.0 14
2 7.0 15
3 8.0 16
I'd like to be able to use something like: df.rename(index={(0,1):(0,9)},inplace=True)
to get:
x y
i1 i2
0 0 1.0 9
9 2.0 10 <-- new key
2 3.0 11
3 4.0 12
1 0 5.0 13
1 6.0 14
2 7.0 15
3 8.0 16
The command executes without raising an error but returns the same df unchanged.
This also returns the same df: df.rename(index={pd.IndexSlice[0,1]:pd.IndexSlice[0,9]},inplace=True)
This will have close to the desired effect:
df.loc[(0,9),:] = df.loc[(0,1),:]
df.drop(index=(0,1),inplace=True)
but if row ordering matters, it'll be a pain to get it into the right order, and possibly quite slow if the df gets big.
I'm using Pandas 1.0.1, python 3.7. Any suggestions? Thank you in advance.
Possible solution with list comprehension and MultiIndex.from_tuples
:
L = [(0,9) if x == (0,1) else x for x in df.index]
df.index = pd.MultiIndex.from_tuples(L, names=df.index.names)
print (df)
x y
i1 i2
0 0 1.0 9
9 2.0 10
2 3.0 11
3 4.0 12
1 0 5.0 13
1 6.0 14
2 7.0 15
3 8.0 16