0

I have a dataframe (df) which looks like:

0   1                   2                       3
0   BBG.apples.S        BBG.XNGS.bananas.S      0
1   BBG.apples.S        BBG.XNGS.oranges.S      0
2   BBG.apples.S        BBG.XNGS.pairs.S        0
3   BBG.apples.S        BBG.XNGS.mango.S        0
4   BBG.apples.S        BBG.XNYS.mango.S        0
5   BBG.XNGS.bananas.S  BBG.XNGS.oranges.S      0
6   BBG.XNGS.bananas.S  BBG.XNGS.pairs.S        0
7   BBG.XNGS.bananas.S  BBG.XNGS.kiwi.S         0
8   BBG.XNGS.oranges.S  BBG.XNGS.pairs.S        0
9   BBG.XNGS.oranges.S  BBG.XNGS.kiwi.S         0
10  BBG.XNGS.peaches.S  BBG.XNGS.strawberrys.S  0
11  BBG.XNGS.peaches.S  BBG.XNGS.strawberrys.S  0
12  BBG.XNGS.peaches.S  BBG.XNGS.strawberrys.S  0
13  BBG.XNGS.peaches.S  BBG.XNGS.kiwi.S         0

I am trying to update a value (first row, third column) in the dataframe using:

for index, row in df.iterrows():

        status = row[3]

        if int(status) == 0:

            df[index]['3'] = 1

but when I print the dataframe out it remains unchanged.

What am I doing wrong?

halfer
  • 19,824
  • 17
  • 99
  • 186
Stacey
  • 4,825
  • 17
  • 58
  • 99
  • 1
    `iterrows()` only returns a single generator, `index,row` are two values. What value do you want to update? (`df[index]['3']` is supposed to represent what row and what column?) – Chris Apr 01 '17 at 20:49
  • Are you sure your column names are strings (`'3'`) and not integers? This could be causing confusion when you try to access the column. If in doubt, see what you get from print(df.columns). – Craig Apr 01 '17 at 21:06

4 Answers4

1

You can't modify a data frame by iterating like that. See here.

If you only want to modify the element at [1, 3], you can access it directly:

df[1, 3] = 1

If you're trying to turn every 0 in column 3 to a 1, try this:

df[df['3'] == 0] = 1

EDIT: In addition, the docs for iterrows say that you'll often get a copy back, which is why the operation fails.

Community
  • 1
  • 1
Arya McCarthy
  • 8,554
  • 4
  • 34
  • 56
1

Replace your last line by:

df.at[index,'3'] = 1

Obviously as mentioned by others you're better off using a vectorized expression instead of iterating, especially for large dataframes.

alex314159
  • 3,159
  • 2
  • 20
  • 28
0

If you are trying to update the third column for all rows based on the row having a certain value, as shown in your example code, then it would be much easier use the where method on the dataframe:

df.loc[:,'3'] = df['3'].where(df['3']!=0, 1)
Craig
  • 4,605
  • 1
  • 18
  • 28
0

Try to update the row using .loc or .iloc (depend on your needs).
For example, in this case:

if int(status) == 0:
    df.iloc[index]['3']='1'
Avi
  • 1
  • 3