示例#1
0
 def test_wrong_method_fail(self):
     ''' Check exception is thrown when wrong method is given'''
     with self.assertLogs('climada.util.interpolation',
                          level='ERROR') as cm:
         interp.interpol_index(np.ones((10, 2)), np.ones((7, 2)), 'method')
     self.assertIn('Interpolation using method' + \
         ' with distance haversine is not supported.', cm.output[0])
 def test_wrong_method_fail(self):
     """Check exception is thrown when wrong method is given"""
     with self.assertRaises(ValueError) as cm:
         u_interp.interpol_index(np.ones((10, 2)), np.ones((7, 2)),
                                 'method')
     self.assertIn(
         'Interpolation using method with distance haversine is not supported.',
         str(cm.exception))
 def test_wrong_distance_fail(self):
     """Check exception is thrown when wrong distance is given"""
     with self.assertRaises(ValueError) as cm:
         u_interp.interpol_index(np.ones((10, 2)),
                                 np.ones((7, 2)),
                                 distance='distance')
     self.assertIn(
         'Interpolation using NN with distance distance is not supported.',
         str(cm.exception))
示例#4
0
 def test_wrong_coord_fail(self):
     """Check exception is thrown when coordinates missing one dimension"""
     with self.assertRaises(IndexError):
         interp.interpol_index(np.ones((10, 2)),
                               np.ones((7, 1)),
                               distance='approx')
     with self.assertRaises(ValueError):
         interp.interpol_index(np.ones((10, 2)),
                               np.ones((7, 1)),
                               distance='haversine')
示例#5
0
 def test_wrong_distance_fail(self):
     """Check exception is thrown when wrong distance is given"""
     with self.assertLogs('climada.util.interpolation',
                          level='ERROR') as cm:
         interp.interpol_index(np.ones((10, 2)),
                               np.ones((7, 2)),
                               distance='distance')
     self.assertIn(
         'Interpolation using NN with distance distance is not supported.',
         cm.output[0])
示例#6
0
 def test_wrong_centroid_fail(self):
     ''' Check exception is thrown when centroids missing one dimension'''
     with self.assertRaises(IndexError):
         interp.interpol_index(np.ones((10, 1)),
                               np.ones((7, 2)),
                               distance='approx')
     with self.assertRaises(ValueError):
         interp.interpol_index(np.ones((10, 1)),
                               np.ones((7, 2)),
                               distance='haversine')
示例#7
0
    def normal_pass(self, dist):
        """Checking result against matlab climada_demo_step_by_step"""
        # Load input
        exposures, centroids = def_input_values()

        # Interpolate with default threshold
        neighbors = interp.interpol_index(centroids, exposures, 'NN', dist)
        # Reference output
        ref_neighbors = def_ref()
        # Check results
        self.assertEqual(exposures.shape[0], len(neighbors))
        self.assertTrue(np.array_equal(neighbors, ref_neighbors))
示例#8
0
    def assign_centroids(self,
                         hazard,
                         method='NN',
                         distance='haversine',
                         threshold=100):
        """Assign for each exposure coordinate closest hazard coordinate.
        -1 used for disatances > threshold in point distances. If raster hazard,
        -1 used for centroids outside raster.

        Parameters:
            hazard (Hazard): hazard to match (with raster or vector centroids)
            method (str, optional): interpolation method to use in vector hazard.
                Nearest neighbor (NN) default
            distance (str, optional): distance to use in vector hazard. Haversine
                default
            threshold (float): distance threshold in km over which no neighbor
                will be found in vector hazard. Those are assigned with a -1.
                Default 100 km.
        """
        LOGGER.info('Matching %s exposures with %s centroids.',
                    str(self.shape[0]), str(hazard.centroids.size))
        if not co.equal_crs(self.crs, hazard.centroids.crs):
            LOGGER.error('Set hazard and exposure to same CRS first!')
            raise ValueError
        if hazard.centroids.meta:
            x_i = ((self.longitude.values -
                    hazard.centroids.meta['transform'][2]) /
                   hazard.centroids.meta['transform'][0]).astype(int)
            y_i = ((self.latitude.values -
                    hazard.centroids.meta['transform'][5]) /
                   hazard.centroids.meta['transform'][4]).astype(int)
            assigned = y_i * hazard.centroids.meta['width'] + x_i
            assigned[assigned < 0] = -1
            assigned[assigned >= hazard.centroids.size] = -1
        else:
            coord = np.stack([self.latitude.values, self.longitude.values],
                             axis=1)
            if np.array_equal(coord, hazard.centroids.coord):
                assigned = np.arange(self.shape[0])
            else:
                assigned = interpol_index(hazard.centroids.coord,
                                          coord,
                                          method=method,
                                          distance=distance,
                                          threshold=threshold)

        self[INDICATOR_CENTR + hazard.tag.haz_type] = assigned
