예제 #1
0
    def test_return_shape(self):
        """
        Check that the returned covariance matrix is the correct size
        :return: Nothing
        """
        print("Testing that covarxy_pv returns 1 dimensional matrix")

        cov = covarxy_pv(self.input_coords, self.coords, self.long, self.lat,
                         self.phi, self.no_pv)

        self.assertEqual(cov.shape, (3, ),
                         "covarxy_pv matrix is incorrect shape")
예제 #2
0
    def test_returns_ones(self):
        """
        Check that we get a matrix of almost ones if data is very close (according to scale)
        :return: nothing
        """

        print("Testing that covarxy_pv returns almost ones if data is close")

        cov = covarxy_pv(self.input_coords, self.coords, 99999999, 99999999,
                         self.phi, self.no_pv)
        for i in cov:
            self.assertAlmostEqual(
                i, 1, 15, "elements in covarxy_pv matrix are not correct")
예제 #3
0
    def test_returns_correct(self):
        """
        Check that the returned covriance matrix contains the correct values
        :return: Nothing
        """

        print("Testing that covarxy_pv returns correct values")

        ans = np.array([1, 0.9134, 0.5941])

        cov = covarxy_pv(self.input_coords, self.coords, self.long, self.lat,
                         self.phi, self.no_pv)

        for i in range(0, ans.size):
            self.assertAlmostEqual(
                ans[i], cov[i], 4,
                "elements in covarxy_pv matrix are not correct")
예제 #4
0
def build_cov(ptmp, coord_float, config):
    """
    Build the covariance matrix
    :param ptmp: matrix of potential temperatures
    :param coord_float_config: the x, y, z position of the float
    :return: covariance matrix
    """

    # Set up theta boundaries for water masses

    ptboundaries = np.array([30, 24, 18, 12, 8, 4, 2.5, 1, -2])
    ptscale_down = np.array([6, 6, 6, 4, 4, 1.5, 1.5, 1, 1])
    ptscale_up = np.array([6, 6, 6, 6, 4, 4, 1.5, 1.5, 1])

    # Set up the building tile = vertical covariance matrix

    # The upper triangle of the matrix (top right values) are the covariance of each ptlevel with
    # every ptlevel below it, looking down the water column from the diagonal
    # The lower triangle of the matrix (bottom left values) are the covariance of each ptlevel with
    # every ptlevel above it, looking up the water column from the diagonal

    ptmp_rows = ptmp.shape[0]
    ptmp_columns = ptmp.shape[1]

    # set up the covariance matrix
    cov = np.zeros((ptmp_rows * ptmp_columns, ptmp_rows))

    # set up interpolation grids
    upper_interp = interpolate.interp1d(ptboundaries, ptscale_down)
    lower_interp = interpolate.interp1d(ptboundaries, ptscale_up)

    # go through each profile
    for profile in range(0, ptmp_columns):

        profile_1 = profile * ptmp_rows

        # go through each level
        for i in range(0, ptmp_rows):
            for j in range(0, ptmp_rows):

                # belongs in the upper triangle, look down water column for vertical scale
                if i < j:
                    l_theta = upper_interp(ptmp[i, profile])
                    cov[i + profile_1, j] = np.exp(
                        -1 * (ptmp[j, profile] - ptmp[i, profile])**2 /
                        l_theta**2)

                # belongs in the lower triangle, look up water column for vertical scale
                elif i > j:
                    l_theta = lower_interp(ptmp[i, profile])
                    cov[i + profile_1, j] = np.exp(
                        -1 * (ptmp[j, profile] - ptmp[i, profile])**2 /
                        l_theta**2)

                # it is in the leading diagonal, so make it equal to 1
                else:
                    cov[i + profile_1, j] = 1

                # if we don't have a value, make it equal to 1
                if np.isnan(cov[i + profile_1, j]):
                    cov[i + profile_1, j] = 1

    # set up matrix to hold horizontal covariance
    h_cov = np.ones((ptmp_columns, ptmp_columns)) * np.nan

    for profile in range(0, ptmp_columns):
        h_cov[profile, :] = covarxy_pv(coord_float[profile], coord_float,
                                       config['MAPSCALE_LONGITUDE_SMALL'],
                                       config['MAPSCALE_LATITUDE_SMALL'],
                                       config['MAPSCALE_PHI_SMALL'],
                                       config['MAPSCALE_USE_PV'])

    h_cov = h_cov[:, 0:ptmp_columns]

    # build final covariance matrix, using horizontal and vertical covariance

    n_cov = np.tile(cov, [1, ptmp_columns])

    # Have to find the covariance for each profile against all other profiles
    for profile in range(0, ptmp_columns):

        lower = profile * ptmp_rows
        upper = (profile + 1) * ptmp_rows

        # go through each profile
        for profile_1 in range(0, ptmp_columns):
            lower_1 = profile_1 * ptmp_rows
            upper_1 = (profile_1 + 1) * ptmp_rows
            n_cov[lower:upper, lower_1:upper_1] = h_cov[profile, profile_1] * \
                                                  n_cov[lower:upper, lower_1:upper_1]

    return n_cov