Skip to content

Commit 632b396

Browse files
authored
Merge pull request #405 from davidhassell/dask-Units
dask: `Data.Units`
2 parents 06ca47d + cb617cc commit 632b396

File tree

3 files changed

+66
-13
lines changed

3 files changed

+66
-13
lines changed

cf/data/dask_utils.py

Lines changed: 43 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,7 @@
1414
from ..cfdatetime import dt2rt, rt2dt
1515
from ..functions import atol as cf_atol
1616
from ..functions import rtol as cf_rtol
17-
18-
# from dask.utils import deepmap # Apply function inside nested lists
17+
from ..units import Units
1918

2019

2120
def _da_ma_allclose(x, y, masked_equal=True, rtol=None, atol=None):
@@ -594,3 +593,45 @@ def cf_dt2rt(a, units):
594593
595594
"""
596595
return dt2rt(a, units_out=units, units_in=None)
596+
597+
598+
def cf_units(a, from_units, to_units):
599+
"""Convert array values to have different equivalent units.
600+
601+
.. versionadded:: TODODASK
602+
603+
.. seealso:: `cf.Data.Units`
604+
605+
:Parameters:
606+
607+
a: `numpy.ndarray`
608+
The array.
609+
610+
from_units: `Units`
611+
The existing units of the array.
612+
613+
to_units: `Units`
614+
The units that the array should be converted to. Must be
615+
equivalent to *from_units*.
616+
617+
:Returns:
618+
619+
`numpy.ndarray`
620+
An array containing values in the new units. In order to
621+
represent the new units, the returned data type may be
622+
different from that of the input array. For instance, if
623+
*a* has an integer data type, *from_units* are kilometres,
624+
and *to_units* are ``'miles'`` then the returned array
625+
will have a float data type.
626+
627+
**Examples**
628+
629+
>>> import numpy as np
630+
>>> a = np.array([1, 2])
631+
>>> print(cf.data.dask_utils.cf_units(a, cf.Units('km'), cf.Units('m')))
632+
[1000. 2000.]
633+
634+
"""
635+
return Units.conform(
636+
a, from_units=from_units, to_units=to_units, inplace=False
637+
)

cf/data/data.py

Lines changed: 7 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@
5050
cf_percentile,
5151
cf_rt2dt,
5252
cf_soften_mask,
53+
cf_units,
5354
cf_where,
5455
)
5556
from .mixin import DataClassDeprecationsMixin
@@ -4699,11 +4700,8 @@ def Units(self, value):
46994700
"Consider using the override_units method instead."
47004701
)
47014702

4702-
if not old_units:
4703-
self.override_units(value, inplace=True)
4704-
return
4705-
4706-
if self.Units.equals(value):
4703+
if not old_units or self.Units.equals(value):
4704+
self._Units = value
47074705
return
47084706

47094707
dtype = self.dtype
@@ -4713,13 +4711,11 @@ def Units(self, value):
47134711
else:
47144712
dtype = _dtype_float
47154713

4716-
def cf_Units(x):
4717-
return Units.conform(
4718-
x=x, from_units=old_units, to_units=value, inplace=False
4719-
)
4720-
47214714
dx = self.to_dask_array()
4722-
dx = dx.map_blocks(cf_Units, dtype=dtype)
4715+
dx = dx.map_blocks(
4716+
partial(cf_units, from_units=old_units, to_units=value),
4717+
dtype=dtype,
4718+
)
47234719
self._set_dask(dx, reset_mask_hardness=False)
47244720

47254721
self._Units = value

cf/test/test_Data.py

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3961,6 +3961,22 @@ def test_Data_fits_in_memory(self):
39613961
d = cf.Data.empty((size,), dtype=float)
39623962
self.assertFalse(d.fits_in_memory())
39633963

3964+
def test_Data_Units(self):
3965+
d = cf.Data(100, "m")
3966+
self.assertEqual(d.Units, cf.Units("m"))
3967+
3968+
d.Units = cf.Units("km")
3969+
self.assertEqual(d.Units, cf.Units("km"))
3970+
self.assertEqual(d.array, 0.1)
3971+
3972+
# Assign non-equivalent units
3973+
with self.assertRaises(ValueError):
3974+
d.Units = cf.Units("watt")
3975+
3976+
# Delete units
3977+
with self.assertRaises(ValueError):
3978+
del d.Units
3979+
39643980
def test_Data_get_data(self):
39653981
d = cf.Data(9)
39663982
self.assertIs(d, d.get_data())

0 commit comments

Comments
 (0)