示例#9
0
    def repeat_coord_pass(self, dist):
        """Check that exposures with the same coordinates have same
        neighbors"""

        # Load input
        exposures, centroids = def_input_values()

        # Repeat a coordinate
        exposures[2, :] = exposures[0, :]

        # Interpolate with default threshold
        neighbors = interp.interpol_index(centroids, exposures, 'NN', dist)

        # Check output neighbors have same size as coordinates
        self.assertEqual(len(neighbors), exposures.shape[0])
        # Check copied coordinates have same neighbors
        self.assertEqual(neighbors[2], neighbors[0])
示例#10
0
    def normal_warning(self, dist):
        """Checking that a warning is raised when minimum distance greater
        than threshold"""
        # Load input
        exposures, centroids = def_input_values()

        # Interpolate with lower threshold to raise warnings
        threshold = 50
        with self.assertLogs('climada.util.interpolation', level='INFO') as cm:
            neighbors = interp.interpol_index(centroids,
                                              exposures,
                                              'NN',
                                              dist,
                                              threshold=threshold)
        self.assertIn("Distance to closest centroid", cm.output[0])

        ref_neighbors = def_ref_50()
        self.assertTrue(np.array_equal(neighbors, ref_neighbors))
示例#11
0
    def set_flooded_area_cut(self, coordinates, centr_indices=None):
        """ Calculates flooded area for any window given with coordinates or
            from indices of hazard centroids. sets yearly flooded area and
            per event
        Parameters:
            coordinates(2d array): coordinates of window
            centr_indices(1d array): indices of hazard centroid
        Raises:
            MemoryError
        """
        if centr_indices is None:
            centr_indices = interpol_index(self.centroids.coord, coordinates)
        self.centroids.set_area_pixel()
        area_centr = self.centroids.area_pixel[centr_indices]
        event_years = np.array([
            date.fromordinal(self.date[i]).year for i in range(len(self.date))
        ])
        years = np.unique(event_years)
        year_ev_mk = self._annual_event_mask(event_years, years)
        try:
            self.fla_ev_centr = np.zeros((self._n_events, len(centr_indices)))
            self.fla_ann_centr = np.zeros((len(years), len(centr_indices)))
            self.fla_ev_centr = np.array(
                np.multiply(self.fraction[:, centr_indices].todense(),
                            area_centr))
            self.fla_event = np.sum(self.fla_ev_centr, axis=1)
            for year_ind in range(len(years)):
                self.fla_ann_centr[year_ind, :] = \
                    np.sum(self.fla_ev_centr[year_ev_mk[year_ind, :], :],
                           axis=0)
            self.fla_annual = np.sum(self.fla_ann_centr, axis=1)
            self.fla_ann_av = np.mean(self.fla_annual)
            self.fla_ev_av = np.mean(self.fla_event)

        except MemoryError:
            self.fla_ev_centr = None
            self.fla_event = None
            self.fla_ann_centr = None
            self.fla_annual = None
            self.fla_ann_av = None
            self.fla_ev_av = None
            LOGGER.warning('Number of events and slected area exceed ' +
                           'memory capacities, area has not been calculated,' +
                           ' attributes set to None')
