Ejemplo n.º 1
0
def PV(data, B, E, f, jacb, jacd, fix):
    N = 64                                      # Number of pts. for best fit curve.
    x = np.linspace(B[-1], data.V.min()-1, N)   # B[-1] is the last element of B, V0

    # Plot the data and the best fit line
    figfit = plt.figure(figsize=(9,9))
    fig = plt.gcf()
    titlestring = 'Fitting Results for '+ data.EOS_type + '-' + str(data.EOS_order)
    fig.canvas.set_window_title(titlestring)
    plt.subplot(221)
    plt.errorbar(x=data.V, y=data.P, xerr=data.Verr, yerr=data.Perr, fmt='ko', label="Data")
    plt.plot(x, f(B,x), 'r', linewidth=3, label="Fit")
    plt.xlabel(r"Volume, $\AA^{3}$", fontsize=14)
    plt.ylabel(r"Pressure, GPa", fontsize=14)
    plt.legend(numpoints=1, loc="upper right")
    plt.tight_layout()
    
    plt.subplot(222)
    K = GEOST_thermo.BM3_V_K(B,x)
    plt.plot(x, K, 'r', linewidth=3)
    plt.xlabel(r"Volume, $\AA^{3}$", fontsize=14)
    plt.ylabel(r"Bulk Modulus, GPa", fontsize=14)
    plt.tight_layout()
    
    plt.subplot(223)
    fe = GEOST_thermo.EULERIAN_STRAIN(B[-1],x)
    dKdP = GEOST_thermo.birch_murnaghan(B,fe).dKdP
    plt.plot(x, dKdP, 'r', linewidth=3)
    plt.xlabel(r"Volume, $\AA^{3}$", fontsize=14)
    plt.ylabel(r"$\partial K / \partial P$", fontsize=14)
    plt.tight_layout()

    plt.subplot(224)
    fe = GEOST_thermo.EULERIAN_STRAIN(B[-1],x)
    d2KdP2 = GEOST_thermo.birch_murnaghan(B,fe).d2KdP2
    plt.plot(x, d2KdP2, 'r', linewidth=3)
    plt.xlabel(r"Volume, $\AA^{3}$", fontsize=14)
    plt.ylabel(r"$\partial^{2} K / \partial P^{2}$", fontsize=14)
    plt.tight_layout()

    return 0
