//----------------------------------------------------------------------------- // TestMatrixL1Norm //----------------------------------------------------------------------------- bool TestMatrixL1Norm() { Matrix A("1,2,3;4,5,6;7,8,9"); return ApproxEqual( L1Norm(A), 18.0, TOLERANCE); }
/* * perform sparse coding with a learned dictionary. */ double MedSTC::sparse_coding(Document *doc, const int &docIx, Params *param, double* theta, double **s ) { double *sPtr = NULL, *bPtr = NULL, dval = 0; // initialize mu & theta double dThetaRatio = m_dGamma / (m_dLambda + doc->length * m_dGamma); int svmMuIx = docIx * m_nLabelNum; int gndIx = doc->gndlabel * m_nK; int nWrd = 0, xVal = 0, k, n; for ( k=0; k<m_nK; k++ ) { theta[k] = 0; } for ( n=0; n<doc->length; n++ ) { mu_[n] = 0 + m_dPoisOffset; nWrd = doc->words[n]; sPtr = s[n]; bPtr = m_dLogProbW[nWrd]; for ( k=0; k<m_nK; k++ ) { dval = sPtr[k]; if ( dval > 0 ) { mu_[n] += dval * bPtr[k]; theta[k] += dval; } } } // initialize theta for ( k=0; k<m_nK; k++ ) { theta[k] = theta[k] * dThetaRatio; } if ( param->SUPERVISED == 1 ) { if ( param->PRIMALSVM == 1 ) { if ( doc->lossAugLabel != -1 && doc->lossAugLabel != doc->gndlabel ) { int lossIx = doc->lossAugLabel * m_nK; double dHingeRatio = 0.5 * m_dC / (m_dLambda + doc->length * m_dGamma); for ( k=0; k<m_nK; k++ ) { theta[k] += (m_dEta[gndIx+k] - m_dEta[lossIx+k]) * dHingeRatio ; theta[k] = max(0.0, theta[k]); // enforce theta to be non-negative. } } } else { double dHingeRatio = 0.5 / (m_dLambda + doc->length * m_dGamma); for ( k=0; k<m_nK; k++ ) { for ( int m=0; m<m_nLabelNum; m++ ) { int yIx = m * m_nK; theta[k] += m_dMu[svmMuIx+m] * (m_dEta[gndIx+k] - m_dEta[yIx+k]) * dHingeRatio ; } theta[k] = max(0.0, theta[k]); // enforce theta to be non-negative. } } } else; // alternating minimization over theta & s. double dconverged=1, fval, dobj_val, dpreVal=1; double mu, eta, beta, aVal, bVal, cVal, discVal, sqrtDiscVal; double s1, s2; int it = 0; while (((dconverged < 0) || (dconverged > param->VAR_CONVERGED) || (it <= 2)) && (it <= param->VAR_MAX_ITER)) { for ( n=0; n<doc->length; n++ ) { nWrd = doc->words[n]; xVal = doc->counts[n]; bPtr = m_dLogProbW[nWrd]; // optimize over s. sPtr = s[n]; for ( k=0; k<m_nK; k++ ) { sold_[k] = sPtr[k]; beta = bPtr[k]; if ( beta > MIN_BETA ) { mu = mu_[n] - sold_[k] * beta; eta = beta + m_dRho - 2 * m_dGamma * theta[k]; // solve the quadratic equation. aVal = 2 * m_dGamma * beta; bVal = 2 * m_dGamma * mu + beta * eta; cVal = mu * eta - xVal * beta; discVal = bVal * bVal - 4 * aVal * cVal; sqrtDiscVal = sqrt( discVal ); s1 = max(0.0, (sqrtDiscVal - bVal) / (2*aVal)); // non-negative s2 = max(0.0, 0 - (sqrtDiscVal + bVal) / (2*aVal)); // non-negative sPtr[k] = max(s1, s2); } else { // solve the degenerated linear equation sPtr[k] = max(0.0, theta[k] - 0.5*m_dRho/m_dGamma); } // update mu. mu_[n] += (sPtr[k] - sold_[k]) * beta; } // update theta. for ( k=0; k<m_nK; k++ ) { theta[k] += (sPtr[k] - sold_[k]) * dThetaRatio; theta[k] = max(0.0, theta[k]); // enforce theta to be non-negative. } } // check optimality condition. fval = 0; m_dLogLoss = 0; for ( n=0; n<doc->length; n++ ) { double dval = mu_[n]; double dLogLoss = (dval - doc->counts[n] * log(dval)); m_dLogLoss += dLogLoss; fval += dLogLoss + m_dGamma * L2Dist(s[n], theta, m_nK) + m_dRho * L1Norm(s[n], m_nK); } fval += m_dLambda * L2Norm(theta, m_nK); dobj_val = fval; if ( param->SUPERVISED == 1 ) { // compute svm objective if ( param->PRIMALSVM == 1 ) { if ( doc->lossAugLabel != -1 && doc->lossAugLabel != doc->gndlabel ) { // hinge loss int lossIx = doc->lossAugLabel * m_nK; dval = loss( doc->gndlabel, doc->lossAugLabel ); for ( k=0; k<m_nK; k++ ) { dval += theta[k] * (m_dEta[lossIx+k] - m_dEta[gndIx+k]); } dobj_val += m_dC * dval; } } else { for ( int m=0; m<m_nLabelNum; m++ ) { int yIx = m * m_nK; dval = loss( doc->gndlabel, m ); for ( k=0; k<m_nK; k++ ) { dval += theta[k] * (m_dEta[yIx+k] - m_dEta[gndIx+k]); } dobj_val += m_dMu[svmMuIx+m] * dval; } } } dconverged = (dpreVal - dobj_val) / dpreVal; dpreVal = dobj_val; it ++; } return fval; }