
public final class ConfidenceCalculator {
    static double accuracy = 1.0e-6;

    static double getOutsideProbability(double x) {
	x = Math.abs(x);
	
	double dx = 2.476 * Math.sqrt(accuracy);

	double Q = 0.0, x1;
	for(x1=maxX; x1 > x; x1-=dx) Q += getdI(x1, dx);	   	    
	Q += getdI(x, x1+dx-x);	    
	
	return Q;
    }    

    static double getConfidence(double x) {
	return 1.0 - getOutsideProbability(x);
    }


    static double getSigma(double confidence) {

	double dx = 2.476 * Math.sqrt(accuracy);

	double I=0.0, x1 = maxX, dI = 0.0;
	while((1.0-I) > confidence) {
	    dI = getdI(x1, dx);
	    I += dI;
	    x1 -= dx;
	}
	x1 += dx * (1.0 + (confidence-(1.0-I))/dI);

	return x1;
    }    

    // Exponential integral bits... 
    static double getdI(double x, double dx) {
       	return x < 1e-3 ? P(x) * dx : P(x) / x * (1.0 - Math.exp(-x*dx));
    }
    

    static double P(double x) {
	return A * Math.exp(-x*x / 2.0);
    }

    static double A = Math.sqrt(0.5 / Math.PI);
    static double maxX = 38.0;
}
