Как заполнить недостающие данные в фрейме данных на основе нескольких условий в строке и из приведенных выше данных

#python #pandas #dataframe #conditional-formatting

Вопрос:

У меня есть следующий фрейм данных,

 ID      LineID  TeamID  ShiftID DateTime        Production  Theoretical  Scrap
1       3       1       NULL    18/6/2020 4:00  482.5291    511.2351     
2       2       1       NULL    18/6/2020 5:00  467.8704    519.9842
3       1       1       NULL    18/6/2020 5:00  390.5945    480.2252    
2186    3       1       NULL    18/6/2020 5:00  0                        0.5
2520    2       1       NULL    18/6/2020 5:00  0                        21
2840    1       1       NULL    18/6/2020 6:00  0                        12
4       1       1       NULL    18/6/2020 6:00  389.2222    480.2252        
5       3       1       NULL    18/6/2020 6:00  516.0907    511.2351    
6       2       1       NULL    18/6/2020 6:00  450.5216    519.9842    
7       3       1       NULL    18/6/2020 6:00  397.9998    511.2351    
8       2       1       NULL    18/6/2020 7:00  456.9486    519.9842    
9       1       1       NULL    18/6/2020 7:00  414.6932    480.2252        
1939    2       1       NULL    18/6/2020 7:00  0                        24
2462    3       1       NULL    18/6/2020 7:00  0                        3
3075    1       1       NULL    18/6/2020 7:00  0                        3.5
1
......
......
......
114678  1       1       NULL    18/6/2018 22:00 343.5955        
114798  3       1       NULL    18/6/2018 22:00 191.2512        
114888  2       1       NULL    18/6/2018 22:00 190.5125        
114657  2       1       NULL    18/6/2018 22:00 414.6432        
114738  1       1       NULL    18/6/2018 22:00 429.43      
114885  3       1       NULL    18/6/2018 23:00 361.3246        
114756  1       1       NULL    18/6/2018 23:00 409.51      

 

Мне нужно заполнить столбцы, где Теоретический пуст, но только там, где лом также пуст.

Таким образом, условие состоит в том , что когда LineID является 3 теоретическим всегда 511.2351 , когда его 2 теоретическое значение всегда 519,9842, а когда 1 его значение всегда 480,2252. Но когда есть стоимость лома, теоретическая должна быть пустой.

Похоже, я не могу придумать метод прямой заливки таким образом.

Я попробовал следующий код, но все остальные строки становятся NaN, кроме этих строк.

 df['Theoretical'] = np.select([(df['LineID']==3) amp; (df['Production']>0) amp; (df['Theoretical']==0) amp; (df['Scrap']==0),
                        (df['LineID']==2) amp; (df['Production']>0) amp; (df['Theoretical']==0) amp; (df['Scrap']==0),
                        (df['LineID']==1) amp; (df['Production']>0) amp; (df['Theoretical']==0) amp; (df['Scrap']==0),],
                       (511.2351,519.9842,480.2252), np.nan)
 
 
ID      LineID  TeamID  ShiftID DateTime        Production  Theoretical  Scrap
1       3       1       NULL    18/6/2020 4:00  
2       2       1       NULL    18/6/2020 5:00  
3       1       1       NULL    18/6/2020 5:00 
2186    3       1       NULL    18/6/2020 5:00  
2520    2       1       NULL    18/6/2020 5:00  
2840    1       1       NULL    18/6/2020 6:00  
4       1       1       NULL    18/6/2020 6:00      
5       3       1       NULL    18/6/2020 6:00  
6       2       1       NULL    18/6/2020 6:00     
7       3       1       NULL    18/6/2020 6:00   
8       2       1       NULL    18/6/2020 7:00    
9       1       1       NULL    18/6/2020 7:00   
1939    2       1       NULL    18/6/2020 7:00 
2462    3       1       NULL    18/6/2020 7:00  
3075    1       1       NULL    18/6/2020 7:00  
1
......
......
......
114678  1       1       NULL    18/6/2018 22:00 343.5955    480.2252    
114798  3       1       NULL    18/6/2018 22:00 191.2512    511.2351        
114888  2       1       NULL    18/6/2018 22:00 190.5125    519.9842    
114657  2       1       NULL    18/6/2018 22:00 414.6432    519.9842
114738  1       1       NULL    18/6/2018 22:00 429.43      480.2252
114885  3       1       NULL    18/6/2018 23:00 361.3246    511.2351    
114756  1       1       NULL    18/6/2018 23:00 409.51      480.2252

 

