def checkGCInRegions(sSeq, lCGMap):
	dGCResults = dict()
	# Loop that loops over each specified segment
	for iBegin, iEndBy in lCGMap:
		sSegPiece = sSeq[iBegin:iEndBy]
		dGCResults[(iBegin, iEndBy)] = getGCcontent(sSegPiece)
	
	return dGCResults
def processCompleteSpecification(dCompleteSpec):
	# Setup initial variables
	lDNASpecification 	= dCompleteSpec['Feature Specification']
	dForbiddenSeqs 		= dCompleteSpec['Forbidden Sequences']
	lGCMap 				= dCompleteSpec['GC Optimization Map']
	fTargetGC 			= dCompleteSpec['GC Target Fraction']
	iIterations			= dCompleteSpec['Optimization Attempts']
	
	# Print info about the job
	print('='*100)
	print('%s Job Info %s' % ('='*45, '='*45))
	print('='*100)
	
	print('Note: DNA specification name: %s' % dCompleteSpec['Specification Name'])
	print('Note: Type of job: %s' % 'GVVGCO (Gneration, Verification, Validation and GC Optimization)')	
	
	print('Note: Feature map contains %i features:' % len(lDNASpecification))
	for iFeature, dFeature in enumerate(lDNASpecification):
		print('      %i: %s: ' % (iFeature, dFeature['name']) )
		print('            SeqType: %s' % ('Generator' if hasattr(dFeature['seq'], '__call__') else 'Specified'), end='')
		if not hasattr(dFeature['seq'], '__call__'): print(', SeqLenght: %i' % len(dFeature['seq']), end='')
		print(', Mutable: %s' % dFeature['mutable'])
		print('            MayContain:%s' % (' None' if not dFeature['maycontain'] else ''), end='')
		sInfront = ''
		for sMayContain in dFeature['maycontain']:
			print ('%s %s' % (sInfront, sMayContain), end='')
			sInfront = ','
		print()
		
	print('Note: Forbidden sequences:')
	lForbiddenSeqNames = list(dForbiddenSeqs.keys())
	lForbiddenSeqNames.sort()
	for sFSeqName in lForbiddenSeqNames:
		print('      %s: %s' % (sFSeqName, dForbiddenSeqs[sFSeqName]))
	
	print('Note: Target GC contents: %f%%' % (fTargetGC*100))	
	print('Note: Optimize GC contents of the folowing regions(%i):' % (len(lGCMap)))
	for iRegion, (iRegBegin, iRegEndBy) in enumerate(lGCMap):
		if not iRegEndBy: iRegEndBy = 0
		print('      Region %i @[%i:%i]' % (iRegion, iRegBegin, iRegEndBy))
		
	print('Note: Number of optimization attempts: %i' % iIterations)
		
	# Setup some stuff to catch prints that would normaly happen to early (i know its not nice to do it this way :P)
	oStdoutOld = sys.stdout # Store default sdtout pipe
	oPrintCatcher = PrintCatcher() 
	sys.stdout = oPrintCatcher # Start catching print output
	
	# Run the DNA creation, verification and optimization function
	tTemp = makeAndGCOptimiseSpecDNA(lDNASpecification, dForbiddenSeqs, lGCMap, fTargetGC, iIterations, bVerbose=False)
	
	# Restore original stdout (and thus stop catching output from the print function)
	sys.stdout = oStdoutOld 

	# If this was a success than display the results
	if tTemp:
		sBestSequence, fBestAvgGCResult, dBestGCRegionResult, lBestFeatureMap, iBestResultAtIteration = tTemp
		print('='*100)
		print('%s Result - Success! :D %s' % ('='*39, '='*39))
		print('='*100)
		
		print('Note: Best result found at iteration: %i' % iBestResultAtIteration)
		print('Note: Optimised GC contents of the folowing regions(%i):' % (len(dBestGCRegionResult)))
		for (iRegBegin, iRegEndBy), fResult in dBestGCRegionResult.items():
			if not iRegEndBy: iRegEndBy = 0
			print('      GC content @[%i:%i]: %f%%' % (iRegBegin, iRegEndBy, fResult*100))
		print('Note: Non-weighted regional average CG contents:  %f%%' % (fBestAvgGCResult[0]*100))
		print('Note: Weighted regional average CG contents: %f%%' % (fBestAvgGCResult[1]*100))
		
		print('Note: Feature map contains features(%i):' % len(lBestFeatureMap))
		for iFeature, (iRegBegin, iRegEndBy) in enumerate(lBestFeatureMap):
			print('      %i @[%i:%i]: %s (GC: %f%%)' % (iFeature, iRegBegin, iRegEndBy, lDNASpecification[iFeature]['name'], getGCcontent(sBestSequence[iRegBegin:iRegEndBy])))
		
		print('Note: Overall GC contents: %f%%' % getGCcontent(sBestSequence))
		
		print('Note: DNA sequence:')
		prettyPrintDNA(sBestSequence, True)

		print('Note: See final verification procedure for more information (displayed below)')	
		print('%s Reverifying Result %s' % ('='*40, '='*40))
		
		makeDNASpecCompliant(sBestSequence, lBestFeatureMap, lDNASpecification, compileForbiddenSeqs(dForbiddenSeqs), bCheckOnly=True)
		
		print('='*100)

	# Else it was no success so than display why it resulted in a failure	
	else:
		print('='*100)
		print('%s Result - Failure! :( %s' % ('='*39, '='*39))
		print('='*100)
		print('Note: Procces ended in a warning because the DNA could not possibly be made valid!')
		print('Note: See final verification procedure for more information (displayed below)')
		print('%s Reverifying Result %s' % ('='*40, '='*40))
		print(oPrintCatcher.sContent, end='')
		print('='*100)