Spark ALS: recomendación para nuevos usuarios

10

La pregunta

¿Cómo pronostico la calificación de un nuevo usuario en un modelo ALS capacitado en Spark? (Nuevo = no visto durante el tiempo de entrenamiento)

El problema

Estoy siguiendo el tutorial oficial de Spark ALS aquí:

http://ampcamp.berkeley.edu/big-data-mini-course/movie-recommendation-with-mllib.html

Puedo construir un buen recomendador con un MSE decente, pero estoy luchando con la forma de ingresar nuevos datos al modelo. El tutorial cambia las calificaciones del primer usuario antes del entrenamiento, pero esto es realmente un truco. Dan la siguiente pista:

9.2. Factores de matriz de aumento:

En este tutorial, agregamos sus calificaciones al conjunto de entrenamiento. Una mejor manera de obtener las recomendaciones para usted es entrenar primero un modelo de factorización matricial y luego aumentar el modelo utilizando sus calificaciones. Si esto le parece interesante, puede echar un vistazo a la implementación de MatrixFactorizationModel y ver cómo actualizar el modelo para nuevos usuarios y nuevas películas.

Sin embargo, la implementación no me ayuda en absoluto. Idealmente, estoy buscando algo como:

predictions = model.predictAllNew(newinput)

Pero no existe tal método. Podría ir y modificar el RDD original, pero creo que eso requeriría que vuelva a entrenar el modelo, por lo que tampoco sería una solución ideal. ¿Seguramente debe haber una manera más elegante?

Donde estoy ahora:

Creo que necesito encontrar la representación latente del nuevo vector. De acuerdo con el documento original , podemos calcular esto así:

Xu=(YTCuY+λI)1YTCup(u)

Pero cuando calculo usando los valores en el documento, no coincide con los valores del modelo. Arreglo alfa y el parámetro de regularización, pero creo que la implementación MLLIB tiene una implementación diferente . Se define aquí (ver línea 1304), pero no siendo experto en Scala, esto es muy difícil de realizar ingeniería inversa para mí ...Cu

Mi intento actual:

V = model.productFeatures().map(lambda x: (x[1])).collect() #product latent matrix Y

Cui =  alpha * np.abs(newinput)
Cui =  (1. + Cui) / (Cui)
Cui[np.where(newinput == 0)] = 0
Cui = np.diag(Cui)

lambdaI = len(np.where(newinput!=0)) * regularization_parameter * np.eye(np.shape(V)[1]) #
term   = np.dot(np.dot(Vt,Cui),V)+lambdaI
term   = np.dot(np.linalg.inv(term),Vt)
term   = np.dot(term,Cui)
term   = np.dot(term,newinput)
latentinput = term

Pero esto no coincide.

ciri
fuente

Respuestas:

9

Muchas preguntas aquí. Primero, para un usuario verdaderamente nuevo sin datos, no hay forma de usar un modelo de recomendación. Si literalmente no tiene información sobre el usuario, lo único que puede hacer es proporcionar algunas recomendaciones predeterminadas.

Por supuesto, una vez que tenga datos y pueda reconstruir el modelo para incorporar al usuario, puede hacer recomendaciones. Puedes hacer eso en Spark pero ya lo sabes. Esto llevará demasiado tiempo si necesita agregar información sobre nuevos usuarios en tiempo de ejecución. La técnica que desea se llama "plegar", que se utiliza para descubrir cuál es el nuevo vector de usuario (aproximadamente) dados los elementos con los que interactúa el usuario. Es solo un poco de álgebra lineal y se deduce de la ecuación que das.

Saqué una vieja diapositiva que podría ayudar:

ALS plegable

El "Cu" no es realmente diferente. Agregué una 'extensión' para manejar el caso de entrada negativa, pero es lo mismo para la entrada positiva.

Aquí hay una implementación de pliegue, aunque creo que será demasiado denso para ser de mucho valor:

https://github.com/OryxProject/oryx/blob/2c01d496f93f2825a076eb7fe492aa39a5290aa6/app/oryx-app-common/src/main/java/com/cloudera/oryx/app/als/ALSUtils.java#L74

Calcular el nuevo vector de usuario implícito en una interacción usuario-elemento es un álgebra lineal bastante fácil. La parte difícil que he encontrado es decidir cuánto pesarlo.

Espero que sea un empujón en la dirección correcta.

Sean Owen
fuente