@@ -633,17 +633,22 @@ def normalize_dataset_missing_values(dataset):
633633 current_missing = var .attrs .get ("missing_value" )
634634 current_fill = var .attrs .get ("_FillValue" )
635635
636- # Build conditions for values that should become NaN
636+ # Build conditions for values that should become NaN.
637+ # NOTE: use ``abs(var - m) <= atol`` rather than np.isclose(var, m).
638+ # np.isclose is not a ufunc, so on a Dask-backed array it does not
639+ # dispatch lazily — it eagerly materialises the whole array to NumPy.
640+ # For long daily variables that means loading the entire (multi-GB)
641+ # series into one worker and OOM-killing it. ``abs`` / ``<=`` are
642+ # Dask-native and stay lazy. With rtol=0, this is exactly np.isclose.
637643 nan_conditions = []
644+ atol = 1e-3
638645
639646 # Check for current missing_value
640647 if current_missing is not None :
641648 try :
642649 current_missing = float (current_missing )
643650 if not np .isnan (current_missing ): # Don't double-convert NaN
644- nan_conditions .append (
645- np .isclose (var , current_missing , rtol = 0 , atol = 1e-3 )
646- )
651+ nan_conditions .append (abs (var - current_missing ) <= atol )
647652 except (ValueError , TypeError ):
648653 pass
649654
@@ -652,9 +657,7 @@ def normalize_dataset_missing_values(dataset):
652657 try :
653658 current_fill = float (current_fill )
654659 if not np .isnan (current_fill ): # Don't double-convert NaN
655- nan_conditions .append (
656- np .isclose (var , current_fill , rtol = 0 , atol = 1e-3 )
657- )
660+ nan_conditions .append (abs (var - current_fill ) <= atol )
658661 except (ValueError , TypeError ):
659662 pass
660663
0 commit comments