Ejemplo n.º 2
0
def ON_REFINE_PRESS():
    global data
    name = thermo.types().names[0]       # Which EOS
    fix  = np.zeros(4, dtype=int)           # Fix flags for refinement
    beta = np.zeros(4, dtype=float)         # Refineable param 1st guesses

    fix, beta = GEOST_gui.GUI().FIX_FLAG()  # Assign fix flags, and parameter guesses

    # Sort out which EOS to work with, derivatives, etc.
    if name == app.EOS_names[0]:    # Birch-Murnaghan
        if app.EOS_order.get() == 2:
            f    = thermo.BM2_V
            jacb = thermo.BM2_V_JACB
            jacd = thermo.BM2_V_JACD
        elif app.EOS_order.get() == 3:
            f    = thermo.BM3_V
            jacb = thermo.BM3_V_JACB
            jacd = thermo.BM3_V_JACD
        elif app.EOS_order.get() == 4:
            f    = thermo.BM4_V
            jacb = thermo.BM4_V_JACB
            jacd = thermo.BM4_V_JACD
    elif name == app.EOS_names[1]:   # Natural Strain
        if app.EOS_order.get() == 2:
            f    = thermo.NS2_V
            jacb = thermo.NS2_V_JACB
            jacd = thermo.NS2_V_JACD
        elif app.EOS_order.get() == 3:
            f    = thermo.NS3_V
            jacb = thermo.NS3_V_JACB
            jacd = thermo.NS3_V_JACD
        elif app.EOS_order.get() == 4:
            f    = thermo.NS4_V
            jacb = thermo.NS4_V_JACB
            jacd = thermo.NS4_V_JACD
    elif name == app.EOS_names[2]:   # Vinet
        f    = thermo.VINET_V
        jacb = thermo.VINET_V_JACB
        jacd = thermo.VINET_V_JACD

    # ODR SETUP
    # model contains information about the ODR functions.
    #        fcn   = model function to refine parameters from
    #        fjacb = derivatives of fcn w.r.t. parameters
    #        fjacd = derivatives of fcn w.r.t. independent var.
    odr_model = odrpack.Model(fcn=f, fjacb=jacb, fjacd=jacd)
    odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
    odr       = odrpack.ODR(odr_data, odr_model, beta0=beta, ifixb=fix, maxit=100)
    odr.set_job(fit_type=0, deriv=2, var_calc=0)   # Use user-supplied derivatives, but CHECK THEM!!!
    
    # ======== ODR RESULTS =========
    output  = odr.run()                          # Output of ODR run
    ref_B   = output.beta                        # LSQ best-fit parameters
    err     = output.sd_beta                     # Parameter errors (1-sigma)
    cov_B   = output.cov_beta                    # Covariance matrix

    # The following was implemented for testing purposes to understand
    # how ODR was computing the covariance matrix, and how to generate
    # correlated random data using the Cholesky decomposition.
    # Most of this is now out of date. -JPT feb 2015
    '''
    # ODR covariance matrix
    print "ODR covariance:"
    print cov_B
    
    # Homemade covariance matrix from C = inv(JtJ), J = jacobian at optimum params.
    # NB: ODR wants the TRANSPOSE of J, so we need to transpose this guy
    J = jacb(ref_B,V).T
    for i in range(J.shape[0]):
        J[i,:] = (-1./Perr[i])*J[i,:]

    Jt = np.transpose(J)
    cov = np.linalg.inv(np.dot(Jt,J))        # Defn. of the covariance
    print 'Homemade cov (see Craigs PDF):'
    print cov
    cor = np.empty(cov.shape, dtype=float)   # Correlation matrix. Need for correlated draws
    for i in range(cov.shape[0]):
        for j in range(cov.shape[1]):
            cor[i,j] = cov[i,j]/np.sqrt(np.dot(cov[i,i],cov[j,j]))

    # Spit results to stdout, will remove once it's finalized.
    print "cor (See Hughes & Hase pp. 94 eqn. 7.30):"
    print cor
    print ""
    print "Why does ODR cov_beta and homemade cov differ?"
    print "Because Hughes & Hase compute cov = inv(A)"
    print "Where Aij = 1/2 * d2 (chi_sq)/dBi dBj"
    print "Therefore one gets cor = 1/4 * inv(A)"
    print "As a result, multiply sqrt of diagonal elements"
    print "by 2 to compare with ODR std_beta."
    print ""
    
    print "spectrum of cor"   # Check that cor is positive definite
    u,w = np.linalg.eig(cor)
    print u

    # Compute the Cholesky of the correlation matrix,
    # NB: Scipy returns a lower triangular Cholesky, we want upper triangular.
    U = np.linalg.cholesky(cor).T
    print "Cholesky(cor)"
    print U

    print "Best fit params:"
    print ref_B
    print "Standard error:"
    print err
    '''

    # Print the results and plot if ODR was successful
    if output.stopreason[0] == 'Iteration limit reached':
        app.LOG_PRINT('ITERATION LIMIT REACHED, LSQ NOT CONVERGED!')
    else:
        RESULTS(ref_B, err, cov_B, output, f) 
        PLOTS(ref_B, err, f, jacb, jacd, cov_B)
         
    return 0
