Beispiel #1
0
def H_var_coeff(coeff, qm, qu, dim):
    """
    H_var_coeff(coeff, qm, qu, dim)

    Variance of mean curvature H across surface determined by coeff at
    resolution qu

    Parameters
    ----------

    coeff:	float, array_like; shape=(n_frame, n_waves**2)
        Optimised surface coefficients
    qm:  int
        Maximum number of wave frequencies in Fouier Sum representing
        intrinsic surface
    qu:  int
        Upper limit of wave frequencies in Fouier Sum representing
        intrinsic surface
    dim:  float, array_like; shape=(3)
        XYZ dimensions of simulation cell

    Returns
    -------

    H_var:  float
        Variance of mean curvature H across whole surface

    """

    if qu == 0:
        return 0

    n_waves = 2 * qm + 1

    u_array = np.array(np.arange(n_waves**2) / n_waves, dtype=int) - qm
    v_array = np.array(np.arange(n_waves**2) % n_waves, dtype=int) - qm
    wave_filter = ((u_array >= -qu) * (u_array <= qu) * (v_array >= -qu) *
                   (v_array <= qu))
    indices = np.argwhere(wave_filter).flatten()
    Psi = vcheck(u_array, v_array)[indices] / 4.

    coeff_filter = coeff[:, :, indices]
    av_coeff_2 = np.mean(coeff_filter**2, axis=(0, 1)) * Psi

    H_var_array = av_coeff_2[indices] * vcheck(u_array[indices],
                                               v_array[indices])
    H_var_array *= (u_array[indices]**4 / dim[0]**4 +
                    v_array[indices]**4 / dim[1]**4 +
                    2 * u_array[indices]**2 * v_array[indices]**2 /
                    (dim[0]**2 * dim[1]**2))
    H_var = 16 * np.pi**4 * np.sum(H_var_array)

    return H_var
def xi_var(coeff, qm, qu):
    """Calculate average variance of surface heights

    Parameters
    ----------
    coeff:	float, array_like; shape=(n_frame, n_waves**2)
        Optimised surface coefficients
    qm:  int
        Maximum number of wave frequencies in Fourier Sum
        representing intrinsic surface
    qu:  int
        Upper limit of wave frequencies in Fourier Sum
        representing intrinsic surface

    Returns
    -------
    calc_var: float
        Variance of surface heights across whole surface

    """

    u_array, v_array = wave_arrays(qm)
    indices = wave_indices(qu, u_array, v_array)

    Psi = vcheck(u_array[indices], v_array[indices]) / 4.

    coeff_filter = coeff[:, :, indices]
    mid_point = len(indices) / 2

    av_coeff = np.mean(coeff_filter[:, :, mid_point], axis=0)
    av_coeff_2 = np.mean(coeff_filter**2, axis=(0, 1)) * Psi

    calc_var = np.sum(av_coeff_2) - np.mean(av_coeff**2, axis=0)

    return calc_var
def initialise_surface(qm, phi, dim):
    """
    Calculate initial parameters for ISM

    Parameters
    ----------
    qm:  int
        Maximum number of wave frequencies in Fourier Sum
        representing intrinsic surface
    phi:  float
        Weighting factor of minimum surface area term in surface
        optimisation function
    dim:  float, array_like; shape=(3)
        XYZ dimensions of simulation cell

    Returns
    -------

    coeff:	array_like (float); shape=(n_waves**2)
        Optimised surface coefficients
    A:  float, array_like; shape=(n_waves**2, n_waves**2)
        Matrix containing wave product weightings
        f(x, u1, Lx).f(y, v1, Ly).f(x, u2, Lx).f(y, v2, Ly)
        for each coefficient in the linear algebra equation
        Ax = b for both surfaces
    b:  float, array_like; shape=(n_waves**2)
        Vector containing solutions z.f(x, u, Lx).f(y, v, Ly)
        to the linear algebra equation Ax = b
        for both surfaces
    area_diag: float, array_like; shape=(n_waves**2)
        Surface area diagonal terms for A matrix
    """

    n_waves = 2*qm+1

    # Form the diagonal xi^2 terms
    u_array, v_array = wave_arrays(qm)
    uv_check = vcheck(u_array, v_array)

    # Make diagonal terms of A matrix
    area_diag = phi * (
        u_array**2 * dim[1] / dim[0]
        + v_array**2 * dim[0] / dim[1]
    )
    area_diag = 4 * np.pi**2 * np.diagflat(area_diag * uv_check)

    # Create empty A matrix and b vector for linear algebra
    # equation Ax = b
    A = np.zeros((2, n_waves**2, n_waves**2))
    b = np.zeros((2, n_waves**2))
    coeff = np.zeros((2, n_waves**2))

    return coeff, A, b, area_diag
def initialise_recon(qm, phi, dim):
    """
    Calculate initial parameters for reconstructed
    ISM fitting procedure

    Parameters
    ----------
    qm:  int
        Maximum number of wave frequencies in Fourier Sum
        representing intrinsic surface
    phi:  float
        Weighting factor of minimum surface area term in surface
        optimisation function
    dim:  float, array_like; shape=(3)
        XYZ dimensions of simulation cell

    Returns
    -------
    psi:  float
        Weighting factor for surface reconstruction function
    curve_matrix: float, array_like; shape=(n_waves**2, n_waves**2)
        Surface curvature terms for A matrix
    H_var: float, array_like; shape=(n_waves**2)
        Diagonal terms for global variance of mean curvature
    """

    psi = phi * dim[0] * dim[1]
    n_waves = 2 * qm + 1

    "Form the diagonal xi^2 terms"
    u_array, v_array = wave_arrays(qm)
    uv_check = vcheck(u_array, v_array)

    u_matrix = np.tile(u_array, (n_waves**2, 1))
    v_matrix = np.tile(v_array, (n_waves**2, 1))

    H_var = 4 * np.pi**4 * uv_check * (
        u_array**4 / dim[0]**4 + v_array**4 / dim[1]**4
        + 2 * (u_array * v_array)**2 / np.prod(dim**2)
    )

    curve_matrix = 16 * np.pi**4 * (
        (u_matrix * u_matrix.T)**2 / dim[0]**4 +
        (v_matrix * v_matrix.T)**2 / dim[1]**4 +
        ((u_matrix * v_matrix.T)**2 +
         (u_matrix.T * v_matrix)**2) / np.prod(dim**2)
    )

    return psi, curve_matrix, H_var