示例#12
0
    def assign_centroids(self, hazard, method='NN', distance='haversine',
                         threshold=100):
        """ Assign for each exposure coordinate closest hazard coordinate

        Parameters:
            hazard (Hazard): hazard to match
            method (str, optional): interpolation method to use. Nearest
                neighbor (NN) default
            distance (str, optional): distance to use. Haversine default
            threshold (float): distance threshold in km over which no neighbor
                will be found. Those are assigned with a -1 index. Default 100
        """
        LOGGER.info('Matching %s exposures with %s centroids.',
                    str(self.shape[0]), str(hazard.centroids.size))

        coord = np.stack([self.latitude.values, self.longitude.values], axis=1)
        if np.array_equal(coord, hazard.centroids.coord):
            assigned = np.arange(self.shape[0])
        else:
            assigned = interpol_index(hazard.centroids.coord, coord, \
                method=method, distance=distance, threshold=threshold)

        self[INDICATOR_CENTR + hazard.tag.haz_type] = assigned
示例#13
0
    def assign_centroids(self,
                         hazard,
                         method='NN',
                         distance='haversine',
                         threshold=100):
        """Assign for each exposure coordinate closest hazard coordinate.
        -1 used for disatances > threshold in point distances. If raster hazard,
        -1 used for centroids outside raster.

        Parameters:
            hazard (Hazard): hazard to match (with raster or vector centroids)
            method (str, optional): interpolation method to use in vector hazard.
                Nearest neighbor (NN) default
            distance (str, optional): distance to use in vector hazard. Haversine
                default
            threshold (float): distance threshold in km over which no neighbor
                will be found in vector hazard. Those are assigned with a -1.
                Default 100 km.
        """
        LOGGER.info('Matching %s exposures with %s centroids.',
                    str(self.gdf.shape[0]), str(hazard.centroids.size))
        if not u_coord.equal_crs(self.crs, hazard.centroids.crs):
            LOGGER.error('Set hazard and exposure to same CRS first!')
            raise ValueError
        if hazard.centroids.meta:
            xres, _, xmin, _, yres, ymin = hazard.centroids.meta[
                'transform'][:6]
            xmin, ymin = xmin + 0.5 * xres, ymin + 0.5 * yres
            x_i = np.round(
                (self.gdf.longitude.values - xmin) / xres).astype(int)
            y_i = np.round(
                (self.gdf.latitude.values - ymin) / yres).astype(int)
            assigned = y_i * hazard.centroids.meta['width'] + x_i
            assigned[(x_i < 0) | (x_i >= hazard.centroids.meta['width'])] = -1
            assigned[(y_i < 0) | (y_i >= hazard.centroids.meta['height'])] = -1
        else:
            coord = np.stack(
                [self.gdf.latitude.values, self.gdf.longitude.values], axis=1)
            haz_coord = hazard.centroids.coord

            if np.array_equal(coord, haz_coord):
                assigned = np.arange(self.gdf.shape[0])
            else:
                # pairs of floats can be sorted (lexicographically) in NumPy
                coord_view = coord.view(dtype='float64,float64').reshape(-1)
                haz_coord_view = haz_coord.view(
                    dtype='float64,float64').reshape(-1)

                # assign each hazard coordinate to an element in coord using searchsorted
                coord_sorter = np.argsort(coord_view)
                haz_assign_idx = np.fmin(
                    coord_sorter.size - 1,
                    np.searchsorted(coord_view,
                                    haz_coord_view,
                                    side="left",
                                    sorter=coord_sorter))
                haz_assign_idx = coord_sorter[haz_assign_idx]

                # determine which of the assignements match exactly
                haz_match_idx = (
                    coord_view[haz_assign_idx] == haz_coord_view).nonzero()[0]
                assigned = np.full_like(coord_sorter, -1)
                assigned[haz_assign_idx[haz_match_idx]] = haz_match_idx

                # assign remaining coordinates to their geographically nearest neighbor
                if haz_match_idx.size != coord_view.size:
                    not_assigned_mask = (assigned == -1)
                    assigned[not_assigned_mask] = interpol_index(
                        haz_coord,
                        coord[not_assigned_mask],
                        method=method,
                        distance=distance,
                        threshold=threshold)

        self.gdf[INDICATOR_CENTR + hazard.tag.haz_type] = assigned