Apakah scikit-learning memiliki algoritma seleksi maju / bertahap?

37

Saya sedang mengerjakan masalah dengan terlalu banyak fitur dan melatih model saya terlalu lama. Saya menerapkan algoritma pemilihan maju untuk memilih fitur.

Namun, saya bertanya-tanya apakah scikit-belajar memiliki algoritma seleksi / stepwise regresi maju?

Maksud
sumber
Saya membuat kelas saya sendiri untuk itu tetapi sangat terkejut bahwa sklearn tidak memilikinya.
Maksud
1
Menggunakan tes hipotesis adalah metode seleksi fitur yang mengerikan. Anda harus melakukan banyak hal dan tentu saja, Anda akan mendapatkan banyak positif dan negatif palsu.
Ricardo Cruz

Jawaban:

21

Tidak, sklearn tampaknya tidak memiliki algoritme pemilihan maju. Namun, ia menyediakan penghapusan fitur rekursif, yang merupakan algoritma penghapusan fitur serakah mirip dengan seleksi mundur berurutan. Lihat dokumentasi di sini:

http://scikit-learn.org/stable/modules/generated/sklearn.feature_selection.RFE.html

brentlance
sumber
3
Saran yang bagus, tetapi masalah dengan implementasi sci-kit adalah pentingnya fitur dikuantifikasi oleh koefisien model, yaitu jika model memiliki coef_antarmuka. Ini akan mengesampingkan metode berbasis pohon dll. Namun, saya pikir apa yang diminta oleh @Maksud adalah apa yang dijelaskan dalam "Pengantar pembelajaran statistik" oleh James di mana fitur ditambahkan / dihapus secara rekursif oleh kepentingannya yang dikuantifikasi dengan validasi set akurasi . Ini memungkinkan pemilihan fitur di semua jenis model, bukan yang parametrik linier saja.
eggie5
9

Sklearn DOES memiliki algoritma pemilihan maju, meskipun tidak disebut dalam scikit-learn. Metode pemilihan fitur yang disebut F_regress di scikit-learn akan secara berurutan menyertakan fitur yang paling meningkatkan model, sampai ada Kfitur dalam model (K adalah input).

Dimulai dengan regresi label pada setiap fitur secara individual, dan kemudian mengamati fitur mana yang paling meningkatkan model menggunakan F-statistik. Kemudian menggabungkan fitur yang menang ke dalam model. Kemudian beralih ke fitur yang tersisa untuk menemukan fitur berikutnya yang paling meningkatkan model, sekali lagi menggunakan F-statistik atau uji F. Ia melakukan ini sampai ada fitur K dalam model.

Perhatikan bahwa fitur yang tersisa yang berkorelasi dengan fitur yang dimasukkan ke dalam model mungkin tidak akan dipilih, karena mereka tidak berkorelasi dengan residu (meskipun mereka mungkin berkorelasi baik dengan label). Ini membantu menjaga dari multi-collinearity.

Candic3
sumber
1
Namun waspadalah
Candic3
1
Maksud Anda Select K-best ?
Nitro
iya nih. Anda juga harus membaca ini: stats.stackexchange.com/questions/204141/… .
Candic3
2
Itu semacam seleksi maju. Tapi ini bukan generik - ini khusus untuk model regresi linier, sedangkan pemilihan maju biasanya dapat bekerja dengan model apa pun (model agnostik) seperti RFE dan dapat menangani masalah klasifikasi atau regresi. Tetapi saya curiga kebanyakan orang mencari use case ini dan tentu saja bagus untuk menyebutkannya di sini.
Simon
2
Ini bukan pilihan LANGKAH, karena setiap nilai p dihitung untuk regresi univariat, terlepas dari semua kovariat lainnya.
David Dale
9

Scikit-belajar memang tidak mendukung regresi bertahap. Itu karena apa yang umumnya dikenal sebagai 'regresi bertahap' adalah algoritma yang didasarkan pada nilai-p dari koefisien regresi linier, dan scikit-learning sengaja menghindari pendekatan inferensial untuk model pembelajaran (pengujian signifikansi dll). Selain itu, OLS murni hanyalah salah satu dari banyak algoritma regresi, dan dari sudut pandang scikit-belajar, itu tidak terlalu penting, juga bukan yang terbaik.

Namun, ada beberapa saran bagi mereka yang masih membutuhkan cara yang baik untuk pemilihan fitur dengan model linier:

  1. Gunakan model yang jarang inheren seperti ElasticNetatau Lasso.
  2. Normalisasi fitur Anda dengan StandardScaler, dan kemudian pesan fitur Anda hanya dengan model.coef_. Untuk kovariat yang benar-benar independen, itu sama dengan menyortir berdasarkan nilai-p. Kelas sklearn.feature_selection.RFEakan melakukannya untuk Anda, dan RFECVbahkan akan mengevaluasi jumlah fitur yang optimal.
  3. R2statsmodels
  4. Lakukan seleksi brute-force maju atau mundur untuk memaksimalkan metrik favorit Anda pada validasi silang (bisa memakan waktu sekitar kuadrat dalam jumlah kovariat). mlxtendPaket yang kompatibel scikit-learn mendukung pendekatan ini untuk estimator dan metrik apa saja.
  5. Jika Anda masih menginginkan regresi bertahap vanila, lebih mudah untuk mendasarkannya statsmodels, karena paket ini menghitung nilai-p untuk Anda. Pilihan maju-mundur dasar bisa terlihat seperti ini:

