void MFSolver::Run() { double bestValRMSE = INFINITY; int bestValIteration = -1; // Iteratively run SGD for (int it = 0; it < iterations; it++) { // Get next user from data User *u = data->getNextUser(); while (u != NULL) { // For every item of the user for (Item i = Item(0); i != Item(ItemCount); i = Item(i+1)) { // Check if there's rating for item if (u->ratings[i].score == UNKNOWN || u->ratings[i].type == Validation) { continue; } // Train on this rating TrainOnRating(*u, i); } // Get next user u = data->getNextUser(); } // End of this iteration Print(it); double valRMSE = RMSE(Validation); if (valRMSE < bestValRMSE) { bestValRMSE = valRMSE; bestValIteration = it; } } // Print best result cout.setf(ios::fixed, ios::floatfield); cout.precision(2); cout << ASCII_RED << "========================================= "; cout << "Final Results "; cout << " =========================================\n" << ASCII_RESET; cout << "Final Train RMSE = " << RMSE(Training) << endl; cout << ASCII_PURPLE << "Final Validation RMSE = " << RMSE(Validation) << ASCII_RESET << endl; cout << ASCII_YELLOW << "Best Validation RMSE = " << bestValRMSE; cout << " (on iteration " << bestValIteration + 1 << ")\n" << ASCII_RESET; cout.unsetf(ios::floatfield); }
void wcCostEstimator::update( const wcMetaVector& meta, const wcFloat& nla ) { wcFloat cost0 = cost(meta); wcFloat step = 0; iteration++; if(unseeded) { optima_expref = meta; unseeded = false; } /// Value Function Update Vtp = Vt; rt = 1-cost0; dVt = learning_rate*(rt - Vtp); Vt += dVt; /// Predicted Optimal Document Update input_layer .activate(meta); hidden1_layer .activate(input_layer); hidden2_layer .activate(hidden1_layer); output_layer .activate(hidden2_layer); optima = output_layer.output; if( training && (RMSE() < WC_ENDOFTRAINING) && (iteration > 5UL) ) { training = false; } if( training /*&& (dVt>0)*/ ) { optima_expref += dVt*(meta-optima_expref); output_layer .reweightOutput(meta, learning_rate); hidden2_layer .reweightHidden(output_layer, learning_rate); hidden1_layer .reweightHidden(hidden2_layer, learning_rate); input_layer .reweightHidden(hidden1_layer, learning_rate); output_layer .reweightSet(); hidden2_layer .reweightSet(); hidden1_layer .reweightSet(); input_layer .reweightSet(); } }
//-------------------------------------- // main function //-------------------------------------- int main(int argc, char** argv) { // Open channels to the FPGA board. // These channels appear as files to the Linux OS int fdr = open("/dev/xillybus_read_32", O_RDONLY); int fdw = open("/dev/xillybus_write_32", O_WRONLY); // Check that the channels are correctly opened if ((fdr < 0) || (fdw < 0)) { fprintf (stderr, "Failed to open Xillybus device channels\n"); exit(-1); } // sin output cos_sin_type s = 0; // cos output cos_sin_type c = 0; // radian input double radian; // sin & cos calculated by math.h double m_s = 0.0, m_c = 0.0; // Error terms double err_ratio_sin = 0.0; double err_ratio_cos = 0.0; double accum_err_sin = 0.0; double accum_err_cos = 0.0; // arrays to store the output double c_array[NUM_DEGREE]; double s_array[NUM_DEGREE]; int nbytes; Timer timer("CORDIC fpga (batch)"); timer.start(); //---------------------------------------------------------------------- // Send all values to the module //---------------------------------------------------------------------- for (int i = 1; i < NUM_DEGREE; ++i) { radian = i * M_PI / 180; // Convert double value to fixed-point representation theta_type theta(radian); // Convert fixed-point to int64 bit64_t theta_i; theta_i(theta.length()-1,0) = theta(theta.length()-1,0); int64_t input = theta_i; // Send bytes through the write channel // and assert that the right number of bytes were sent nbytes = write (fdw, (void*)&input, sizeof(input)); assert (nbytes == sizeof(input)); } //---------------------------------------------------------------------- // Read all results //---------------------------------------------------------------------- for (int i = 1; i < NUM_DEGREE; ++i) { // Receive bytes through the read channel // and assert that the right number of bytes were recieved int64_t c_out, s_out; nbytes = read (fdr, (void*)&c_out, sizeof(c_out)); assert (nbytes == sizeof(c_out)); nbytes = read (fdr, (void*)&s_out, sizeof(s_out)); assert (nbytes == sizeof(s_out)); // convert int64 to fixed point bit64_t c_i = c_out; bit64_t s_i = s_out; c(c.length()-1,0) = c_i(c.length()-1,0); s(s.length()-1,0) = s_i(s.length()-1,0); // Store to array c_array[i] = c; s_array[i] = s; } timer.stop(); //------------------------------------------------------------ // Check results //------------------------------------------------------------ for (int i = 1; i < NUM_DEGREE; ++i) { // Load the stored result c = c_array[i]; s = s_array[i]; // Call math lib radian = i * M_PI / 180; m_s = sin( radian ); m_c = cos( radian ); // Calculate normalized error err_ratio_sin = ( abs_double( (double)s - m_s) / (m_s) ) * 100.0; err_ratio_cos = ( abs_double( (double)c - m_c) / (m_c) ) * 100.0; // Accumulate error ratios accum_err_sin += err_ratio_sin * err_ratio_sin; accum_err_cos += err_ratio_cos * err_ratio_cos; } //------------------------------------------------------------ // Write out root mean squared error (RMSE) of error ratios //------------------------------------------------------------ // Print to screen std::cout << "#------------------------------------------------\n" << "Overall_Error_Sin = " << RMSE(accum_err_sin) << "\n" << "Overall_Error_Cos = " << RMSE(accum_err_cos) << "\n" << "#------------------------------------------------\n"; // Clean up close(fdr); close(fdw); return 0; }
void ModelMFWt::hogTrain(const Data &data, Model &bestModel, std::unordered_set<int>& invalidUsers, std::unordered_set<int>& invalidItems) { //copy passed known factors //uFac = data.origUFac; //iFac = data.origIFac; std::cout << "\nModelMFWt::hogTrain trainSeed: " << trainSeed; int nnz = data.trainNNZ; std::cout << "\nObj b4 svd: " << objective(data, invalidUsers, invalidItems) << " Train RMSE: " << RMSE(data.trainMat) << " Train nnz: " << nnz << std::endl; std::chrono::time_point<std::chrono::system_clock> startSVD, endSVD; startSVD = std::chrono::system_clock::now(); //initialization with svd of the passed matrix //svdFrmSvdlibCSR(data.trainMat, facDim, uFac, iFac, false); endSVD = std::chrono::system_clock::now(); std::chrono::duration<double> durationSVD = (endSVD - startSVD) ; std::cout << "\nsvd duration: " << durationSVD.count(); int iter, bestIter = -1; double bestObj, prevObj; double bestValRMSE, prevValRMSE; gk_csr_t *trainMat = data.trainMat; //vector to hold user gradient accumulation std::vector<std::vector<double>> uGradsAcc (nUsers, std::vector<double>(facDim,0)); //vector to hold item gradient accumulation std::vector<std::vector<double>> iGradsAcc (nItems, std::vector<double>(facDim,0)); //std::cout << "\nNNZ = " << nnz; prevObj = objective(data, invalidUsers, invalidItems); bestObj = prevObj; std::cout << "\nObj aftr svd: " << prevObj << " Train RMSE: " << RMSE(data.trainMat); std::chrono::time_point<std::chrono::system_clock> start, end; std::chrono::duration<double> duration; std::vector<std::unordered_set<int>> uISet(nUsers); genStats(trainMat, uISet, std::to_string(trainSeed)); getInvalidUsersItems(trainMat, uISet, invalidUsers, invalidItems); std::unordered_set<int> headItems = getHeadItems(trainMat, 0.5); std::unordered_set<int> headUsers = getHeadItems(trainMat, 0.5); double lambda0 = 0.8; double lambda1 = 1.0 - lambda0; //random engine std::mt19937 mt(trainSeed); //get user-item ratings from training data auto uiRatings = getUIRatings(trainMat, invalidUsers, invalidItems); //index to above uiRatings pair std::vector<size_t> uiRatingInds(uiRatings.size()); std::iota(uiRatingInds.begin(), uiRatingInds.end(), 0); std::cout << "\nTrain NNZ after removing invalid users and items: " << uiRatings.size() << std::endl; double subIterDuration = 0; for (iter = 0; iter < maxIter; iter++) { //shuffle the user item rating indexes std::shuffle(uiRatingInds.begin(), uiRatingInds.end(), mt); start = std::chrono::system_clock::now(); const int indsSz = uiRatingInds.size(); #pragma omp parallel for for (int k = 0; k < indsSz; k++) { auto ind = uiRatingInds[k]; //get user, item and rating int u = std::get<0>(uiRatings[ind]); int item = std::get<1>(uiRatings[ind]); float itemRat = std::get<2>(uiRatings[ind]); double r_ui_est = dotProd(uFac[u], iFac[item], facDim); double diff = itemRat - r_ui_est; if (headItems.find(item) != headItems.end()) { diff = diff*lambda0; } else { diff = diff*(lambda0 + lambda1); } //update user for (int i = 0; i < facDim; i++) { uFac[u][i] -= learnRate*(-2.0*diff*iFac[item][i] + 2.0*uReg*uFac[u][i]); } r_ui_est = dotProd(uFac[u], iFac[item], facDim); diff = itemRat - r_ui_est; if (headItems.find(item) != headItems.end()) { diff = diff*lambda0; } else { diff = diff*(lambda0 + lambda1); } //update item for (int i = 0; i < facDim; i++) { iFac[item][i] -= learnRate*(-2.0*diff*uFac[u][i] + 2.0*iReg*iFac[item][i]); } } end = std::chrono::system_clock::now(); duration = end - start; subIterDuration = duration.count(); //check objective if (iter % OBJ_ITER == 0 || iter == maxIter-1) { if (isTerminateModel(bestModel, data, iter, bestIter, bestObj, prevObj, invalidUsers, invalidItems)) { break; } if (iter % 50 == 0) { std::cout << "ModelMFWt::train trainSeed: " << trainSeed << " Iter: " << iter << " Objective: " << std::scientific << prevObj << " Train RMSE: " << RMSE(data.trainMat, invalidUsers, invalidItems) << " Val RMSE: " << prevValRMSE << " sub duration: " << subIterDuration << std::endl; } if (iter % 500 == 0 || iter == maxIter - 1) { std::string modelFName = std::string(data.prefix); bestModel.saveFacs(modelFName); } } } //save best model found till now std::string modelFName = std::string(data.prefix); bestModel.saveFacs(modelFName); std::cout << "\nBest model validation RMSE: " << bestModel.RMSE(data.valMat, invalidUsers, invalidItems); }
void MFSolver::Print(int currentIteration) { cout << ASCII_RED << "========================================= "; cout << "Iteration " << currentIteration + 1; cout << " =========================================\n" << ASCII_RESET; cout.setf(ios::fixed, ios::floatfield); cout.precision(2); // Print qi if (featureSize <= data->getUserCount()) { cout << ASCII_CYAN << "[qi]" << ASCII_RESET << endl; for (int i = 0; i < (5 * featureSize - 3) / 2 + 8; i++) cout << " "; cout << ASCII_YELLOW << "Feature" << ASCII_RESET << endl; for (int i = 0; i < data->getItemCount(); i++) { if (i == data->getItemCount() / 2) { cout << ASCII_YELLOW << " Item " << ASCII_RESET; } else { cout << " "; } cout << "|"; for (int f = 0; f < featureSize; f++) { cout.width(5); cout << q[i][f]; } cout << " |\n"; } } // Print pu if (featureSize <= data->getUserCount()) { cout << ASCII_CYAN << "[pu]" << ASCII_RESET << endl; for (int i = 0; i < (5 * data->getUserCount()) / 2 + 8; i++) cout << " "; cout << ASCII_YELLOW << "User" << ASCII_RESET << endl; for (int f = 0; f < featureSize; f++) { if (f == featureSize / 2) { cout << ASCII_YELLOW << "Feature " << ASCII_RESET; } else { cout << " "; } cout << "|"; for (int u = 0; u < data->getUserCount(); u++) { cout.width(5); cout << p[u][f]; } cout << " |\n"; } cout << endl; } // Print prediction cout << ASCII_CYAN << "[Prediction]" << ASCII_RESET << endl; cout << " White: Train Set" << endl; cout << ASCII_PURPLE << " Purple: Validation Set" << ASCII_RESET << endl; cout << ASCII_YELLOW << " "; for (Item i = Item(0); i < Item(ItemCount); i = Item(i+1)) { if (Data::ItemName(i).length() < 5) cout.width(5); cout << Data::ItemName(i); cout << " "; } cout << ASCII_RESET << endl; User *u = data->getNextUser(); while (u != NULL) { cout << ASCII_GREEN; cout.width(12); cout << u->name << ASCII_RESET; for (Item i = Item(0); i < Item(ItemCount); i = Item(i+1)) { int length = Data::ItemName(i).length(); if (length < 5) length = 5; Rating r = u->ratings[i]; if (r.score < 0) { cout.width(length + 2); cout << ""; } else if (r.type == Training) { cout.width(length); cout << Predict(*u, i); cout << ":" << r.score; } else { cout << ASCII_PURPLE; cout.width(length); cout << Predict(*u, i); cout << ":" << r.score; cout << ASCII_RESET; } } cout << endl; u = data->getNextUser(); } cout << endl; // Print results cout << ASCII_CYAN << "[Results]" << ASCII_RESET << endl; cout << " Training RMSE = " << RMSE(Training) << endl; cout << ASCII_PURPLE << " Validation RMSE = " << RMSE(Validation) << ASCII_RESET << endl; cout << endl; cout.unsetf(ios::floatfield); }
//-------------------------------------- // main function of TB //-------------------------------------- int main(int argc, char** argv) { // sin output double ans = 0; // cos output // sin & cos calculated by math.h double m_an = 0.0; // Error terms double err_ratio; double accum_err; // arrays to store the output double array[NUM_DEGREE]; // HLS streams for communicating with the cordic block //hls::stream<bit32_t> cordic_in; hls::stream<bit32_t> cordic_out; //------------------------------------------------------------ // Send data to CORDIC sim //------------------------------------------------------------ for (int i = 1; i < NUM_DEGREE; i++) { bit32_t input = i; // Send both words to the HLS module // cordic_in.write( input ); //cordic_in.write( input+1 ); } //------------------------------------------------------------ // Execute CORDIC sim and store results //------------------------------------------------------------ for (int i = 1; i < NUM_DEGREE; i++) { // Run the HLS function dut( cordic_out ); // Read the two 32-bit cosine output words, low word first bit32_t output; output = cordic_out.read(); // Store to array array[i] = output; } //------------------------------------------------------------ // Check results //------------------------------------------------------------ for (int i = 1; i < NUM_DEGREE; ++i) { // Load the stored result ans = array[i]; m_an = i; // Calculate normalized error err_ratio = ( abs_double( (double)ans - m_an) / (m_an) ) * 100.0; // Accumulate error ratios accum_err += err_ratio * err_ratio; std::cout << "ans = "<< ans <<" m_an = "<<m_an<<"\n"; } //------------------------------------------------------------ // Write out root mean squared error (RMSE) of error ratios //------------------------------------------------------------ // Print to screen std::cout << "#------------------------------------------------\n" << "Overall_Error_Test = " << RMSE(accum_err) << "\n" << "#------------------------------------------------\n"; return 0; }