Example #1
0
def test_zero_mean_normalized_correlation():
    np.testing.assert_approx_equal(
        zero_mean_normalized_correlation(3,
                                         np.linalg.norm([2 / 3, 1 / 3, 1 / 3]),
                                         1 / 3, [1, 0, 0], [1, 0, 0]),
        1,
    )
    # nb_pixels,image_std,average_image_intensity,image_intensities,int_local
    assert zero_mean_normalized_correlation(3, 0, 1, [1, 1, 1], [0, 0, 1]) == 0
Example #2
0
def _correlate_templates(image, library, n_largest, method, mask):
    r"""Correlates all simulated diffraction templates in a DiffractionLibrary
    with a particular experimental diffraction pattern (image).

    Calculated using the normalised (see return type documentation) dot
    product, or cosine distance,

    .. math:: fast_correlation
        \\frac{\\sum_{j=1}^m P(x_j, y_j) T(x_j, y_j)}{\\sqrt{\\sum_{j=1}^m T^2(x_j, y_j)}}

    .. math:: zero_mean_normalized_correlation
        \\frac{\\sum_{j=1}^m P(x_j, y_j) T(x_j, y_j)- avg(P)avg(T)}{\\sqrt{\\sum_{j=1}^m (T(x_j, y_j)-avg(T))^2+\sum_{j=1}^m P(x_j,y_j)-avg(P)}}
        for a template T and an experimental pattern P.

    Parameters
    ----------
    image : numpy.array
        The experimental diffraction pattern of interest.
    library : DiffractionLibrary
        The library of diffraction simulations to be correlated with the
        experimental data.
    n_largest : int
        The number of well correlated simulations to be retained per phase
    method : str
        Name of method used to compute correlation between templates and diffraction patterns. Can be
        'fast_correlation' or 'zero_mean_normalized_correlation'.
    mask : bool
        A mask for navigation axes. 1 indicates positions to be indexed.


    Returns
    -------
    top_matches : numpy.array
        Array of shape (<num phases>*n_largest, 5) containing the top n
        correlated simulations for the experimental pattern of interest, where
        each entry is on the form [phase index,alpha,beta,gamma,correlation].


    References
    ----------
    E. F. Rauch and L. Dupuy, “Rapid Diffraction Patterns identification through
       template matching,” vol. 50, no. 1, pp. 87–99, 2005.

    """
    phase_count = len(library.keys())
    top_matches = np.zeros((n_largest * phase_count, 5))

    # return for the masked data
    if mask != 1:
        return top_matches

    if method == "zero_mean_normalized_correlation":
        nb_pixels = image.shape[0] * image.shape[1]
        average_image_intensity = np.average(image)
        image_std = np.linalg.norm(image - average_image_intensity)

    for phase_number, phase in enumerate(library.keys()):
        saved_results = np.zeros((n_largest, 5))
        saved_results[:, 0] = phase_number

        for entry_number in np.arange(len(library[phase]['orientations'])):
            orientations = library[phase]["orientations"][entry_number]
            pixel_coords = library[phase]["pixel_coords"][entry_number]
            intensities = library[phase]["intensities"][entry_number]

            # Extract experimental intensities from the diffraction image
            image_intensities = image[pixel_coords[:, 1], pixel_coords[:, 0]]

            if method == "zero_mean_normalized_correlation":
                corr_local = zero_mean_normalized_correlation(
                    nb_pixels,
                    image_std,
                    average_image_intensity,
                    image_intensities,
                    intensities,
                )

            elif method == "fast_correlation":
                corr_local = fast_correlation(
                    image_intensities, intensities,
                    library[phase]["pattern_norms"][entry_number])

            if corr_local > np.min(saved_results[:, 4]):
                row_index = np.argmin(saved_results[:, 4])
                or_saved[row_index, 1:3] = or_local
                corr_saved[row_index, 4] = corr_local

        phase_sorted = saved_results[saved_results[:, 4].argsort()]
        start_slot = phase_number * n_largest
        end_slot = (phase_number + 1) * n_largest
        top_matches[start_slot:end_slot, :] = phase_sorted

    return top_matches