Ejemplo n.º 3
0
def f34test(data, B, fix):    
    F = np.zeros(2, dtype=float)    # pdf
    C = np.zeros(2, dtype=float)    # p-values
    B3 = np.zeros(3, dtype=float)   # for the 2nd order EOS, assign K0 and V0 from user guesses
    B3[0] = B[0]
    B3[1] = B[1]
    B3[2] = B[3]
                
    if data.EOS_type == GEOST_thermo.types().names[0]:   # Figure out what EOS's to use
        # If birch murnaghan
        odr_model = odrpack.Model(fcn=GEOST_thermo.BM3_V, fjacb=GEOST_thermo.BM3_V_JACB,
                                  fjacd=GEOST_thermo.BM3_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B3, ifixb=[fix[0],fix[1],fix[3]])
        odr.set_job(deriv=3)          # Use user-supplied derivatives
        output = odr.run()            # Output of ODR run
        ref_B3  = output.beta         # LSQ best-fit parameters
        err_B3  = output.sd_beta      # Parameter errors (1-sigma)
        f3 = GEOST_thermo.BM3_V(ref_B3,data.V)
        df3 = data.V.shape[0] - 3
                
        odr_model = odrpack.Model(fcn=GEOST_thermo.BM4_V, fjacb=GEOST_thermo.BM4_V_JACB,
                                  fjacd=GEOST_thermo.BM4_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B, ifixb=fix)
        odr.set_job(deriv=3)          # Use user-supplied derivatives, but CHECK THEM!!!
        output = odr.run()            # Output of ODR run
        ref_B4  = output.beta         # LSQ best-fit parameters
        err_B4  = output.sd_beta      # Parameter errors (1-sigma)
        f4 = GEOST_thermo.BM3_V(ref_B3,data.V)
        df4 = data.V.shape[0] - 4
        
    elif data.EOS_type == GEOST_thermo.types().names[1]:
        # If Natural strain
        odr_model = odrpack.Model(fcn=GEOST_thermo.NS3_V, fjacb=GEOST_thermo.NS3_V_JACB, fjacd=GEOST_thermo.NS3_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B3, ifixb=[fix[0], fix[1], fix[3]])
        odr.set_job(deriv=3)          # Use user-supplied derivatives, but CHECK THEM!!!
        output = odr.run()            # Output of ODR run
        ref_B3  = output.beta         # LSQ best-fit parameters
        err_B3  = output.sd_beta      # Parameter errors (1-sigma)
        f3 = GEOST_thermo.NS3_V(ref_B3,data.V)
        df3 = data.V.shape[0] - 3
        
        odr_model = odrpack.Model(fcn=GEOST_thermo.NS4_V, fjacb=GEOST_thermo.NS4_V_JACB,
                                  fjacd=GEOST_thermo.NS4_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B, ifixb=fix)
        odr.set_job(deriv=3)          # Use user-supplied derivatives, but CHECK THEM!!!
        output = odr.run()            # Output of ODR run
        ref_B4  = output.beta         # LSQ best-fit parameters
        err_B4  = output.sd_beta      # Parameter errors (1-sigma)
        f4 = GEOST_thermo.NS4_V(ref_B4,data.V)
        df4 = data.V.shape[0] - 4
                    
    elif data.EOS_type == GEOST_thermo.types().names[2]:
        self.LOG_PRINT("ERROR in PLOTS: Cannot do F-test using Vinet EOS.")
    else:
        self.LOG_PRINT("ERROR in PLOTS: Unrecognized value of EOS_SELECT")

    chisq_3 = float(0)
    chisq_4 = float(0)
    for i in range(data.P.shape[0]):   # Compute the chi-squared for each EOS
        chisq_3 += (data.P[i] - f3[i])**2
        chisq_4 += (data.P[i] - f4[i])**2
                
    # Compute the F-statistic
    Fx34 = (chisq_3 - chisq_4)/(chisq_4/df4)

    x1 = np.linspace(0.01, 2*Fx34, 128)
    pdf34 = f_dist.pdf(x1, 1, df4)
    cdf34 = f_dist.cdf(x1, 1, df4)

    # Use Scipy's built-in F-distribution methods
    F = f_dist.pdf(Fx34, 1, df4)
        
    # Compute the P-value
    C = 1 - f_dist.cdf(Fx34, 1, df4)

    # Finally, Make the plot. SHould be a 1 row 2 column plot showing
    # f-test for 2nd to 3rd order EOS and 3rd to 4th order EOS.
    plt.figure()
    fig = plt.gcf()
    fig.canvas.set_window_title("F-Test Results")
    plt.plot(x1, pdf34, 'r', linewidth=3, alpha=0.8)
    plt.plot(x1, cdf34, 'b', linewidth=3, alpha=0.8)
    plt.plot(Fx34, f_dist.pdf(Fx34, 1, df4), 'ko')
    plt.fill_between(x1, 0, pdf34, where=f_dist.cdf(Fx34, 1, df4)<cdf34, facecolor='red', alpha=0.2)
    plt.xticks(fontsize=14)
    plt.ylim([-0.01,1.01])
    plt.title("Comparing 3rd vs. 4th order EOS", fontsize=14)
    plt.xlabel(r"$\left( \chi^{2}_{3} - \chi^{2}_{4} \right) / \left(\chi^{2}_{4} / \nu_{4} \right)$",
               fontsize=12)
    plt.legend(['PDF', 'CDF', r"$F_{X}$"], loc='upper right', numpoints=1)
    plt.text(Fx34, f_dist.pdf(Fx34, 1, df4)+0.05, "p-value= {:8.4f}".format(1-f_dist.cdf(Fx34, 1, df4)), fontsize=14)
    plt.tight_layout()
    return [chisq_3/df3, chisq_4/df4, Fx34, f_dist.cdf(Fx34, 1, df4)]
