使用nptyping标注含NDArray的元组返回函数时遇错误求解决
解决nptyping中NDArray联合类型注解的错误
错误根源是nptyping的NDArray不支持直接用Python原生的|运算符表示联合数据类型,它要求数据类型参数为字符串描述,或使用nptyping提供的Union包裹多个类型。以下是两种可行的修正方案:
方案1:使用nptyping的Union
从nptyping导入Union,用它来包裹多个数据类型,替代Int32 | Float32的写法:
from nptyping import NDArray, UInt8, Int32, Float32, Shape, Bool, Union import numpy as np import rasterio from typing import Generator, Any, Final, Literal def _scale_and_round( self, arr: NDArray[Any, Float32] ) -> tuple[NDArray[Any, Union[Int32, Float32]], dict[str, Any]]: array: NDArray[Any, Any] = arr * self.scale_factor if self.scale_factor == 1000: array = array.astype(np.int32) return array, self.metadata def ndvi( self, red_src: Any, nir_src: Any ) -> tuple[NDArray[Any, Union[Int32, Float32]], dict[str, Any]]: redB: NDArray[Any, Any] = red_src.read() nirB: NDArray[Any, Any] = nir_src.read() np.seterr(divide="ignore", invalid="ignore") ndvi: NDArray[Any, Float32] = ( nirB.astype(np.float32) - redB.astype(np.float32) ) / (nirB.astype(np.float32) + redB.astype(np.float32)) # replace nan with 0 where_are_NaNs: NDArray[Any, Bool] = np.isnan(ndvi) ndvi[where_are_NaNs] = 0 return self._scale_and_round(ndvi)
方案2:使用字符串形式的联合类型
直接用字符串描述联合类型,无需额外导入Union:
from nptyping import NDArray, UInt8, Int32, Float32, Shape, Bool import numpy as np import rasterio from typing import Generator, Any, Final, Literal def _scale_and_round( self, arr: NDArray[Any, Float32] ) -> tuple[NDArray[Any, "Int32 | Float32"], dict[str, Any]]: array: NDArray[Any, Any] = arr * self.scale_factor if self.scale_factor == 1000: array = array.astype(np.int32) return array, self.metadata def ndvi( self, red_src: Any, nir_src: Any ) -> tuple[NDArray[Any, "Int32 | Float32"], dict[str, Any]]: redB: NDArray[Any, Any] = red_src.read() nirB: NDArray[Any, Any] = nir_src.read() np.seterr(divide="ignore", invalid="ignore") ndvi: NDArray[Any, Float32] = ( nirB.astype(np.float32) - redB.astype(np.float32) ) / (nirB.astype(np.float32) + redB.astype(np.float32)) # replace nan with 0 where_are_NaNs: NDArray[Any, Bool] = np.isnan(ndvi) ndvi[where_are_NaNs] = 0 return self._scale_and_round(ndvi)
注意:原代码缺少import numpy as np,需补充后才能正常运行np.int32、np.isnan等调用。
内容的提问来源于stack exchange,提问作者diegus
相关产品推荐
相关产品推荐

