示例#1
0
    def cfunits_conform(self, to_units, from_units=None):
        """
        Conform value units in-place. If there are scale or offset parameters in the attribute dictionary, they will
        be removed.

        :param to_units: Target conform units.
        :type to_units: str or units object
        :param from_units: Overload source units.
        :type from_units: str or units object
        :raises: NoUnitsError
        """
        if from_units is None and self.units is None:
            raise NoUnitsError(self)

        # Use overloaded value for source units.
        from_units = self.cfunits if from_units is None else from_units

        # Get the conform value before swapping the units. Conversion inside time dimensions may be negatively affected
        # otherwise.
        to_conform_value = self._get_to_conform_value_()

        # Update the units attribute with the destination units. Do this before conversion to not enter recursion when
        # setting the new value.
        self.units = to_units

        # Conform the units.
        new_value = get_conformed_units(to_conform_value, from_units, to_units)
        self._set_to_conform_value_(new_value)

        # Let the data type load from the value array.
        self._dtype = None
        # Remove any compression attributes if present.
        for remove in NETCDF_ATTRIBUTES_TO_REMOVE_ON_VALUE_CHANGE:
            self.attrs.pop(remove, None)
示例#2
0
 def bounds(self, value):
     self._bounds = get_none_or_2d(value)
     if self._bounds is not None and self._original_units is not None:
         are_units_equal = get_are_units_equal((self.units, self._original_units))
         if not are_units_equal:
             self._bounds = get_conformed_units(self._bounds, self._original_units, self.conform_units_to)
     if value is not None:
         self._validate_bounds_()
示例#3
0
    def cfunits_conform(self, *args, **kwargs):
        # Get the from units before conforming the value. The units are changed in the value conform.
        from_units = kwargs.get('from_units') or self.cfunits
        # Store the original units to use for bounds conversion.
        self._original_units = self.cfunits
        # Conform the value.
        AbstractSourcedVariable.cfunits_conform(self, *args, **kwargs)

        # Conform the units
        if self._bounds is not None:
            self._bounds = get_conformed_units(self._bounds, from_units, args[0])
示例#4
0
 def test_get_field_with_overloaded_units(self):
     rd = self.test_data.get_rd('cancm4_tas', kwds={'conform_units_to': 'celsius'})
     preload = [False, True]
     for pre in preload:
         field = rd.get()
         # Conform units argument needs to be attached to a field variable.
         units_celsius = get_units_object('celsius')
         self.assertEqual(field.variables['tas']._conform_units_to, units_celsius)
         sub = field.get_time_region({'year': [2009], 'month': [5]})
         if pre:
             # If we wanted to load the data prior to subset then do so and manually perform the units conversion.
             to_test = sub.variables['tas'].value.copy()
             get_conformed_units(to_test, sub.variables['tas'].cfunits, units_celsius)
         # Assert the conform attribute makes it though the subset
         self.assertEqual(sub.variables['tas']._conform_units_to, units_celsius)
         value = sub.variables['tas'].value
         self.assertAlmostEqual(np.ma.mean(value), 5.921925206338206)
         self.assertAlmostEqual(np.ma.median(value), 10.745431900024414)
         if pre:
             # Assert the manually converted array matches the loaded value.
             self.assertNumpyAll(to_test, value)
示例#5
0
 def test_get_conformed_units(self):
     value = np.array([5, 6, 7])
     res = get_conformed_units(value, 'celsius', 'fahrenheit')
     try:
         import cf_units
         # Test original values are unchanged.
         self.assertEqual(np.mean(value), 6)
         test_value = res
     except ImportError:
         import cfunits
         # Test inplace conversion is used.
         test_value = value
     # Test values are conformed.
     self.assertAlmostEqual(np.mean(test_value), 42.799999999999876)
示例#6
0
 def test_get_conformed_units(self):
     value = np.array([5, 6, 7])
     res = get_conformed_units(value, 'celsius', 'fahrenheit')
     try:
         import cf_units
         # Test original values are unchanged.
         self.assertEqual(np.mean(value), 6)
         test_value = res
     except ImportError:
         import cfunits
         # Test inplace conversion is used.
         test_value = value
     # Test values are conformed.
     self.assertAlmostEqual(np.mean(test_value), 42.799999999999876)