PCA y la división de tren / prueba / validación

Aug 19 2020

Tengo un problema de clasificación binaria con 1149 observaciones y 13,454 predictores. Quiero aplicar la metodología descrita por cbeleites descontentos con SX en PCA y la división de tren / prueba .

En este contexto, tengo dos preguntas:

(i) Si hago una búsqueda en la cuadrícula de la cantidad de PC a usar, ¿es incorrecto probar una cantidad de PC para usar que sea mayor que la cantidad de observaciones en el conjunto de prueba? Me parece intuitivo que el número máximo de PC que deben probarse en la búsqueda de la cuadrícula debe ser igual o menor que el número de observaciones en el conjunto de prueba (supuestamente para evitar una situación p >> n).

(ii) ¿Es más correcto usar un set de reserva? es decir, utilice primero una validación cruzada de 10 veces para encontrar el número óptimo de PC utilizando el 90% de los datos según lo descrito por cbeleites descontentos con SX , luego ajuste un nuevo estimador utilizando el número óptimo de PC utilizando todos los datos que se utilizaron en el ¿El primer paso predice la probabilidad de las clases de la reserva?

EDITAR Para ser más claro, mi código se parece a esto:

tests=[]
pps=[]
pcs=[]
skf=model_selection.StratifiedKFold(n_splits=10,random_state=61,shuffle=True)

for i in (2,5,10,25,50,100,114):

    tmp_pps=[]
    tmp_tests=[]

    for train_index, test_index in skf.split(X, y):
    
        estimator = SVC(probability=True)
        pca = PCA(i, svd_solver='arpack')
        scaler= StandardScaler()
    
        X_train, X_test = X[train_index], X[test_index]
        y_train, y_test = y[train_index], y[test_index]
    
        fScaler = scaler.fit(X_train)
        X_train_scaled = fScaler.transform(X_train)
        X_test_scaled = fScaler.transform(X_test)
    
        fpca = pca.fit(X_train_scaled)
        X_train_PCA = pca.transform(X_train_scaled)
        X_test_PCA = pca.transform(X_test_scaled)
    
        ft = estimator.fit(X_train_PCA, y_train)
        pp = estimator.predict_proba(X_test_PCA)[:, 1]
    
        tmp_tests.append(y_test)
        tmp_pps.append(pp)
    
    tests.append(tmp_tests)
    pps.append(tmp_pps)
    pcs.append(i)

for i in range(len(pcs)):
    pp = np.concatenate(res[i]).ravel()
    y_test = np.concatenate(tests[i]).ravel()
    score = roc_auc_score(y_test, pp)
    print(pcs[i],score)

¿Es este un enfoque incorrecto / sesgado?

Respuestas

gunes Aug 19 2020 at 01:30

i) Sí, el número de PC debe ser menor o igual al número de observaciones porque la matriz de datos (suponga la media normalizada sin pérdida de generalidad), $X_{n\times p}$, tiene rango $\leq \min(n,p)=n$, en este caso. $X^TX$ tendrá rango $\leq n$ también porque $\text{rank}(AB)\leq \text{rank}(A)$.

ii) Dado que tiene un número reducido de observaciones, podría ser mejor utilizar la validación cruzada para elegir el mejor número de PC. Necesita encontrar un criterio (por ejemplo, cubrir una variación del 95%) y un esquema de votación adecuado para fusionar decisiones provenientes de diferentes pliegues. Al final, puedes usar todos tus datos de entrenamiento para encontrar las PC. El equipo de prueba debe estar separado del principio, es decir, no debe usarlo ni siquiera para seleccionar el número de PC.