Beispiel #5
0
def surface_tension_coeff(coeff_2, qm, qu, dim, T):
    """
    Returns spectrum of surface tension, corresponding to
    the frequencies in q2_set

    Parameters
    ----------

    coeff_2:  float, array_like; shape=(n_waves**2)
        Square of optimised surface coefficients
    qm:  int
        Maximum number of wave frequencies in Fourier Sum
        representing intrinsic surface
    qu:  int
        Upper limit of wave frequencies in Fourier Sum
        representing intrinsic surface
    dim:  float, array_like; shape=(3)
        XYZ dimensions of simulation cell
    T:  float
        Average temperature of simulation (K)

    Returns
    -------
    unique_q:  float, array_like
        Set of frequencies for power spectrum histogram
    av_gamma:  float, array_like
        Surface tension histogram of Fourier series frequencies

    """

    u_array, v_array = wave_arrays(qm)

    indices = wave_indices(qu, u_array, v_array)

    q, q2 = calculate_frequencies(u_array[indices], v_array[indices], dim)

    int_A = dim[0] * dim[1] * q2 * coeff_2[indices] * vcheck(
        u_array[indices], v_array[indices]) / 4
    gamma = con.k * T * 1E23 / int_A

    unique_q, av_gamma = filter_frequencies(q, gamma)

    return unique_q, av_gamma
Beispiel #6
0
def power_spectrum_coeff(coeff_2, qm, qu, dim):
    """
    Returns power spectrum of average surface coefficients,
    corresponding to the frequencies in q2_set

    Parameters
    ----------

    coeff_2:  float, array_like; shape=(n_waves**2)
        Square of optimised surface coefficients
    qm:  int
        Maximum number of wave frequencies in Fourier Sum
        representing intrinsic surface
    qu:  int
        Upper limit of wave frequencies in Fourier Sum
        representing intrinsic surface
    dim:  float, array_like; shape=(3)
        XYZ dimensions of simulation cell

    Returns
    -------
    unique_q:  float, array_like
        Set of frequencies for power spectrum
        histogram
    av_fourier:  float, array_like
        Power spectrum histogram of Fourier
        series coefficients

    """

    u_array, v_array = wave_arrays(qm)

    indices = wave_indices(qu, u_array, v_array)

    q, q2 = calculate_frequencies(u_array[indices], v_array[indices], dim)

    fourier = coeff_2[indices] / 4 * vcheck(u_array[indices], v_array[indices])

    # Remove redundant frequencies
    unique_q, av_fourier = filter_frequencies(q, fourier)

    return unique_q, av_fourier
Beispiel #7
0
def intrinsic_area(coeff, qm, qu, dim):
    """
    Calculate the intrinsic surface area from coefficients
    at resolution qu

    Parameters
    ----------

    coeff:	float, array_like; shape=(n_waves**2)
        Optimised surface coefficients
    qm:  int
        Maximum number of wave frequencies in Fourier Sum
        representing intrinsic surface
    qu:  int
        Upper limit of wave frequencies in Fourier Sum
        representing intrinsic surface
    dim:  float, array_like; shape=(3)
        XYZ dimensions of simulation cell

    Returns
    -------

    int_A:  float
        Relative size of intrinsic surface area, compared
        to cell cross section XY
    """

    u_array, v_array = wave_arrays(qm)
    indices = wave_indices(qu, u_array, v_array)

    q2 = np.pi**2 * (u_array[indices]**2 / dim[0]**2 +
                     v_array[indices]**2 / dim[1]**2)

    int_A = q2 * coeff[indices]**2 * vcheck(u_array[indices], v_array[indices])
    int_A = 1 + 0.5 * np.sum(int_A)

    return int_A
Beispiel #8
0
def coeff_to_fourier_2(coeff_2, qm, dim):
    """Converts square coefficients to square Fourier
    coefficients"""

    n_waves = 2 * qm + 1
    u_mat, v_mat = np.meshgrid(np.arange(-qm, qm + 1), np.arange(-qm, qm + 1))
    x_mat, y_mat = np.meshgrid(np.linspace(0, 1 / dim[0], n_waves),
                               np.linspace(0, 1 / dim[1], n_waves))

    Psi = vcheck(u_mat.flatten(), v_mat.flatten()) / 4.

    frequencies = np.pi * 2 * (u_mat * x_mat + y_mat * v_mat) / n_waves
    amplitudes_2 = np.reshape(Psi * coeff_2, (n_waves, n_waves))

    A = np.zeros((n_waves, n_waves))

    for i in range(n_waves):
        for j in range(n_waves):
            A[i][j] += (
                amplitudes_2 *
                np.exp(-2 * np.pi * 1j / n_waves *
                       (u_mat * x_mat[i][j] + y_mat[i][j] * v_mat))).sum()

    return A, frequencies