3

I have a dataframe much like the one in this question: Pandas: drop a level from a multi-level column index?

cols = pd.MultiIndex.from_tuples([("a", "b"), ("a", "c")])
pd.DataFrame([[1,2], [3,4]], columns=cols)

    a
   ---+--
    b | c
--+---+--
0 | 1 | 2
1 | 3 | 4

In the question reference above, the questioner wanted to know how to drop the column heading a. I would like to know how to drop it and all the columns underneath it (in this case b) so that the resulting dataframe looks like:

  | c
--+--
0 | 2
1 | 4

can you help me achieve this?

MetaStack
  • 3,266
  • 4
  • 30
  • 67
  • 1
    By "all the columns underneath it" you mean the first column under that header? – Andy Hayden Jan 28 '19 at 00:51
  • As pointed out, `'a'` is the first level label for both columns in your dataframe. So both `'b'` and `'c'` are "under" `'a'`. Could you clarify what your intention is? – busybear Jan 28 '19 at 01:30

4 Answers4

3

Just for clarity, I think both 'b' and 'c' are contained under 'a'. However, you can select which you wish to drop in the following code.

First build the DataFrame:

cols = pd.MultiIndex.from_tuples([("a", "b"), ("a", "c")])
df = pd.DataFrame([[1,2], [3,4]], columns=cols)

Then drop the column ('a','b')... and also drop the 'a' level, leaving you with 'c'.

df.drop([('a', 'b')], axis=1,inplace=True)
df.columns = df.columns.droplevel()

The resulting DataFrame looks like this.

    c
0   2
1   4
run-out
  • 3,114
  • 1
  • 9
  • 25
  • thank you, you're right, my attention to detail was lacking but you knew what I meant. this answer works great – MetaStack Jan 28 '19 at 04:15
1

You can use the following assuming what you call "the column underneath", is the first one.

z['a'].drop(z['a'].columns[0], axis=1)

This is a quick answer based on the result expected, sorry if it seems dumb, but maybe you can be more precise in your question.

Rags
  • 21
  • 3
1

Not sure why you need this but you can using groupby achieve this

df=df.groupby(level=0,axis=0).apply(lambda  x : x.iloc[:,1:])
df.columns=df.columns.get_level_values(1)
df
   c
0  2
1  4
BENY
  • 317,841
  • 20
  • 164
  • 234
0

You could select just that slice from the columns then rename the column header to a single level header:

df.loc(axis=1)[:,'c'].set_axis(['c'], axis=1, inplace=False)

Output:

   c
0  2
1  4
Scott Boston
  • 147,308
  • 15
  • 139
  • 187