Ich habe Matrix Factorization, die Grundlage des empfohlenen Modells, in Python implementiert.
Es ist ein System, das die Präferenz für einen Artikel vorhersagt und einem bestimmten Benutzer den am besten geeigneten Artikel präsentiert. Beispiele für die Implementierung als Service sind die "Empfohlenen Produkte für Sie" von Amazon und die "Empfohlenen Videos" von Youtube.
Ein Algorithmus, der häufig in Empfehlungen verwendet wird.
Basierend auf den Bewertungswertinformationen für das Element des Benutzers wird der Bewertungswert des Elements vorhergesagt, das nicht bewertet wurde, und derjenige, der wahrscheinlich einen hohen Bewertungswert aufweist, wird empfohlen.
Erstens gibt es eine Matrix (A), die aus m Benutzern und n Elementen besteht, und jeder Wert darin ist ein Bewertungswert für ein Element durch einen bestimmten Benutzer. Diese Matrix (A) wird in eine Benutzermatrix (U) zerlegt, die aus Benutzern und latenten Variablen (P) besteht, und eine Elementmatrix (I), die aus Elementen und latenten Variablen (Q) besteht.
Der Wert, der durch Nehmen des inneren Produkts der Benutzermatrix und der Artikelmatrix erhalten wird, wird als vorhergesagter Wert verwendet. Der Parameter wird viele Male aktualisiert, bis der Fehler zwischen dem vorhergesagten Wert und dem richtigen Antwortwert unter den Schwellenwert fällt oder die Anzahl der Wiederholungen eine bestimmte Anzahl überschreitet.
Wir haben https://grouplens.org/datasets/movielens/100k/ als Datensatz übernommen.
import numpy as np
import random
import pandas as pd
import math
class MFx(object):
#Stellen Sie jede Variable ein
def __init__(self,K=20,alpha=1e-6,beta=0.0):
self.K=K
self.alpha=alpha
self.beta=beta
def fit(self,X,n_user,n_item,n_iter=100):
self.R=X.copy()
self.samples=X.copy()
#Anfangswert für latente Faktorvariable einstellen
self.user_factors = np.random.rand(n_user,self.K)
self.item_factors = np.random.rand(n_item,self.K)
#stochastic gradient descent
self.loss=[]
for i in range(n_iter):
self.sgd()
mse=self.mse()
self.loss.append((i,mse))
def sgd(self):
np.random.shuffle(self.samples)
for user,item,rating in self.samples:
err=rating-self.predict_pair(user,item)
#update parameter
self.user_factors[user] += self.alpha*(err*self.item_factors[item]-self.beta*self.user_factors[user])
self.item_factors[item] += self.alpha*(err*self.user_factors[user]-self.beta*self.item_factors[item])
def mse(self):
predicted = self.predict(self.R)
error=np.hstack((self.R,np.array(predicted).reshape(-1,1)))
error=np.sqrt(pow((error[:,2]-error[:,3]),2).mean())
return error
#Vorhersagewertbewertung für einen bestimmten Gegenstand durch einen bestimmten Benutzer (inner ist das innere Produkt von Vektoren)
def predict_pair(self,user,item):
return np.inner(self.user_factors[user],self.item_factors[item])
def predict(self,X):
rate=[]
for row in X:
rate.append(self.predict_pair(row[0],row[1]))
return rate
def get_full_matrix(self):
return np.inner(self.user_factors,self.item_factors)
#Daten gelesen
def load_ml100k():
samples=pd.read_csv('data/ml-100k/u.data',sep='\t',header=None)
samples=samples.iloc[:,:3]
samples.columns=['user','item','rate']
samples['user']=samples['user']-1
samples['item']=samples['item']-1
return samples
#Datensatz zum Array-Typ
df = np.array(load_ml100k())
#Löschen Sie denselben Wert und zählen Sie die Anzahl der Benutzer und Elemente
n_user=np.unique(df[:,0]).max()+1
n_item=np.unique(df[:,1]).max()+1
n_rate=np.unique(df[:,2]).max()
#Zufällige Reihenfolge
random.shuffle(df)
#80% der Gesamtgröße sind für das Training bestimmt, der Rest für Tests
train_size=int(df.shape[0]*0.8)
train_df=df[:train_size]
test_df=df[train_size:]
#MF
MF=MFx(K=20,alpha=0.01,beta=0.5)
MF.fit(train_df,n_user,n_item,n_iter=10)
Die folgenden zwei Bewertungen wurden für die Empfehlungsgenauigkeit vorgenommen.
Finden Sie den quadratischen Fehler zwischen dem vorhergesagten Wert und dem richtigen Antwortwert und berechnen Sie den Durchschnitt. Je niedriger der Wert, desto genauer die Empfehlung.
#Sagen Sie den Bewertungswert des Elements in den Testdaten voraus
pre=MF.predict(test_df)
#f=np.array(pre)
#print(type(test_df))
#Erstellen Sie eine Matrix mit dem vorhergesagten Wert nach dem Auswertungswert der Testdaten
ret1=np.hstack((test_df, np.array(pre).reshape(-1, 1)))
#Berechnen Sie den durchschnittlichen quadratischen Fehler zwischen dem vorhergesagten Wert und dem tatsächlichen Bewertungswert
print("pred")
print(np.sqrt(pow((ret1[:,2]-ret1[:,3]),2).mean()))
NDCG Erstellen Sie ein Ranking basierend auf dem richtigen Antwortwert und ein Ranking basierend auf dem vorhergesagten Wert. Vergleichen Sie die beiden Rankings und messen Sie, wie nahe das vorhergesagte Ranking am richtigen Ranking liegt. Der Bereich der NDCG-Werte liegt zwischen 0 und 1, und je näher er an 1 liegt, desto besser wird das Ranking generiert.
def get_dcg(f):
dcg=0.0
s=1
if type(f[0])==float:
f=[f]
for i in f:
if s==1:
dcg+=i[0]
s+=1
else:
dcg+=i[0]/math.log2(s)
s+=1
return dcg
def get_ndcgs(pre):
user=[]
x=[]
for i in np.argsort(pre[:,0]):
user.append(pre[i][0])
x.append(pre[i])
users=list(set(user))
columns=['user','item','real','pred']
y=pd.DataFrame(data=pre, columns=columns, dtype='float')
y.set_index("user",inplace=True)
y_real=y.sort_values(['user','real'],ascending=[True, False])
y_pred=y.sort_values(['user','pred'],ascending=[True, False])
ndcg=0
fff=users
for ii in fff:
fr=y_real.loc[ii,"real":"pred"].values.tolist()
fp=y_pred.loc[ii,"real":"pred"].values.tolist()
ndcg+=get_dcg(fp)/get_dcg(fr)
return ndcg/len(fff)
print("NDCG")
print(get_ndcgs(ret1[:,:4]))
Recommended Posts