Мне нужно, чтобы все было так

 ID      LineID  TeamID  ShiftID DateTime        Production  Theoretical  Scrap
1       3       1       NULL    18/6/2020 4:00  482.5291    511.2351    
2       2       1       NULL    18/6/2020 5:00  467.8704    519.9842
3       1       1       NULL    18/6/2020 5:00  390.5945    480.2252    
2186    3       1       NULL    18/6/2020 5:00  0                        0.5
2520    2       1       NULL    18/6/2020 5:00  0                        21
2840    1       1       NULL    18/6/2020 6:00  0                        12
4       1       1       NULL    18/6/2020 6:00  389.2222    480.2252        
5       3       1       NULL    18/6/2020 6:00  516.0907    511.2351    
6       2       1       NULL    18/6/2020 6:00  450.5216    519.9842    
7       3       1       NULL    18/6/2020 6:00  397.9998    511.2351    
8       2       1       NULL    18/6/2020 7:00  456.9486    519.9842    
9       1       1       NULL    18/6/2020 7:00  414.6932    480.2252        
1939    2       1       NULL    18/6/2020 7:00  0                        24
2462    3       1       NULL    18/6/2020 7:00  0                        3
3075    1       1       NULL    18/6/2020 7:00  0                        3.5
1
......
......
......
114678  1       1       NULL    18/6/2018 22:00 343.5955    480.2252    
114798  3       1       NULL    18/6/2018 22:00 191.2512    511.2351        
114888  2       1       NULL    18/6/2018 22:00 190.5125    519.9842    
114657  2       1       NULL    18/6/2018 22:00 414.6432    519.9842
114738  1       1       NULL    18/6/2018 22:00 429.43      480.2252
114885  3       1       NULL    18/6/2018 23:00 361.3246    511.2351    
114756  1       1       NULL    18/6/2018 23:00 409.51      480.2252    

 

Ответ №1:

Конечно, это не лучшее решение, но вы можете попробовать что-то вроде следующего

 df_new = pd.DataFrame({
    "LineID":[1, 2, 3, 1, 2, 1, 1, 2, 3, 1, 2, 1], 
    "Theoretical": [480.2252, 519.9842, 511.2351, np.nan, np.nan, np.nan, np.nan, np.nan, np.nan, np.nan, np.nan, np.nan],
    "Scrap": [np.nan, 0.5, 21, np.nan, 24, np.nan, 40, 34,  np.nan, 0.4,  np.nan, 10]
})

df_new 
    LineID  Theoretical     Scrap
0   1   480.2252    NaN
1   2   519.9842    0.5
2   3   511.2351    21.0
3   1   NaN     NaN
4   2   NaN     24.0
5   1   NaN     NaN
6   1   NaN     40.0
7   2   NaN     34.0
8   3   NaN     NaN
9   1   NaN     0.4
10  2   NaN     NaN
11  1   NaN     10.0

df_new.loc[(df_new["Theoretical"].isna()) amp; (df_new["Scrap"].isna()) amp; (df_new["LineID"] == 3), "Theoretical"] = 511.2351
df_new.loc[(df_new["Theoretical"].isna()) amp; (df_new["Scrap"].isna()) amp; (df_new["LineID"] == 2), "Theoretical"] = 519.9842
df_new.loc[(df_new["Theoretical"].isna()) amp; (df_new["Scrap"].isna()) amp; (df_new["LineID"] == 1), "Theoretical"] = 480.2252

df_new

    LineID  Theoretical     Scrap
0   1   480.2252    NaN
1   2   519.9842    0.5
2   3   511.2351    21.0
3   1   480.2252    NaN
4   2   NaN     24.0
5   1   480.2252    NaN
6   1   NaN     40.0
7   2   NaN     34.0
8   3   511.2351    NaN
9   1   NaN     0.4
10  2   519.9842    NaN
11  1   NaN     10.0
 

Комментарии:

1. да, вы правы, вторым условием было не null (), и вам также нужна isna (). Я обновил код. Пробовать снова.

2. я надеюсь, что есть лучший способ сделать это, лол, я тоже придумал что-то подобное