Ejemplo n.º 4
0
def f23test(data, B, fix):
    F = np.zeros(2, dtype=float)    # pdf
    C = np.zeros(2, dtype=float)    # p-values
    B2 = np.zeros(2, dtype=float)   # for the 2nd order EOS, assign K0 and V0 from user guesses
    B2[0] = B[0]
    B2[1] = B[-1]
                
    if data.EOS_type == GEOST_thermo.types().names[0]:   # Figure out what EOS's to use
        # If birch murnaghan
        odr_model = odrpack.Model(fcn=GEOST_thermo.BM2_V, fjacb=GEOST_thermo.BM2_V_JACB,
                                  fjacd=GEOST_thermo.BM2_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B2, ifixb=[fix[0],fix[-1]])
        odr.set_job(deriv=3)          # Use user-supplied derivatives
        output = odr.run()            # Output of ODR run
        ref_B2  = output.beta         # LSQ best-fit parameters
        err_B2  = output.sd_beta      # Parameter errors (1-sigma)
        f2 = GEOST_thermo.BM2_V(ref_B2,data.V)
        df2 = data.V.shape[0] - 2
                
        odr_model = odrpack.Model(fcn=GEOST_thermo.BM3_V, fjacb=GEOST_thermo.BM3_V_JACB,
                                  fjacd=GEOST_thermo.BM3_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B, ifixb=fix)
        odr.set_job(deriv=3)          # Use user-supplied derivatives, but CHECK THEM!!!
        output = odr.run()            # Output of ODR run
        ref_B3  = output.beta         # LSQ best-fit parameters
        err_B3  = output.sd_beta      # Parameter errors (1-sigma)
        f3 = GEOST_thermo.BM3_V(ref_B3,data.V)
        df3 = data.V.shape[0] - 3
        
    elif data.EOS_type == GEOST_thermo.types().names[1]:
        # If Natural strain
        odr_model = odrpack.Model(fcn=GEOST_thermo.NS2_V, fjacb=GEOST_thermo.NS2_V_JACB, fjacd=GEOST_thermo.NS2_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B2, ifixb=[fix[0],fix[-1]])
        odr.set_job(deriv=3)          # Use user-supplied derivatives
        output = odr.run()            # Output of ODR run
        ref_B2  = output.beta         # LSQ best-fit parameters
        err_B2  = output.sd_beta      # Parameter errors (1-sigma)
        f2 = GEOST_thermo.NS2_V(ref_B2,data.V)
        df2 = data.V.shape[0] - 2
            
        odr_model = odrpack.Model(fcn=GEOST_thermo.NS3_V, fjacb=GEOST_thermo.NS3_V_JACB,
                                  fjacd=GEOST_thermo.NS3_V_JACD)
        odr_data  = odrpack.RealData(x=data.V, y=data.P, sx=data.Verr, sy=data.Perr)
        odr = odrpack.ODR(odr_data, odr_model, beta0=B, ifixb=fix)
        odr.set_job(deriv=3)          # Use user-supplied derivatives, but CHECK THEM!!!
        output = odr.run()            # Output of ODR run
        ref_B3  = output.beta         # LSQ best-fit parameters
        err_B3  = output.sd_beta      # Parameter errors (1-sigma)
        f3 = GEOST_thermo.NS3_V(ref_B3,data.V)
        df3 = data.V.shape[0] - 3
        
    chisq_2 = float(0)
    chisq_3 = float(0)
    for i in range(data.P.shape[0]):   # Compute the chi-squared for each EOS
        chisq_2 += (data.P[i] - f2[i])**2
        chisq_3 += (data.P[i] - f3[i])**2
                
    # Compute the F-statistic
    Fx23 = (chisq_2 - chisq_3)/(chisq_3/df3)
    
    # Use Scipy's built-in F-distribution methods
    F = f_dist.pdf(Fx23, 1, df3)
        
    # Compute the P-value
    C = 1 - f_dist.cdf(Fx23, 1, df3)

    x1 = np.linspace(0.01, 2*Fx23, 128)
    pdf23 = f_dist.pdf(x1, 1, df3)
    cdf23 = f_dist.cdf(x1, 1, df3)

    # Results
    plt.figure()
    fig = plt.gcf()
    fig.canvas.set_window_title("F-Test Results")
    plt.plot(x1, pdf23, 'r', linewidth=3, alpha=0.8)
    plt.plot(x1, cdf23, 'b', linewidth=3, alpha=0.8)
    plt.plot(Fx23, f_dist.pdf(Fx23, 1, df3), 'ko')
    plt.fill_between(x1, 0, pdf23, where=f_dist.cdf(Fx23, 1, df3)<cdf23, facecolor='red', alpha=0.2)
    plt.xticks(fontsize=14)
    plt.ylim([-0.01,1.01])
    plt.title("F test for 2nd vs. 3rd order EOS", fontsize=14)
    plt.xlabel(r"$\left( \chi^{2}_{2} - \chi^{2}_{3} \right) / \left(\chi^{2}_{3} / \nu_{3} \right)$",
               fontsize=12)
    plt.ylabel(r"PDF/CDF")
    plt.legend(['PDF', 'CDF', r"$F_{X}$"], loc='upper right', numpoints=1)
    plt.text(Fx23, f_dist.pdf(Fx23, 1, df3)+0.05, "p-value= {:8.4f}".format(1-f_dist.cdf(Fx23, 1, df3)), fontsize=14)    
    plt.tight_layout()
    return [chisq_2/df2, chisq_3/df3, Fx23, f_dist.cdf(Fx23, 1, df3)]
