Esempio n. 1
0
std::string
Interaction::
dotBracket( const Interaction & i, const char symOpen, const char symClose, const bool fullLength )
{
#if INTARNA_IN_DEBUG_MODE
	if (!i.isValid())
		throw std::runtime_error("Interaction::dotBracket("+toString(i)+") not valid!");
#endif

	if (fullLength) {
		// compile dot-bracket representation for full sequence lengths
		return	std::string(i.basePairs.begin()->first, '.' ) // leading unpaired s1
				+ dotSomething(i.basePairs.begin(), i.basePairs.end(), true, symOpen) // s1 structure
				+ std::string(i.s1->size() - i.basePairs.rbegin()->first -1, '.' ) // trailing unpaired s1
				+"&"
				+ std::string(i.s2->size() - i.basePairs.rbegin()->second -1, '.' ) // leading unpaired s2
				+ dotSomething(i.basePairs.rbegin(), i.basePairs.rend(), false, symClose) // s2 structure
				+ std::string(i.basePairs.rbegin()->second, '.' ) // trailing unpaired s2
				;
	} else {
		// compile dot-bracket representation for interacting subsequences only
		return	dotSomething(i.basePairs.begin(), i.basePairs.end(), true, symOpen)
				+"&"
				+ dotSomething(i.basePairs.rbegin(), i.basePairs.rend(), false, symClose)
				;
	}
}
Esempio n. 2
0
std::string
Interaction::
dotBar( const Interaction & i, const bool fullLength )
{
#if INTARNA_IN_DEBUG_MODE
	if (!i.isValid())
		throw std::runtime_error("Interaction::dotBar("+toString(i)+") not valid!");
#endif

	// check whether to do full length output
	if (fullLength) {
		// compile dot-bar representation for full sequences
		return "1"
				+ std::string(i.basePairs.begin()->first, '.' ) // leading unpaired s1
				+ dotSomething(i.basePairs.begin(), i.basePairs.end(), true, '|') // s1 structure
				+ std::string(i.s1->size() - i.basePairs.rbegin()->first -1, '.' ) // trailing unpaired s1
				+ "&"
				+ "1"
				+ std::string(i.basePairs.rbegin()->second, '.' ) // trailing unpaired s2
				+ dotSomething(i.basePairs.rbegin(), i.basePairs.rend(), false, '|') // s2 structure
				+ std::string( i.s2->size() - i.basePairs.begin()->second -1, '.' ) // leading unpaired s2
				;
	} else {
		// compile dot-bar representation for interacting subsequences only
		return	toString(i.basePairs.begin()->first +1)
				+ dotSomething(i.basePairs.begin(), i.basePairs.end(), true, '|')
				+"&"
				+toString(i.basePairs.rbegin()->second +1)
				+ dotSomething(i.basePairs.rbegin(), i.basePairs.rend(), false, '|')
				;
	}
}
void
PredictorMfe2dHeuristic::
traceBack( Interaction & interaction, const OutputConstraint & outConstraint  )
{
	// check if something to trace
	if (interaction.basePairs.size() < 2) {
		return;
	}

#if INTARNA_IN_DEBUG_MODE
	// sanity checks
	if ( interaction.basePairs.size() != 2 ) {
		throw std::runtime_error("PredictorMfe2dHeuristic::traceBack() : given interaction does not contain boundaries only");
	}
#endif

	// check for single interaction
	if (interaction.basePairs.at(0).first == interaction.basePairs.at(1).first) {
		// delete second boundary (identical to first)
		interaction.basePairs.resize(1);
		// update done
		return;
	}

#if INTARNA_IN_DEBUG_MODE
	// sanity checks
	if ( ! interaction.isValid() ) {
		throw std::runtime_error("PredictorMfe2dHeuristic::traceBack() : given interaction not valid : "+toString(interaction));
	}
#endif

	// ensure sorting
	interaction.sort();
	// get indices in hybridE for boundary base pairs
	size_t	i1 = energy.getIndex1(interaction.basePairs.at(0)),
			i2 = energy.getIndex2(interaction.basePairs.at(0));
	const size_t j1 = energy.getIndex1(interaction.basePairs.at(1));
	const size_t j2 = energy.getIndex2(interaction.basePairs.at(1));


	// the currently traced value for i1-j1, i2-j2
	E_type curE = hybridE(i1,i2).E;
	assert( hybridE(i1,i2).j1 == j1 );
	assert( hybridE(i1,i2).j2 == j2 );
	assert( i1 <= j1 );
	assert( i2 <= j2 );
	assert( j1 < hybridE.size1() );
	assert( j2 < hybridE.size2() );

	// trace back
	// temp variables
	size_t k1,k2;
	// check all possible splits of the interval (i1,i2)-(j1,j2)
	// only reasonable, if there is an enclosed position k1 between i1-j1
	while( (j1-i1) > 1 ) {

		const BestInteraction * curCell = NULL;
		bool traceNotFound = true;
		// check all combinations of decompositions into (i1,i2)..(k1,k2)-(j1,j2)
		for (k1=std::min(j1,i1+energy.getMaxInternalLoopSize1()+1); traceNotFound && k1>i1; k1--) {
		for (k2=std::min(j2,i2+energy.getMaxInternalLoopSize2()+1); traceNotFound && k2>i2; k2--) {
			// temp access to current cell
			curCell = &(hybridE(k1,k2));
			// check if right boundary is equal (part of the heuristic)
			if ( curCell->j1 == j1 && curCell->j2 == j2 &&
					// and energy is the source of curE
					E_equal( curE, (energy.getE_interLeft(i1,k1,i2,k2) + curCell->E ) ) )
			{
				// stop searching
				traceNotFound = false;
				// store splitting base pair if not last one of interaction range
				if ( k1 < j1 ) {
					interaction.basePairs.push_back( energy.getBasePair(k1,k2) );
				}
				// trace right part of split
				i1=k1;
				i2=k2;
				curE = curCell->E;
			}
		}
		}
		assert( !traceNotFound );
	}

	// sort final interaction (to make valid) (faster than calling sort())
	if (interaction.basePairs.size() > 2) {
		Interaction::PairingVec & bps = interaction.basePairs;
		// shift all added base pairs to the front
		for (size_t i=2; i<bps.size(); i++) {
			bps.at(i-1).first = bps.at(i).first;
			bps.at(i-1).second = bps.at(i).second;
		}
		// set last to j1-j2
		(*bps.rbegin()) = energy.getBasePair( j1, j2 );
	}

}