2017-03-16 1 views
0

ich einen Datenrahmen haben, die wie folgt aussieht:Padded Daten in Pandas Dataframe Überprüfung auf bestimmte Spalten

import numpy as np 
raw_data = {'Series_Date':['2017-03-10','2017-03-13','2017-03-14','2017-03-15'],'SP':[35.6,56.7,41,41],'1M':[-7.8,56,56,-3.4],'3M':[24,-31,53,5]} 
import pandas as pd 
df = pd.DataFrame(raw_data,columns=['Series_Date','SP','1M','3M']) 
print df 

nur möchte ich einen Test auf bestimmte Spalten in diesem Datenrahmen ausführen, werden alle Spaltennamen in dieser Liste:

check = {'1M','SP'} 
print check 

Für diese Spalten, würde ich gerne wissen, wenn die Werte in diesen beiden Spalten gleich dem Wert des Vortages ist. So ist der Ausgangsdatenrahmen sollte Serie Datum und einen Kommentar, wie (zum Beispiel in diesem Fall zurückkehren :)

output_data = {'Series_Date':['2017-03-14','2017-03-15'],'Comment':["Value for 1M data is same as previous day","Value for SP data is same as previous day"]} 
output_data_df = pd.DataFrame(output_data,columns = ['Series_Date','Comment']) 
print output_data_df 

Könnten Sie bitte etwas Unterstützung geben, wie damit umgehen?

Antwort

0

Ich bin mir nicht sicher, es ist der sauberste Weg, es zu tun. Allerdings funktioniert es

check = {'1M', 'SP'} 
prev_dict = {c: None for c in check} 

def check_prev_value(row): 
    global prev_dict 
    msg = "" 
    # MAYBE add clause to check if both are equal 
    for column in check: 
     if row[column] == prev_dict[column]: 
      msg = 'Value for %s data is same as previous day' % column 
     prev_dict[column] = row[column] 
    return msg 

df['comment'] = df.apply(check_prev_value, axis=1) 

output_data_df = df[df['comment'] != ""] 
output_data_df = output_data_df[["Series_Date", "comment"]].reset_index(drop=True) 

Für Ihre Eingabe:

Series_Date SP 1M 3M 
0 2017-03-10 35.6 -7.8 24 
1 2017-03-13 56.7 56.0 -31 
2 2017-03-14 41.0 56.0 53 
3 2017-03-15 41.0 -3.4 5 

Die Ausgabe lautet:

Series_Date         comment 
0 2017-03-14 Value for 1M data is same as previous day 
1 2017-03-15 Value for SP data is same as previous day 
+0

Danke bu t Was wäre, wenn ich nach anderen Spalten wie SP, SP oder 3M suchen würde? Ich möchte, dass meine Spalten gemäß den Spalten in der 'Prüfliste' getestet werden. – sg91

+0

Ich habe den Code aktualisiert. Jetzt wird nach Spalten gesucht, die in der Liste angezeigt werden – AndreyF

0

Die folgende tut mehr oder weniger, was Sie wollen. Columns item_ok werden dem ursprünglichen Datenrahmen Spezifizierungs hinzugefügt, wenn der Wert der gleiche wie Vortages ist oder nicht:

from datetime import timedelta 
df['Date_diff'] = pd.to_datetime(df['Series_Date']).diff() 
for item in check: 
    df[item+'_ok'] = (df[item].diff() == 0) & (df['Date_diff'] == timedelta(1)) 
df_output = df.loc[(df[[item + '_ok' for item in check]]).any(axis=1)] 
0

Referenz: this answer

cols = ['1M','SP'] 
for col in cols: 
    df[col + '_dup'] = df[col].groupby((df[col] != df[col].shift()).cumsum()).cumcount() 

Output Spalte eine ganze Zahl größer als Null aufweisen, wenn ein Duplikat gefunden.

df: 

    Series_Date SP 1M 3M 1M_dup SP_dup 
0 2017-03-10 35.6 -7.8 24  0  0 
1 2017-03-13 56.7 56.0 -31  0  0 
2 2017-03-14 41.0 56.0 53  1  0 
3 2017-03-15 41.0 -3.4 5  0  1 

Scheibe dups zu finden:

col = 'SP' 
dup_df = df[df[col + '_dup'] > 0][['Series_Date', col + '_dup']] 

dup_df: 

    Series_Date SP_dup 
3 2017-03-15  1 

Hier ist eine Funktion Version des oben (mit dem zusätzlichen Merkmal mehrere Spalten der Handhabung):

import pandas as pd 
import numpy as np 

def find_repeats(df, col_list, date_col='Series_Date'): 
    dummy_df = df[[date_col, *col_list]].copy() 
    dates = dummy_df[date_col] 
    date_series = [] 
    code_series = [] 
    if len(col_list) > 1: 
     for col in col_list: 
      these_repeats = df[col].groupby((df[col] != df[col].shift()).cumsum()).cumcount().values 
      repeat_idx = list(np.where(these_repeats > 0)[0]) 
      date_arr = dates.iloc[repeat_idx] 
      code_arr = [col] * len(date_arr) 
      date_series.extend(list(date_arr)) 
      code_series.extend(code_arr) 
     return pd.DataFrame({date_col: date_series, 'col_dup': code_series}).sort_values(date_col).reset_index(drop=True) 
    else: 
     col = col_list[0] 
     dummy_df[col + '_dup'] = df[col].groupby((df[col] != df[col].shift()).cumsum()).cumcount() 
     return dummy_df[dummy_df[col + '_dup'] > 0].reset_index(drop=True) 

find_repeats(df, ['1M']) 

    Series_Date 1M 1M_dup 
0 2017-03-14 56.0  1 

find_repeats(df, ['1M', 'SP']) 

    Series_Date col_dup 
0 2017-03-14  1M 
1 2017-03-15  SP 

Und hier ist eine andere Art und Weise mit pandas diff:

def find_repeats(df, col_list, date_col='Series_Date'): 
    code_list = [] 
    dates = list() 

    for col in col_list: 
     these_dates = df[date_col].iloc[np.where(df[col].diff().values == 0)[0]].values 
     code_arr = [col] * len(these_dates) 
     dates.extend(list(these_dates)) 
     code_list.extend(code_arr) 
    return pd.DataFrame({date_col: dates, 'val_repeat': code_list}).sort_values(date_col).reset_index(drop=True) 
Verwandte Themen