У меня есть датафрейм, как показано ниже. + ---------- + ------- + ----- + ------- + ------- + ----- + | Дата | А | B | C | D | E | + ---------- + ------- + ----- + ------- + ------- + ----- + | 1-янв-21 | 1,089 | ...

1
Tommy 12 Фев 2021 в 10:34

1 ответ

Лучший ответ

Вы можете сортировать значения по sorted по столбцам с параметром keys, а затем изменять index по списку:

df = df.set_index('Date').apply(lambda x: pd.Series(sorted(x, key=pd.notna)))
df.index = [f't-{x}' if x!=0 else 't' for x in range(len(df)-1, -1, -1)]

print (df)
        A      B       C       D      E
t-4  1089    NaN     NaN     NaN    NaN
t-3   609    NaN   491.0     NaN    NaN
t-2  1440  547.0   184.0   195.0  665.0
t-1   704  824.0   345.0  1091.0  969.0
t     297  632.0  1426.0   512.0  555.0

В numpy можно использовать очень красивую функцию @Divakar:

df = df.drop('Date', axis=1)
#https://stackoverflow.com/a/44559180/2901002
df = pd.DataFrame(justify(df.to_numpy(), invalid_val=np.nan, axis=0, side='down'), 
                  columns=df.columns)

df.index = [f't-{x}' if x!=0 else 't' for x in range(len(df)-1, -1, -1)]

print (df)
          A      B       C       D      E
t-4  1089.0    NaN     NaN     NaN    NaN
t-3   609.0    NaN   491.0     NaN    NaN
t-2  1440.0  547.0   184.0   195.0  665.0
t-1   704.0  824.0   345.0  1091.0  969.0
t     297.0  632.0  1426.0   512.0  555.0

Если нужен первый столбец Time, используйте DataFrame.insert:

L = [f't-{x}' if x!=0 else 't' for x in range(len(df)-1, -1, -1)]

df.insert(0, 'Time', L)
print (df)
  Time       A      B       C       D      E
0  t-4  1089.0    NaN     NaN     NaN    NaN
1  t-3   609.0    NaN   491.0     NaN    NaN
2  t-2  1440.0  547.0   184.0   195.0  665.0
3  t-1   704.0  824.0   345.0  1091.0  969.0
4    t   297.0  632.0  1426.0   512.0  555.0
3
jezrael 12 Фев 2021 в 07:58
66167897