예제 #1
0
/**
 * Iteratively train each feature on the entire data set
 * Once sufficient progress has been made, move on
 */
void SvdOrder::calculateFeatures()
{
    qDebug() << "Training";

    // Keep looping until you have passed the maximum number
    // of epochs or have stopped making significant progress
    double prevRMSE = 1e8;
    double RMSE     = 1e7;
    Movie movie(currDb);
    double averageRating = currDb->getAverageRating();
    for (unsigned int i = 0;
         i < MIN_EPOCHS || 
            (i < MAX_EPOCHS && (prevRMSE - RMSE) > MIN_IMPROVEMENT);
         i++)
    {
        prevRMSE = RMSE;
        RMSE = 0;

        User user(currDb,6);
        int numUsers = currDb->totalUsers();
        int totalSamples = 0; 

        for (int j = 0; j < numUsers; j++)
        {   
            for (int k = 0; k < user.votes(); k++)
            {
                int movieId = user.movie(k);
                float rating = user.score(k) - averageRating;

                int userIndex = j;
                int movieIndex = movieId - 1;

                float predict = predictRating(movieIndex, userIndex);

                float diff = predict - rating;
                RMSE += diff * diff;

                // Update all the feature vectors here
                for (unsigned int l = 0; l < NUM_FEATURES; l++)
                {
                    float oldUF = userFeatures[userIndex][l];
                    float oldMF = movieFeatures[movieIndex][l];

                    userFeatures[userIndex][l] -= LRATE * 
                                        (diff * oldMF * 2 + REGULARIZE * oldUF);
                    movieFeatures[movieIndex][l] -= LRATE * 
                                        (diff * oldUF * 2 + REGULARIZE * oldMF);
                }
                totalSamples++;
            }
            user.next();
        }

        RMSE = sqrt(RMSE / totalSamples);
        qDebug() << "Epoch" << i + 1 << "RMSE: " << RMSE;
    }                

    qDebug() << "Done with training";
}
예제 #2
0
/**
 * Loop through the entire list of finished features
 */
double SvdOrder::determine(int user)
{
    int movieIndex = currentMovie - 1;
    int userIndex  = currDb->mapUser(user);
    return currDb->getAverageRating() + predictRating(movieIndex, userIndex);
}