Beispiel #1
0
// return a vector of the top k indices of a
void topk(RealVec a, vector<size_t> & indtop){
  multimap<real, size_t> m; // mapping from value to its index
  RealVecItr it;
  for (it = a.begin(); it != a.end(); ++it)
    m.insert(make_pair(*it, it - a.begin()));

  multimap<real, size_t>::reverse_iterator itm; // mapping from value to its index
  size_t indx=0;
  for (itm = m.rbegin(); itm != m.rend(); ++itm){
    //cout << itm->first <<" , "<< itm->second << endl;
    indtop[indx]=itm->second;
    indx++;
  } 
}
void MCMCGRDiagnosticPSRF::outputResults(
				const std::string& filenameGRScalars,
				const RealVec& sampledInd,
				int precData) const
{
	/* sampledInd may contain more values than we monitored */
	RealVec::const_iterator it;
	advance(it, scalars.size());
	RealVec sampledIndTmp(sampledInd.begin(), it);
	
	std::vector < std::string > colNames;
	getScalarColNames(colNames);
	colNames.push_back("W");
	colNames.push_back("B");
	colNames.push_back("estVarV");
	colNames.push_back("rhat");
	
		colNames.push_back("rhatFlag");
		colNames.push_back("sampled?");
	
	std::vector < const RealVec* > data;
	addDataPtrs(data, scalars);
	data.push_back(&Ws);
	data.push_back(&Bs);
	data.push_back(&estVarV);
	data.push_back(&rhat);
	
		data.push_back(&rhatFlag);
		data.push_back(&sampledIndTmp);
	
	outputToFileVertical(data, colNames, 
	filenameGRScalars, precData);
} 
int MCMCGRDiagnosticPSRF::calcDiagnosticsForLoop()
{
	if (keepLogs) {
		// store the current runningSumAllChains as well
		runningSumOverall.push_back(runningSumAllChains);
	}

	// convergence diagnostics calculations for v's

	// the Ws: average, over chains, of sample variance of scalar value
	cxsc::real thisW = sumOfSampleVariancesOverChains/(chains * 1.0); 
	
	#ifdef MYDEBUG_CALCS_EXTRA
			cout << "and thisW = " << thisW << endl;
	#endif
	
				
	Ws.push_back(thisW); 
	// the Bs
	size_t statesForCalcs = states - statesNotInCalcs;
	
	cxsc::real thisB = (1.0/( (chains - 1) * statesForCalcs ) 
						* ( sumOfSquaresOfRunningSums 
						- (runningSumAllChains 
						* runningSumAllChains/(chains * 1.0)) ) );
	Bs.push_back(thisB); 
	
	#ifdef MYDEBUG_CALCS
		//check thisB is correct, doing it the long way
		// runningSumPtr has one running sum for each chain
		RealVec chainAverages;
		cxsc::real accRunningSums(0.0);
		for (RealVecItr it = runningSum.begin(); it < runningSum.end(); ++it) {
			cxsc::real thisChainRunningSum = (*it);
			cxsc::real thisChainAv = thisChainRunningSum/(statesForCalcs * 1.0);
			chainAverages.push_back(thisChainAv);
			accRunningSums+=thisChainRunningSum;
		}
		cxsc::real overallAv = accRunningSums/(statesForCalcs * chains * 1.0);
		cxsc::dotprecision accDiffs(0.0);
		for (RealVecItr it = chainAverages.begin(); it < chainAverages.end(); ++it) {
			cxsc::real thisDiff = (*it) - overallAv;
			// sum up the squares of the differences compared to overall average
			cxsc::accumulate(accDiffs, thisDiff, thisDiff);
		}
		cxsc::real altB = rnd(accDiffs)*( statesForCalcs/(chains - 1.0) );
		
		cout << "\nthisB for v's is\t" << thisB << endl;
		cout << "altB for v's is\t" << altB << endl;
		//assert(thisB == altB);
	
	#endif
	
	// the estimated var(v)
	cxsc::real thisVarV(0.0);
	if (statesForCalcs > 1) {
		thisVarV = statesForCalcs/(statesForCalcs-1.0) 
					* thisW + (1.0/statesForCalcs)*thisB;
	}
	#ifndef OLDCALCMETHOD
		if (statesForCalcs > 1) thisVarV +=thisB/(1.0*chains*statesForCalcs);
	#endif
	
	estVarV.push_back(thisVarV); 
	// the rhats
	cxsc::real thisRhat(0.0);
	// allow division by 0 if w = 0 when var does not
	if (thisW > 0.0 || thisVarV > 0.0) {
		thisRhat = thisVarV/thisW;
	}
	rhat.push_back(thisRhat); 
	
	#ifdef MYDEBUG_CALCS_EXTRA
			cout << "thisRhat = " << thisRhat << " - press any key " << endl;
			getchar();
	#endif
	
	if ( (thisRhat <= 1.0 + tol) 
				&& (thisRhat >= 1.0 - tol) ) {
		// if we have not been converged before on this scalar value
		if (!rhatDiagnosticFlag)  {
			#ifdef MYDEBUG
				cout << "\n" << getScalarsName() 
					<< " convergence test satisfied in state " 
					  << states << " (states in calcs = " 
					  << statesForCalcs << ")"<< endl;
			#endif
			// set the flag for this scalar value
			rhatDiagnosticFlag = 1;
		}
	} 
	else { // not converged on this scalar value
		// if we were okay on this scalar value before
		if (rhatDiagnosticFlag) {
			#ifdef MYDEBUG
				cout << "\n--------- Note: " << getScalarsName() 
				<< " convergence test now NOT satisfied in state " 
				  << states << endl;
		
			#endif
			
			rhatDiagnosticFlag = 0; // update the flag
			
		} 
	}
	
	if (keepLogs) {
		// store the flag as well, as a real, which is a fudge...
		rhatFlag.push_back(rhatDiagnosticFlag);
	}

	// end of checking diagnostic for v's

	return rhatDiagnosticFlag;
} // end calculations