示例#1
0
文件: traceback.c 项目: ash211/gtfold
int traceVM(int i, int j) {

	int done;
	int h;
	int A_temp;
	int eVM = 0;

	done = 0;
	int VMij = VM(i,j);

	for (h = i + 2; h <= j - 1 && !done; h++) {
		A_temp = WM(i+1,h-1) + WM(h,j - 1) + Ea + Eb + auPenalty(i, j);
		if (A_temp == VMij) { 
			done = 1;
			eVM += traceWM(i + 1, h - 1);
			eVM += traceWM(h, j - 1);
			break;
		}
	}

	if (check_base(i+1)) {
		for (h = i + 3; h <= j - 1 && !done; h++) {
			A_temp = WM(i + 2,h - 1) + WM(h,j - 1) + Ea + Eb + auPenalty(i,j) + Ed5(i,j,i + 1); 
			if (A_temp == VMij) {
				done = 1;
				eVM += traceWM(i + 2, h - 1);
				eVM += traceWM(h, j - 1);
				break;
			}
		}
	}

	if (check_base(j-1)) {
		for (h = i + 2; h <= j - 2 && !done; h++) { 
			A_temp = WM(i + 1,h - 1) + WM(h,j - 2) + Ea + Eb + auPenalty(i, j) + Ed3(i,j,j - 1);
			if (A_temp == VMij) {
				done = 1;
				eVM += traceWM(i + 1, h - 1);
				eVM += traceWM(h, j - 2);
				break;
			}
		}
	}

	if (check_base(i+1)&&check_base(j-1)) {
		for (h = i + 3; h <= j - 2 && !done; h++) { 
			A_temp = WM(i + 2,h - 1) + WM(h,j - 2) + Ea + Eb + auPenalty(i,j) + Ed5(i,j,i + 1) + Ed3(i,j,j - 1);
			if (A_temp == VMij) {
				done = 1;
				eVM += traceWM(i + 2, h - 1);
				eVM += traceWM(h, j - 2);
				break;
			}
		}
	}

	return eVM;
}
示例#2
0
文件: traceback.c 项目: ash211/gtfold
int traceWM(int i, int j) {

	int done;
	int h1, h;
	int eWM = 0; 

	done = 0;
	h1 = 0;

	if (i >= j)
		return 0;
	else {
		for (h = i; h < j && !done; h++) {
			int aa = WM(i,h) + WM(h + 1,j); 
			if (aa == WM(i,j)) {
				done = 1;
				h1 = h;
				break;
			}
		}
		if (h1 != 0) {
			eWM += traceWM(i, h);
			eWM += traceWM(h + 1, j);
		} else {
			if (WM(i,j) == V(i,j) + auPenalty(i, j) + Eb) { 
				done = 1;
				structure[i] = j;
				structure[j] = i;
				eWM += traceV(i, j);
			} else if (WM(i,j) == V(i+1, j) + Ed3(j,i + 1,i) + auPenalty(i+1, j) + Eb + Ec && check_base(i)) { 
				done = 1;
				eWM += traceV(i + 1, j);
				structure[i + 1] = j;
				structure[j] = i + 1;
			} else if (WM(i,j) == V(i,j-1) + Ed5(j-1,i,j) + auPenalty(i,j-1) +  Eb + Ec && check_base(j) ) { 
				done = 1;
				eWM += traceV(i, j - 1);
				structure[i] = j - 1;
				structure[j - 1] = i;
			} else if (WM(i,j) == V(i+1,j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j) + auPenalty(i+1, j-1) + Eb + 2*Ec && check_base(i) && check_base(j)) { 
				done = 1;
				eWM += traceV(i + 1, j - 1);
				structure[i + 1] = j - 1;
				structure[j - 1] = i + 1;
			} else if (WM(i,j) == WM(i + 1,j) + Ec && check_base(i)) { 
				done = 1;
				eWM += traceWM(i + 1, j);
			} else if (WM(i,j) == WM(i,j - 1) + Ec && check_base(j)) { 
				done = 1;
				eWM += traceWM(i, j - 1);
			}
		}
	}
	return eWM;
}
示例#3
0
int traceVM(int i, int j) {
	int done = 0;
	int eVM = 0;

	if (g_unamode||g_mismatch) {
		if (VM(i,j) == WMPrime[i+1][j - 1] + Ea + Eb + auPenalty(i, j) ) {
			done = 1;
			eVM += traceWMPrime(i + 1, j - 1);
		} else if (VM(i,j) == WMPrime[i + 2][j - 1] + Ea + Eb + auPenalty(i,j) + Ed5(i,j,i + 1) + Ec && canSS(i+1) ) {
			done = 1;
			eVM += traceWMPrime(i + 2, j - 1);
		}
		else if ( VM(i,j) == WMPrime[i + 1][j - 2] + Ea + Eb + auPenalty(i, j) + Ed3(i,j,j - 1) + Ec && canSS(j-1)) {
			done = 1;
			eVM += traceWMPrime(i + 1, j - 2);
		}
		else if (V(i,j) == WMPrime[i + 2][j - 2] + Ea + Eb + auPenalty(i,j) + Estackm(i,j) + 2*Ec && canSS(i+1) && canSS(j-1) ) {
			done = 1;
			eVM += traceWMPrime(i + 2, j - 2);
		}
	} else if (g_dangles == 2) {
		if (V(i,j) ==  WMPrime[i + 1][j - 1] + Ea + Eb + auPenalty(i,j) + Ed5(i,j,i + 1) + Ed3(i,j,j - 1) && canSS(i+1) && canSS(j-1) ) {
			done = 1;
			eVM += traceWMPrime(i + 1, j - 1);
		}
	}	else if (g_dangles == 0) {
		if (VM(i,j) == WMPrime[i+1][j - 1] + Ea + Eb + auPenalty(i, j) ) {
			done = 1;
			eVM += traceWMPrime(i + 1, j - 1);
		}
	} else {
		if (VM(i,j) == WMPrime[i+1][j - 1] + Ea + Eb + auPenalty(i, j) ) {
			done = 1;
			eVM += traceWMPrime(i + 1, j - 1);
		} else if (VM(i,j) == WMPrime[i + 2][j - 1] + Ea + Eb + auPenalty(i,j) + Ed5(i,j,i + 1) + Ec && canSS(i+1) ) {
			done = 1;
			eVM += traceWMPrime(i + 2, j - 1);
		}
		else if ( VM(i,j) == WMPrime[i + 1][j - 2] + Ea + Eb + auPenalty(i, j) + Ed3(i,j,j - 1) + Ec && canSS(j-1)) {
			done = 1;
			eVM += traceWMPrime(i + 1, j - 2);
		} else if (V(i,j) ==  WMPrime[i + 2][j - 2] + Ea + Eb + auPenalty(i,j) + Ed5(i,j,i + 1) + Ed3(i,j,j - 1) + 2*Ec && canSS(i+1) && canSS(j-1) ) {
			done = 1;
			eVM += traceWMPrime(i + 2, j - 2);
		}
	}
	if(!done) { 
		fprintf(stderr, "ERROR: VM(%d,%d) could not be traced\n", i,j);
	}

	return eVM;
}
示例#4
0
void traceW(int j) {
	int done = 0, i;
	int wim1, flag = 1 ;
	
  if (j == 0 || j == 1)
    return;
	
	for (i = 1; i < j && !done; i++) {
		if (j-i < TURN) continue;

		wim1 = MIN(0, W[i-1]);
		flag = 1;
		if ( wim1 != W[i-1] && canSSregion(0,i)) flag = 0;

		if (g_unamode||g_mismatch) {
			if ((W[j] == V(i,j) + auPenalty(i, j) + wim1 && canStack(i,j)) || forcePair(i,j)) { 
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i, j, auPenalty(i, j)/100.00);
							total_ex += auPenalty(i, j);
							traceV(i, j);
							if (flag ) traceW(i - 1);
							break;
			} else if ((W[j] ==  V(i,j-1) + auPenalty(i,j-1) + Ed5(j-1,i,j) + wim1 && canSS(j) && canStack(i,j-1)) || forcePair(i, j-1)) { 	
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i, j-1, (auPenalty(i,j-1) + Ed5(j-1,i,j))/100.00);
							total_ex += (auPenalty(i,j-1) + Ed5(j-1,i,j));
							traceV(i, j - 1);
							if (flag ) traceW(i - 1);
							break;
			} else if ((W[j] == V(i+1,j) + auPenalty(i+1,j) + Ed3(j,i+1,i) + wim1 && canSS(i) && canStack(i+1,j)) || forcePair(i+1,j)){
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i+1, j, (auPenalty(i+1,j) + Ed3(j,i+1,i))/100.00);
							total_ex += (auPenalty(i+1,j) + Ed3(j,i+1,i));
							traceV(i + 1, j);
							if (flag ) traceW(i - 1);
							break;
			} else if ((W[j] == V(i+1,j-1) + auPenalty(i+1, j-1) + Estacke(j-1,i+1) + wim1 && canSS(i) && canSS(j) && canStack(i+1,j-1)) || forcePair(i+1,j-1)) { 
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i+1, j-1, (auPenalty(i+1, j-1) + Estacke(j-1,i+1))/100.00);
							total_ex += (auPenalty(i+1, j-1) + Estacke(j-1,i+1));
							traceV(i + 1, j - 1);
							if (flag ) traceW(i - 1);
							break;
			}
		} else if (g_dangles == 2) {
				int e_dangles = 0;
				if (i>1) e_dangles +=  Ed3(j,i,i-1);
				if (j<length) e_dangles += Ed5(j,i,j+1);
				if ((W[j] == V(i,j) + auPenalty(i, j) + e_dangles + wim1 && canSS(i) && canSS(j) && canStack(i+1,j-1)) || forcePair(i+1,j-1)) { 
												done = 1;
												if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i+1, j-1, (auPenalty(i, j) + e_dangles)/100.00);
												total_ex += (auPenalty(i, j) + e_dangles);
												traceV(i, j);
												if (flag ) traceW(i - 1);
												break;
				} 
		}	else if (g_dangles == 0) {
			if ((W[j] == V(i,j) + auPenalty(i, j) + wim1 && canStack(i,j)) || forcePair(i,j)) { 
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i, j, auPenalty(i, j)/100.00);
							total_ex += auPenalty(i, j);
							traceV(i, j);
							if (flag ) traceW(i - 1);
							break;
			}
		} else { // default
			if ((W[j] == V(i,j) + auPenalty(i, j) + wim1 && canStack(i,j)) || forcePair(i,j)) { 
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i, j, auPenalty(i, j)/100.00);
							total_ex += auPenalty(i, j);
							traceV(i, j);
							if (flag ) traceW(i - 1);
							break;
			} else if ((W[j] ==  V(i,j-1) + auPenalty(i,j-1) + Ed5(j-1,i,j) + wim1 && canSS(j) && canStack(i,j-1)) || forcePair(i, j-1)) { 	
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i, j-1, (auPenalty(i,j-1) + Ed5(j-1,i,j))/100.00);
							total_ex += (auPenalty(i,j-1) + Ed5(j-1,i,j));
							traceV(i, j - 1);
							if (flag ) traceW(i - 1);
							break;
			} else if ((W[j] == V(i+1,j) + auPenalty(i+1,j) + Ed3(j,i+1,i) + wim1 && canSS(i) && canStack(i+1,j)) || forcePair(i+1,j)){
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i+1, j, (auPenalty(i+1,j) + Ed3(j,i+1,i))/100.00);
							total_ex += (auPenalty(i+1,j) + Ed3(j,i+1,i));
							traceV(i + 1, j);
							if (flag ) traceW(i - 1);
							break;
			} else if ((W[j] == V(i+1,j-1) + auPenalty(i+1, j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j) + wim1 && canSS(i) && canSS(j) && canStack(i+1,j-1)) || forcePair(i+1,j-1)) { 
							done = 1;
							if (print_energy_decompose == 1) fprintf(energy_decompose_outfile, "i %5d j %5d ExtLoop   %12.2f\n", i+1, j-1, (auPenalty(i+1, j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j))/100.00);
							total_ex += (auPenalty(i+1, j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j));
							traceV(i + 1, j - 1);
							if (flag ) traceW(i - 1);
							break;
			} 
		}
	}
		
	if (W[j] == W[j - 1] && !done) traceW(j-1);
 
	//if (!done) {
	//	fprintf(stderr, "ERROR: W(%d) could not be traced\n", j);
	//}

	return;
}
示例#5
0
int traceWM(int i, int j) {
	assert(i < j);
	int done=0, eWM=0;

	if (!done && WM(i,j) == WMPrime[i][j]) {
			eWM += traceWMPrime(i,j);
			done = 1;
	}

	if (!done){
		if (g_unamode||g_mismatch) {
						if (WM(i,j) == V(i,j) + auPenalty(i, j) + Eb && canStack(i,j)) { 
										eWM += traceV(i, j);
										done = 1;
						} else if (WM(i,j) == V(i+1, j) + Ed3(j,i + 1,i) + auPenalty(i+1, j) + Eb + Ec && canSS(i) &&  canStack(i+1,j)) { 
										eWM += traceV(i + 1, j);
										done = 1;
						} else if (WM(i,j) == V(i,j-1) + Ed5(j-1,i,j) + auPenalty(i,j-1) +  Eb + Ec && canSS(j) && canStack(i,j-1)) { 
										done = 1;
										eWM += traceV(i, j - 1);
						} else if (WM(i,j) == V(i+1,j-1) + Estackm(j-1,i+1) + auPenalty(i+1, j-1) + Eb + 2*Ec && canSS(i) && canSS(j) && canStack(i+1,j-1)) {
										done = 1;
										eWM += traceV(i + 1, j - 1);
						}
		} else if (g_dangles == 2) {
						int energy = V(i,j) + auPenalty(i, j) + Eb;				
						energy += (i==1)?Ed3(j,i,length):Ed3(j,i,i-1);
						/*if (j<len)*/ energy += Ed5(j,i,j+1);
						if (WM(i,j) ==  energy && canSS(i) && canSS(j) && canStack(i+1,j-1)) { 
										eWM += traceV(i, j);
										done = 1;
						}
		} else if (g_dangles == 0) {
						if (WM(i,j) == V(i,j) + auPenalty(i, j) + Eb && canStack(i,j)) { 
										eWM += traceV(i, j);
										done = 1;
						}
		} else  {
						if (WM(i,j) == V(i,j) + auPenalty(i, j) + Eb && canStack(i,j)) { 
										eWM += traceV(i, j);
										done = 1;
						} else if (WM(i,j) == V(i+1, j) + Ed3(j,i + 1,i) + auPenalty(i+1, j) + Eb + Ec && canSS(i) &&  canStack(i+1,j)) { 
										eWM += traceV(i + 1, j);
										done = 1;
						} else if (WM(i,j) == V(i,j-1) + Ed5(j-1,i,j) + auPenalty(i,j-1) +  Eb + Ec && canSS(j) && canStack(i,j-1)) { 
										eWM += traceV(i, j - 1);
										done = 1;
						} else if (WM(i,j) == V(i+1,j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j) + auPenalty(i+1, j-1) + Eb + 2*Ec && canSS(i) && canSS(j) && canStack(i+1,j-1)) { 
										eWM += traceV(i + 1, j - 1);
										done = 1;
						}
		}
	}
	
	if (!done){
		if (WM(i,j) == WM(i + 1,j) + Ec && canSS(i)) { 
							done = 1;
							eWM += traceWM(i + 1, j);
		} else if (WM(i,j) == WM(i,j - 1) + Ec && canSS(j)) { 
							done = 1;
							eWM += traceWM(i, j - 1);
		}
	}

	if(!done) { 
		fprintf(stderr, "ERROR: WM(%d,%d) could not be traced\n", i,j);
	}
	return eWM;
}
示例#6
0
int calculate(int len, int nThreads) { 
	int b, i, j;
#ifdef _OPENMP
	if (nThreads>0) omp_set_num_threads(nThreads);
#endif
#ifdef _OPENMP
#pragma omp parallel
#pragma omp master
	fprintf(stdout,"Thread count: %3d \n",omp_get_num_threads());
#endif


	for (b = TURN+1; b <= len-1; b++) {
#ifdef _OPENMP
#pragma omp parallel for private (i,j) schedule(guided)
#endif
		for (i = 1; i <= len - b; i++) {
			j = i + b;
			int flag = 0, newWM = INFINITY_; 
			if (canPair(RNA[i], RNA[j])) {
				flag = 1;
				int eh = canHairpin(i,j)?eH(i,j):INFINITY_; //hair pin
				int es = canStack(i,j)?eS(i,j)+getShapeEnergy(i)+getShapeEnergy(j)+V(i+1,j-1):INFINITY_; // stack
				if (j-i > 6) { // Internal Loop BEGIN
					int p=0, q=0;
					int VBIij = INFINITY_;
					for (p = i+1; p <= MIN(j-2-TURN,i+MAXLOOP+1) ; p++) {
						int minq = j-i+p-MAXLOOP-2;
						if (minq < p+1+TURN) minq = p+1+TURN;
						int maxq = (p==i+1)?(j-2):(j-1);
						for (q = minq; q <= maxq; q++) {
							if (!canPair(RNA[p], RNA[q])) continue;
							if (!canILoop(i,j,p,q)) continue;
							VBIij = MIN(eL(i, j, p, q) + V(p,q), VBIij);
						}
					}
					VBI(i,j) = VBIij;
					V(i,j) = V(i,j) + getShapeEnergy(i) + getShapeEnergy(j);

				} // Internal Loop END
				if (j-i > 10) { // Multi Loop BEGIN
					int h;
					int VMij, VMijd, VMidj, VMidjd;
					VMij = VMijd = VMidj = VMidjd = INFINITY_;
					for (h = i+TURN+1; h <= j-1-TURN; h++) { 
						VMij = MIN(VMij, WMU(i+1,h-1) + WML(h,j-1)); 
						VMidj = MIN(VMidj, WMU(i+2,h-1) + WML(h,j-1)); 
						VMijd = MIN(VMijd, WMU(i+1,h-1) + WML(h,j-2)); 
						VMidjd = MIN(VMidjd, WMU(i+2,h-1) + WML(h,j-2)); 
					}
					int d3 = canSS(j-1)?Ed3(i,j,j-1):INFINITY_;
					int d5 = canSS(i+1)?Ed5(i,j,i+1):INFINITY_;
					VMij = MIN(VMij, (VMidj + d5 +Ec)) ;
					VMij = MIN(VMij, (VMijd + d3 +Ec));
					VMij = MIN(VMij, (VMidjd + d5 + d3+ 2*Ec));
					VMij = VMij + Ea + Eb + auPenalty(i,j);
					VM(i,j) = canStack(i,j)?VMij:INFINITY_;
				} // Multi Loop END
				V(i,j) = MIN4(eh,es,VBI(i,j),VM(i,j));
			}
			else V(i,j) = INFINITY_;
			if (j-i > 4) { // WM BEGIN
				int h; 
				for (h = i+TURN+1 ; h <= j-TURN-1; h++) {
					//ZS: This sum corresponds to when i,j are NOT paired with each other.
					//So we need to make sure only terms where i,j aren't pairing are considered. 
					newWM = (!forcePair(i,j))?MIN(newWM, WMU(i,h-1) + WML(h,j)):newWM;
				}
				newWM = MIN(V(i,j) + auPenalty(i,j) + Eb, newWM); 
				newWM = canSS(i)?MIN(V(i+1,j) + Ed3(j,i+1,i) + auPenalty(i+1,j) + Eb + Ec, newWM):newWM; //i dangle
				newWM = canSS(j)?MIN(V(i,j-1) + Ed5(j-1,i,j) + auPenalty(i,j-1) + Eb + Ec, newWM):newWM;  //j dangle
				newWM = (canSS(i)&&canSS(j))?MIN(V(i+1,j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j) + auPenalty(i+1,j-1) + Eb + 2*Ec, newWM):newWM; //i,j dangle
				newWM = canSS(i)?MIN(WMU(i+1,j) + Ec, newWM):newWM; //i dangle
				newWM = canSS(j)?MIN(WML(i,j-1) + Ec, newWM):newWM; //j dangle
				WMU(i,j) = WML(i,j) = newWM;
			} // WM END
		}
	}
	for (j = TURN+2; j <= len; j++) {
		int i, Wj, Widjd, Wijd, Widj, Wij, Wim1;
		Wj = INFINITY_;
		for (i = 1; i < j-TURN; i++) {
			Wij = Widjd = Wijd = Widj = INFINITY_;
			Wim1 = MIN(0, W[i-1]); 
			Wij = V(i, j) + auPenalty(i, j) + Wim1;
			Widjd = (canSS(i)&&canSS(j))?V(i+1,j-1) + auPenalty(i+1,j-1) + Ed3(j-1,i + 1,i) + Ed5(j-1,i+1,j) + Wim1:Widjd;
			Wijd = canSS(j)?V(i,j-1) + auPenalty(i,j-1) + Ed5(j-1,i,j) + Wim1:Wijd;
			Widj = canSS(i)?V(i+1, j) + auPenalty(i+1,j) + Ed3(j,i + 1,i) + Wim1:Widj;
			Wj = MIN(MIN4(Wij, Widjd, Wijd, Widj), Wj); 
		}
		W[j] = canSS(j)?MIN(Wj, W[j-1]):Wj;
	}
	return W[len];
}
示例#7
0
文件: traceback.c 项目: ash211/gtfold
void traceW(int j) {
	int done, i, Wj,Wj_temp;
	int wim1, flag, Widjd, Wijd, Widj, Wij;
	Wj = INFINITY_;
	flag = 1;
	done = 0; 
	
	if (j == 0 || j == 1) return;

	for (i = 1; i < j && !done; i++) {
		if (j-i < TURN) continue;

		wim1 = MIN(0, W[i-1]);
		flag = 1;
		if (wim1 != W[i-1]) flag = 0;

		Widjd = Wijd =  Widj = INFINITY_;
		Wij = V(i,j) + auPenalty(i, j) + wim1;
		Widjd =(check_base(i)&&check_base(j))?(V(i+1,j-1) + auPenalty(i+1, j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j) + wim1): INFINITY_;
		Wijd = (check_base(j))?(V(i,j-1) + auPenalty(i,j-1) + Ed5(j-1,i,j) + wim1):INFINITY_;
		Widj = (check_base(i))?(V(i+1,j) + auPenalty(i+1,j) + Ed3(j,i+1,i) + wim1):INFINITY_;
		Wj_temp=Wj;
		Wj = MIN(MIN(MIN(Wij, Widjd), MIN(Wijd, Widj)), Wj);

		if (W[j] == Wj) {
			if (W[j] == Wij) { 
				done = 1;
				if (verbose == 1) 
					printf("i %5d j %5d ExtLoop   %12.2f\n", i, j, auPenalty(i, j)/100.00);
				total_ex += auPenalty(i, j);
				structure[i] = j;
				structure[j] = i;
				traceV(i, j);
				if (flag || is_ss(1,i)) traceW(i - 1);
				break;
			} else if (W[j] == Widjd && check_base(i) && check_base(j)) { 
				done = 1;
				if (verbose == 1) 
					printf("i %5d j %5d ExtLoop   %12.2f\n", i+1, j-1, (auPenalty(i+1, j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j))/100.00);
				total_ex += (auPenalty(i+1, j-1) + Ed3(j-1,i+1,i) + Ed5(j-1,i+1,j));
				structure[i + 1] = j - 1;
				structure[j - 1] = i + 1;
				traceV(i + 1, j - 1);
				if (flag || is_ss(1,i)) traceW(i - 1);
				break;
			} else if (W[j] == Wijd && check_base(j)) { 
				done = 1;
				if (verbose == 1) 
					printf("i %5d j %5d ExtLoop   %12.2f\n", i, j-1, (auPenalty(i,j-1) + Ed5(j-1,i,j))/100.00);
				total_ex += (auPenalty(i,j-1) + Ed5(j-1,i,j));
				structure[i] = j - 1;
				structure[j - 1] = i;
				traceV(i, j - 1);
				if (flag || is_ss(1,i)) traceW(i - 1);
				break;
			} else if (W[j] == Widj && check_base(i)) { 
				done = 1;
				if (verbose == 1) 
					printf("i %5d j %5d ExtLoop   %12.2f\n", i+1, j, (auPenalty(i+1,j) + Ed3(j,i+1,i))/100.00);
				total_ex += (auPenalty(i+1,j) + Ed3(j,i+1,i));
				structure[i + 1] = j;
				structure[j] = i + 1;
				traceV(i + 1, j);
				if (flag || is_ss(1,i)) traceW(i - 1);
				break;
			}
		}
	}
		
	if (W[j] == W[j - 1] && !done) traceW(j-1);

	return;
}