`` `

from sklearn.datasets import load_boston
import pandas as pd
import numpy as np
import statsmodels.api as sm

data = load_boston()
X = pd.DataFrame(data.data, columns=data.feature_names)
y = data.target


def stepwise_selection(X, y, 
                       initial_list=[], 
                       threshold_in=0.01, 
                       threshold_out = 0.05, 
                       verbose=True):
    """ Perform a forward-backward feature selection 
    based on p-value from statsmodels.api.OLS
    Arguments:
        X - pandas.DataFrame with candidate features
        y - list-like with the target
        initial_list - list of features to start with (column names of X)
        threshold_in - include a feature if its p-value < threshold_in
        threshold_out - exclude a feature if its p-value > threshold_out
        verbose - whether to print the sequence of inclusions and exclusions
    Returns: list of selected features 
    Always set threshold_in < threshold_out to avoid infinite looping.
    See https://en.wikipedia.org/wiki/Stepwise_regression for the details
    """
    included = list(initial_list)
    while True:
        changed=False
        # forward step
        excluded = list(set(X.columns)-set(included))
        new_pval = pd.Series(index=excluded)
        for new_column in excluded:
            model = sm.OLS(y, sm.add_constant(pd.DataFrame(X[included+[new_column]]))).fit()
            new_pval[new_column] = model.pvalues[new_column]
        best_pval = new_pval.min()
        if best_pval < threshold_in:
            best_feature = new_pval.argmin()
            included.append(best_feature)
            changed=True
            if verbose:
                print('Add  {:30} with p-value {:.6}'.format(best_feature, best_pval))

        # backward step
        model = sm.OLS(y, sm.add_constant(pd.DataFrame(X[included]))).fit()
        # use all coefs except intercept
        pvalues = model.pvalues.iloc[1:]
        worst_pval = pvalues.max() # null if pvalues is empty
        if worst_pval > threshold_out:
            changed=True
            worst_feature = pvalues.argmax()
            included.remove(worst_feature)
            if verbose:
                print('Drop {:30} with p-value {:.6}'.format(worst_feature, worst_pval))
        if not changed:
            break
    return included

result = stepwise_selection(X, y)

print('resulting features:')
print(result)

Contoh ini akan mencetak output berikut:

Add  LSTAT                          with p-value 5.0811e-88
Add  RM                             with p-value 3.47226e-27
Add  PTRATIO                        with p-value 1.64466e-14
Add  DIS                            with p-value 1.66847e-05
Add  NOX                            with p-value 5.48815e-08
Add  CHAS                           with p-value 0.000265473
Add  B                              with p-value 0.000771946
Add  ZN                             with p-value 0.00465162
resulting features:
['LSTAT', 'RM', 'PTRATIO', 'DIS', 'NOX', 'CHAS', 'B', 'ZN']
David Dale
sumber
Kode regresi bertahap yang diposting ke depan tidak berfungsi dengan benar. Seharusnya memberikan hasil yang identik dengan mundur mundur bertahap, tetapi tidak. Ini adalah faktor pengembalian dengan nilai p yang lebih tinggi dari ambang batas ketika Anda menjalankan kembali regresi. Saya juga menjalankan dataset yang sama dengan STATA dan ambang yang sama menggunakan mundur secara bertahap dan mendapatkan hasil yang berbeda secara material. Pada dasarnya, jangan gunakan itu. Saya akan menulis kode regresi bertahap mundur saya sendiri menggunakan templatnya.
Michael Corley MBA LSSBB
Kemunduran bertahap maju dan mundur sama sekali tidak dijamin untuk menyatu dengan solusi yang sama. Dan jika Anda menemukan bug dalam solusi saya, silakan lampirkan kode untuk mereproduksinya.
David Dale
1

Sebenarnya ada algoritma yang bagus yang disebut "Forward_Select" yang menggunakan Statsmodels dan memungkinkan Anda untuk mengatur metrik Anda sendiri (AIC, BIC, Adjusted-R-Squared, atau apa pun yang Anda suka) untuk secara progresif menambahkan variabel ke model. Algoritma dapat ditemukan di bagian komentar di halaman ini - gulir ke bawah dan Anda akan melihatnya di dekat bagian bawah halaman.

https://planspace.org/20150423-forward_selection_with_statsmodels/

Saya akan menambahkan bahwa algoritma ini juga memiliki satu fitur yang bagus: Anda dapat menerapkannya pada masalah klasifikasi atau regresi! Anda hanya harus mengatakannya.

Cobalah dan lihat sendiri.

Ram Seshadri
sumber
0

Sebenarnya sklearn tidak memiliki algoritma pemilihan maju, pikir permintaan tarik dengan implementasi menunggu pemilihan fitur maju di repositori Scikit-Learn sejak April 2017.

Sebagai alternatif, ada seleksi mundur maju dan selangkah lebih maju di mlxtend . Anda dapat menemukan dokumen itu di Pemilih Fitur Berurutan

Ynjxsjmh
sumber