Ejemplo n.º 5
0
#!/usr/bin/env python
import numpy as np
import GEOST_thermo as thermo
import matplotlib.pyplot as plt

kB = 8.6173324E-05  #eV/K
B = [1, 100., 300.]
D = thermo.debye(B)

X = np.zeros((2,24), dtype=float)
for i in range(X.shape[1]):
    X[0,i] = 100. - float(i)
    X[1,i] = 1000.
    
B = np.zeros(3)
B[0] = 1000.
B[1] = 1.5
B[2] = 1.

TD = np.zeros(X.shape[1])
U  = np.zeros(X.shape[1])
Cv = np.zeros(X.shape[1])
for i in range(U.shape[0]):
    TD[i] = 1000.*np.exp(B[1] - B[1]*(100./X[0,i])**(-B[2]))
    U[i]  = D.U(TD[i], X[1,i])
    Cv[i] = D.Cv(TD[i], X[1,i])

plt.figure()
plt.subplot(221)
plt.title(r'$\Theta_{D}$')
plt.xlabel("Volume")
Ejemplo n.º 6
0
    VTerr[0,i+1*n] = Verrhit[i+1*n]
    VT[0,i+2*n] = Vhit[i+2*n]
    VTerr[0,i+2*n] = Verrhit[i+2*n]
    VT[1,i+0*n] = 1000.   # Hi-T's
    VTerr[1,i+0*n] = 10.
    VT[1,i+1*n] = 1500.
    VTerr[1,i+1*n] = 20.
    VT[1,i+2*n] = 2000.
    VTerr[1,i+2*n] = 30.
    
# Generate pressures
A = np.zeros(3, dtype=float)
A[0] = 700.    # ThetaD0
A[1] = 1.5     # gD0
A[2] = 1.      # q
D = GEOST_thermo.debye([20, ref_Biso[-1], 273.]) # Instantiate debye
Phit = D.P_thermal(A, VT) + np.random.normal(0,0.5,3*n)
print 'Phit', Phit
Perrhit = abs(np.random.normal(0,1,3*n))
Perrhit = np.sort(Perrhit)

print "Thermal EOS refinement using Debye"
print "True values & initial guesses:", A
# ODR SETUP for isothermal EOS
# model contains information about the ODR functions.
#        fcn   = model function to refine parameters from
#        fjacb = derivatives of fcn w.r.t. parameters
#        fjacd = derivatives of fcn w.r.t. independent var.
odr_model = odrpack.Model(fcn=D.P_thermal)
odr_data  = odrpack.RealData(x=VT, y=Phit, sx=VTerr, sy=Perrhit)
odr       = odrpack.ODR(odr_data, odr_model, beta0=A, maxit=100)
Ejemplo n.º 7
0
A = np.zeros(3)    # Debye setup
A[0] = 20.         # No. atoms/cell
A[1] = B[1]        # V0
A[2] = 273.        # Reference temperature (K)

data273 = data(N,B)
X273 = np.zeros((2,N), dtype=float)  # Volume
X273[0,:] = data(N,B).V
X273[1,:] = 273.
Y273 = data(N,B).P
e273 = np.zeros((2,N), dtype=float)  # errs
e273[0,:] = data(N,B).Verr
e273[1,:] = data(N,B).Perr

debye273 = thermo.debye(A)
C = np.zeros(3)
C[0] = 1000.
C[1] = 1.5
C[2] = 1.

###

# 700 K
N = 24
K0 = 100.
V0 = 202.

B = np.ones(2)     # isothermal EOS initial parameters
B[0] = K0          # K0
B[1] = V0          # V0