I have this code, it’s working for the first 9 itterations and then I get the SettingWithCopyWarning and it doesnt continue on, what can I do?
df_day = df.copy() date = df_day['Date'] df_day['Day'] = 'N/A' x = 0 for str in df_day: df_day['Day'][x] = datetime.datetime.strptime(date[x], '%d/%m/%Y').weekday() x = x + 1 y = 0 for int in df_day['Day']: if df_day['Day'][y] == 0: df_day['Day'][y] = 'Monday' y = y + 1 elif df_day['Day'][y] == 1: df_day['Day'][y] = 'Tuesday' y = y + 1 elif df_day['Day'][y] == 2: df_day['Day'][y] = 'Wednesday' y = y + 1 elif df_day['Day'][y] == 3: df_day['Day'][y] = 'Thursday' y = y + 1 elif df_day['Day'][y] == 4: df_day['Day'][y] = 'Friday' y = y + 1 elif df_day['Day'][y] == 5: df_day['Day'][y] = 'Saturday' y = y + 1 elif df_day['Day'][y] == 6: df_day['Day'][y] = 'Sunday' y = y + 1 df_day.head(15)
So I have this now, but it still only runs through the first 10 lines of data! Something to do with the first for loop I think! (I know it’s still a for loop but its been requested as being in a for loop!)
x = 0 for int in df_day: if x < length_data_day: df_day.loc[x,'Day'] = datetime.datetime.strptime(date[x], '%d/%m/%Y').weekday() x = x + 1 elif x == length_data_day: end df_day.head(15) y = 0 for int in df_day['Day']: if df_day.loc[y,'Day'] == 0: df_day.loc[y,'Day'] = 'Monday' y = y + 1 elif df_day.loc[y,'Day'] == 1: df_day.loc[y,'Day'] = 'Tuesday' y = y + 1 elif df_day.loc[y,'Day'] == 2: df_day.loc[y,'Day'] = 'Wednesday' y = y + 1 elif df_day.loc[y,'Day'] == 3: df_day.loc[y,'Day'] = 'Thursday' y = y + 1 elif df_day.loc[y,'Day'] == 4: df_day.loc[y,'Day'] = 'Friday' y = y + 1 elif df_day.loc[y,'Day'] == 5: df_day.loc[y,'Day'] = 'Saturday' y = y + 1 elif df_day.loc[y,'Day'] == 6: df_day.loc[y,'Day'] = 'Sunday' y = y + 1 else: df_day.loc[y,'Day'] = 'Error' y = y + 1 df_day.head(15)
Advertisement
Answer
You’re chaining your indexes (e.g., dataframe[col_index][row_index]
.
In general, you should use
dataframe.loc[row_index, col_index]
dataframe.iloc[row_index, col_index]
dataframe.at[row_index, col_index]
dataframe.iat[row_index, col_index]
But in your case, you don’t need any of that. In fact, you rarely need to loop through a dataframe.
In your case, I would do:
day_names= { 0: 'Monday', 1: 'Tuesday', 2: 'Wednesday', 3: 'Thursday', 4: 'Friday', 5: 'Saturday', 6: 'Sunday' } df_day = ( df.assign(Date=lambda df: pandas.to_datetime(df['Date'])) .assign(WeekDayNum=lambda df: df['Date']).dt.weekday) .assign(WeekDayName=lambda df: df['WeekDayNum']).map(day_names)) )
Or, you could be more clever about how your use your date objects:
import numpy import pandas x = ['01/01/2020', '02/01/2020', '03/01/2020', '04/01/2020', '05/01/2020', '06/01/2020', '07/01/2020', '08/01/2020', '09/01/2020'] ( pandas.DataFrame({'DateString': x, 'N': numpy.arange(len(x))}) .assign(Date=lambda df: pandas.to_datetime(df['DateString'], format='%d/%m/%Y')) .assign(Weekday=lambda df: df['Date'].dt.strftime('%A')) )
And that gives me:
DateString N Date Weekday 0 01/01/2020 0 2020-01-01 Wednesday 1 02/01/2020 1 2020-01-02 Thursday 2 03/01/2020 2 2020-01-03 Friday 3 04/01/2020 3 2020-01-04 Saturday 4 05/01/2020 4 2020-01-05 Sunday 5 06/01/2020 5 2020-01-06 Monday 6 07/01/2020 6 2020-01-07 Tuesday 7 08/01/2020 7 2020-01-08 Wednesday 8 09/01/2020 8 2020-01-09 Thursday