2016-09-09 4 views
1

meine erste Pipeline für sklearn Schreiben ich auf einige Probleme gestoßen, wenn nur eine Teilmenge der Spalten in eine Rohrleitung gelegt wird:sklearn Funktion Transformator in Pipeline

mydf = pd.DataFrame({'classLabel':[0,0,0,1,1,0,0,0], 
        'categorical':[7,8,9,5,7,5,6,4], 
        'numeric1':[7,8,9,5,7,5,6,4], 
        'numeric2':[7,8,9,5,7,5,6,"N.A"]}) 
columnsNumber = ['numeric1'] 
XoneColumn = X[columnsNumber] 

Ich benutze die functionTransformer wie:

def extractSpecificColumn(X, columns): 
    return X[columns] 

pipeline = Pipeline([ 
    ('features', FeatureUnion([ 
     ('continuous', Pipeline([ 
      ('numeric', FunctionTransformer(columnsNumber)), 
      ('scale', StandardScaler()) 
     ])) 
    ], n_jobs=1)), 
    ('estimator', RandomForestClassifier(n_estimators=50, criterion='entropy', n_jobs=-1)) 
]) 

cv.cross_val_score(pipeline, XoneColumn, y, cv=folds, scoring=kappaScore) 

Ergebnis: TypeError: 'list' object is not callable wenn der Funktionsumwandler aktiviert ist.

edit:

Wenn ich ein ColumnExtractor wie instanziiert unten kein Fehler zurückgegeben. Aber ist das functionTransformer nicht nur für einfache Fälle wie dieses gedacht und sollte einfach funktionieren?

class ColumnExtractor(TransformerMixin): 
    def __init__(self, columns): 
     self.columns = columns 

    def transform(self, X, *_): 
     return X[self.columns] 

    def fit(self, *_): 
     return self 
+0

sollte nicht 'XoneColumn = X [columnsNumber]' sei 'XoneColumn = mydf [columnsNumber]'? – EdChum

+0

auch Blick auf Frage 2 in Ihrem GitHub die Indizes, die von 'train_test_split' zurückgegeben werden, sind die Ordnungsindexwerte, so empfehle ich' .iloc' auf dem dfs 'X_train = X.iloc [train_index] X_test = X.iloc [ test_index] y_train = y.iloc [train_index] y_test = y.iloc [test_index] ' – EdChum

+1

der sklearn-code geht davon aus, dass alles ein np-array ist, also hast du die wahl, entweder dein pandas df in ein np-array umzuwandeln .Werte 'oder um die' Pandas' Indexer wie 'iloc',' loc' und 'ix' – EdChum

Antwort

1

FunctionTransformer auf „Lift“, eine Funktion zu einer Transformation verwendet, die ich denke, mit einigen Daten Reinigungsschritte helfen kann. Stellen Sie sich vor, Sie haben ein überwiegend numerisches Array und möchten es mit einem Transformer transformieren, der Fehler ausgibt, wenn es eine nan (wie Normalize) bekommt. Sie könnten mit so etwas wie

df.fillna(0, inplace=True) 
... 
cross_val_score(pipeline, ...) 

beenden, aber vielleicht Sie, dass fillna nur in einer Transformation erforderlich, um stattdessen die fillna wie oben zu haben, Sie haben

normalize = make_pipeline(
    FunctionTransformer(np.nan_to_num, validate=False), 
    Normalize() 
) 

, die es, wie Sie die Normalisierung endet wollen. Dann können Sie diese Schnipsel an mehr Orten verwenden, ohne den Code mit .fillna(0)

In Ihrem Beispiel Littering, sind Sie in ['numeric1'] vorbei, das ist ein list und nicht ein Extraktor wie die ähnlich df[['numeric1']] getippt. Was können Sie stattdessen wollen, ist eher wie

FunctionTransformer(operator.itemgetter(columns)) 

aber, dass immer noch nicht funktionieren, weil das Objekt, das schließlich in den FunctionTransformer geleitet wird ein np.array und keine DataFrame sein.

Um Operationen für bestimmte Spalten eines DataFrame auszuführen, möchten Sie möglicherweise eine Bibliothek wie sklearn-pandas verwenden, mit der Sie bestimmte Transformatoren nach Spalte definieren können.

Verwandte Themen