Package osgeo :: Module gdal_array |
[hide private]
[frames] | no frames]

# Source Code for Module osgeo.gdal_array

      1  # This file was automatically generated by SWIG (http://www.swig.org).
      2  # Version 3.0.12
      3  #
      4  # Do not make changes to this file unless you know what you are doing--modify
      5  # the SWIG interface file instead.
      6
      7  from sys import version_info as _swig_python_version_info
      8  if _swig_python_version_info >= (2, 7, 0):
      9 -    def swig_import_helper():
     10          import importlib
     11          pkg = __name__.rpartition('.')[0]
     12          mname = '.'.join((pkg, '_gdal_array')).lstrip('.')
     13          try:
     14              return importlib.import_module(mname)
     15          except ImportError:
     16              return importlib.import_module('_gdal_array')
     17      _gdal_array = swig_import_helper()
     18      del swig_import_helper
     19  elif _swig_python_version_info >= (2, 6, 0):
     20 -    def swig_import_helper():
     21          from os.path import dirname
     22          import imp
     23          fp = None
     24          try:
     25              fp, pathname, description = imp.find_module('_gdal_array', [dirname(__file__)])
     26          except ImportError:
     27              import _gdal_array
     28              return _gdal_array
     29          try:
     30              _mod = imp.load_module('_gdal_array', fp, pathname, description)
     31          finally:
     32              if fp is not None:
     33                  fp.close()
     34          return _mod
     35      _gdal_array = swig_import_helper()
     36      del swig_import_helper
     37  else:
     38      import _gdal_array
     39  del _swig_python_version_info
     40
     41  try:
     42      _swig_property = property
     43  except NameError:
     44      pass  # Python < 2.2 doesn't have 'property'.
     45
     46  try:
     47      import builtins as __builtin__
     48  except ImportError:
     49      import __builtin__
     50
     51 -def _swig_setattr_nondynamic(self, class_type, name, value, static=1):
     52      if (name == "thisown"):
     53          return self.this.own(value)
     54      if (name == "this"):
     55          if type(value).__name__ == 'SwigPyObject':
     56              self.__dict__[name] = value
     57              return
     58      method = class_type.__swig_setmethods__.get(name, None)
     59      if method:
     60          return method(self, value)
     61      if (not static):
     62          if _newclass:
     63              object.__setattr__(self, name, value)
     64          else:
     65              self.__dict__[name] = value
     66      else:
     67          raise AttributeError("You cannot add attributes to %s" % self)
     68
     69
     70 -def _swig_setattr(self, class_type, name, value):
     71      return _swig_setattr_nondynamic(self, class_type, name, value, 0)
     72
     73
     74 -def _swig_getattr(self, class_type, name):
     75      if (name == "thisown"):
     76          return self.this.own()
     77      method = class_type.__swig_getmethods__.get(name, None)
     78      if method:
     79          return method(self)
     80      raise AttributeError("'%s' object has no attribute '%s'" % (class_type.__name__, name))
     81
     82
     83 -def _swig_repr(self):
     84      try:
     85          strthis = "proxy of " + self.this.__repr__()
     86      except __builtin__.Exception:
     87          strthis = ""
     88      return "<%s.%s; %s >" % (self.__class__.__module__, self.__class__.__name__, strthis,)
     89
     90  try:
     91      _object = object
     92      _newclass = 1
     93  except __builtin__.Exception:
     94 -    class _object:
     95          pass
     96      _newclass = 0
     97
     98  from sys import version_info as _swig_python_version_info
     99  if _swig_python_version_info >= (2, 7, 0):
    100      from . import gdal
    101  else:
    102      import gdal
    103  del _swig_python_version_info
    104 -class VirtualMem(_object):
    105      """Proxy of C++ CPLVirtualMemShadow class."""
    106
    107      __swig_setmethods__ = {}
    108      __setattr__ = lambda self, name, value: _swig_setattr(self, VirtualMem, name, value)
    109      __swig_getmethods__ = {}
    110      __getattr__ = lambda self, name: _swig_getattr(self, VirtualMem, name)
    111
    112 -    def __init__(self, *args, **kwargs):
    113          raise AttributeError("No constructor defined")
    114      __repr__ = _swig_repr
    115      __swig_destroy__ = _gdal_array.delete_VirtualMem
    116      __del__ = lambda self: None
    117
    118 -    def GetAddr(self):
    119          """GetAddr(VirtualMem self)"""
    120          return _gdal_array.VirtualMem_GetAddr(self)
    121
    122
    123 -    def Pin(self, start_offset=0, nsize=0, bWriteOp=0):
    124          """
    125          Pin(VirtualMem self, size_t start_offset=0, size_t nsize=0, int bWriteOp=0)
    126          Pin(VirtualMem self, size_t start_offset=0, size_t nsize=0)
    127          Pin(VirtualMem self, size_t start_offset=0)
    128          Pin(VirtualMem self)
    129          """
    130          return _gdal_array.VirtualMem_Pin(self, start_offset, nsize, bWriteOp)
    131
    132  VirtualMem_swigregister = _gdal_array.VirtualMem_swigregister
    133  VirtualMem_swigregister(VirtualMem)
    134
    135
    136 -def _StoreLastException():
    137      """_StoreLastException()"""
    138      return _gdal_array._StoreLastException()
    139
    140 -def TermProgress_nocb(dfProgress, pszMessage=None, pData=None):
    141      """TermProgress_nocb(double dfProgress, char const * pszMessage=None, void * pData=None) -> int"""
    142      return _gdal_array.TermProgress_nocb(dfProgress, pszMessage, pData)
    143  TermProgress = _gdal_array.TermProgress
    144
    145 -def OpenNumPyArray(psArray, binterleave):
    146      """OpenNumPyArray(PyArrayObject * psArray, bool binterleave) -> Dataset"""
    147      return _gdal_array.OpenNumPyArray(psArray, binterleave)
    148
    149 -def OpenMultiDimensionalNumPyArray(psArray):
    150      """OpenMultiDimensionalNumPyArray(PyArrayObject * psArray) -> Dataset"""
    151      return _gdal_array.OpenMultiDimensionalNumPyArray(psArray)
    152
    153 -def GetArrayFilename(psArray):
    154      """GetArrayFilename(PyArrayObject * psArray) -> retStringAndCPLFree *"""
    155      return _gdal_array.GetArrayFilename(psArray)
    156
    157 -def BandRasterIONumPy(band, bWrite, xoff, yoff, xsize, ysize, psArray, buf_type, resample_alg, callback=0, callback_data=None):
    158      """BandRasterIONumPy(Band band, int bWrite, double xoff, double yoff, double xsize, double ysize, PyArrayObject * psArray, GDALDataType buf_type, GDALRIOResampleAlg resample_alg, GDALProgressFunc callback=0, void * callback_data=None) -> CPLErr"""
    159      return _gdal_array.BandRasterIONumPy(band, bWrite, xoff, yoff, xsize, ysize, psArray, buf_type, resample_alg, callback, callback_data)
    160
    161 -def DatasetIONumPy(ds, bWrite, xoff, yoff, xsize, ysize, psArray, buf_type, resample_alg, callback=0, callback_data=None, binterleave=True, band_list=0):
    162      """DatasetIONumPy(Dataset ds, int bWrite, double xoff, double yoff, double xsize, double ysize, PyArrayObject * psArray, GDALDataType buf_type, GDALRIOResampleAlg resample_alg, GDALProgressFunc callback=0, void * callback_data=None, bool binterleave=True, int band_list=0) -> CPLErr"""
    163      return _gdal_array.DatasetIONumPy(ds, bWrite, xoff, yoff, xsize, ysize, psArray, buf_type, resample_alg, callback, callback_data, binterleave, band_list)
    164
    165 -def MDArrayIONumPy(bWrite, mdarray, psArray, nDims1, nDims3, buffer_datatype):
    166      """MDArrayIONumPy(bool bWrite, GDALMDArrayHS * mdarray, PyArrayObject * psArray, int nDims1, int nDims3, GDALExtendedDataTypeHS * buffer_datatype) -> CPLErr"""
    167      return _gdal_array.MDArrayIONumPy(bWrite, mdarray, psArray, nDims1, nDims3, buffer_datatype)
    168
    169 -def VirtualMemGetArray(virtualmem):
    170      """VirtualMemGetArray(VirtualMem virtualmem)"""
    171      return _gdal_array.VirtualMemGetArray(virtualmem)
    172
    173 -def RATValuesIONumPyWrite(poRAT, nField, nStart, psArray):
    174      """RATValuesIONumPyWrite(RasterAttributeTable poRAT, int nField, int nStart, PyArrayObject * psArray) -> CPLErr"""
    175      return _gdal_array.RATValuesIONumPyWrite(poRAT, nField, nStart, psArray)
    176
    177 -def RATValuesIONumPyRead(poRAT, nField, nStart, nLength):
    178      """RATValuesIONumPyRead(RasterAttributeTable poRAT, int nField, int nStart, int nLength) -> PyObject *"""
    179      return _gdal_array.RATValuesIONumPyRead(poRAT, nField, nStart, nLength)
    180
    181  import numpy
    182
    183  from osgeo import gdalconst
    184  from osgeo import gdal
    185  gdal.AllRegister()
    186
    187  codes = {gdalconst.GDT_Byte: numpy.uint8,
    188           gdalconst.GDT_UInt16: numpy.uint16,
    189           gdalconst.GDT_Int16: numpy.int16,
    190           gdalconst.GDT_UInt32: numpy.uint32,
    191           gdalconst.GDT_Int32: numpy.int32,
    192           gdalconst.GDT_UInt64: numpy.uint64,
    193           gdalconst.GDT_Int64: numpy.int64,
    194           gdalconst.GDT_Float32: numpy.float32,
    195           gdalconst.GDT_Float64: numpy.float64,
    196           gdalconst.GDT_CInt16: numpy.complex64,
    197           gdalconst.GDT_CInt32: numpy.complex64,
    198           gdalconst.GDT_CFloat32:  numpy.complex64,
    199           gdalconst.GDT_CFloat64: numpy.complex128}
    200
    201
    202 -def OpenArray(array, prototype_ds=None, interleave='band'):
    203
    204      interleave = interleave.lower()
    205      if interleave == 'band':
    206          interleave = True
    207      elif interleave == 'pixel':
    208          interleave = False
    209      else:
    210          raise ValueError('Interleave should be band or pixel')
    211
    212      ds = OpenNumPyArray(array, interleave)
    213
    214      if ds is not None and prototype_ds is not None:
    215          if type(prototype_ds).__name__ == 'str':
    216              prototype_ds = gdal.Open(prototype_ds)
    217          if prototype_ds is not None:
    218              CopyDatasetInfo(prototype_ds, ds)
    219
    220      return ds
    221
    222
    223 -def flip_code(code):
    224      if isinstance(code, (numpy.dtype, type)):
    225  # since several things map to complex64 we must carefully select
    226  # the opposite that is an exact match (ticket 1518)
    227          if code == numpy.int8:
    228              return gdalconst.GDT_Byte
    229          if code == numpy.complex64:
    230              return gdalconst.GDT_CFloat32
    231
    232          for key, value in codes.items():
    233              if value == code:
    234                  return key
    235          return None
    236      else:
    237          try:
    238              return codes[code]
    239          except KeyError:
    240              return None
    241
    242 -def NumericTypeCodeToGDALTypeCode(numeric_type):
    243      if not isinstance(numeric_type, (numpy.dtype, type)):
    244          raise TypeError("Input must be a type")
    245      return flip_code(numeric_type)
    246
    247 -def GDALTypeCodeToNumericTypeCode(gdal_code):
    248      return flip_code(gdal_code)
    249
    250 -def _RaiseException():
    251      if gdal.GetUseExceptions():
    252          _StoreLastException()
    253          raise RuntimeError(gdal.GetLastErrorMsg())
    254
    255 -def LoadFile(filename, xoff=0, yoff=0, xsize=None, ysize=None,
    256               buf_xsize=None, buf_ysize=None, buf_type=None,
    257               resample_alg=gdal.GRIORA_NearestNeighbour,
    258               callback=None, callback_data=None, interleave='band',
    259               band_list=None):
    260      ds = gdal.Open(filename)
    261      if ds is None:
    262          raise ValueError("Can't open "+filename+"\n\n"+gdal.GetLastErrorMsg())
    263
    264      return DatasetReadAsArray(ds, xoff, yoff, xsize, ysize,
    265                                buf_xsize=buf_xsize, buf_ysize=buf_ysize, buf_type=buf_type,
    266                                resample_alg=resample_alg,
    267                                callback=callback, callback_data=callback_data,
    268                                interleave=interleave,
    269                                band_list=band_list)
    270
    271 -def SaveArray(src_array, filename, format="GTiff", prototype=None, interleave='band'):
    272      driver = gdal.GetDriverByName(format)
    273      if driver is None:
    274          raise ValueError("Can't find driver "+format)
    275
    276      return driver.CreateCopy(filename, OpenArray(src_array, prototype, interleave))
    277
    278
    279 -def DatasetReadAsArray(ds, xoff=0, yoff=0, win_xsize=None, win_ysize=None, buf_obj=None,
    280                         buf_xsize=None, buf_ysize=None, buf_type=None,
    281                         resample_alg=gdal.GRIORA_NearestNeighbour,
    282                         callback=None, callback_data=None, interleave='band',
    283                         band_list=None):
    284      """Pure python implementation of reading a chunk of a GDAL file
    285      into a numpy array.  Used by the gdal.Dataset.ReadAsArray method."""
    286
    287      if win_xsize is None:
    288          win_xsize = ds.RasterXSize
    289      if win_ysize is None:
    290          win_ysize = ds.RasterYSize
    291
    292      if band_list is None:
    293          band_list = list(range(1, ds.RasterCount + 1))
    294
    295      interleave = interleave.lower()
    296      if interleave == 'band':
    297          interleave = True
    298          xdim = 2
    299          ydim = 1
    300          banddim = 0
    301      elif interleave == 'pixel':
    302          interleave = False
    303          xdim = 1
    304          ydim = 0
    305          banddim = 2
    306      else:
    307          raise ValueError('Interleave should be band or pixel')
    308
    309      nbands = len(band_list)
    310      if nbands == 0:
    311          return None
    312
    313      if nbands == 1:
    314          return BandReadAsArray(ds.GetRasterBand(band_list[0]), xoff, yoff, win_xsize, win_ysize,
    315                                 buf_xsize=buf_xsize, buf_ysize=buf_ysize, buf_type=buf_type,
    316                                 buf_obj=buf_obj,
    317                                 resample_alg=resample_alg,
    318                                 callback=callback,
    319                                 callback_data=callback_data)
    320
    321      if buf_obj is None:
    322          if buf_xsize is None:
    323              buf_xsize = win_xsize
    324          if buf_ysize is None:
    325              buf_ysize = win_ysize
    326          if buf_type is None:
    327              buf_type = ds.GetRasterBand(band_list[0]).DataType
    328              for idx in range(1, nbands):
    329                  band_index = band_list[idx]
    330                  if buf_type != ds.GetRasterBand(band_index).DataType:
    331                      buf_type = gdalconst.GDT_Float32
    332
    333          typecode = GDALTypeCodeToNumericTypeCode(buf_type)
    334          if typecode is None:
    335              buf_type = gdalconst.GDT_Float32
    336              typecode = numpy.float32
    337          else:
    338              buf_type = NumericTypeCodeToGDALTypeCode(typecode)
    339
    340          if buf_type == gdalconst.GDT_Byte and ds.GetRasterBand(1).GetMetadataItem('PIXELTYPE', 'IMAGE_STRUCTURE') == 'SIGNEDBYTE':
    341              typecode = numpy.int8
    342          buf_shape = (nbands, buf_ysize, buf_xsize) if interleave else (buf_ysize, buf_xsize, nbands)
    343          buf_obj = numpy.empty(buf_shape, dtype=typecode)
    344
    345      else:
    346          if len(buf_obj.shape) != 3:
    347              raise ValueError('Array should have 3 dimensions')
    348
    349          shape_buf_xsize = buf_obj.shape[xdim]
    350          shape_buf_ysize = buf_obj.shape[ydim]
    351          if buf_xsize is not None and buf_xsize != shape_buf_xsize:
    352              raise ValueError('Specified buf_xsize not consistent with array shape')
    353          if buf_ysize is not None and buf_ysize != shape_buf_ysize:
    354              raise ValueError('Specified buf_ysize not consistent with array shape')
    355          if buf_obj.shape[banddim] != nbands:
    356              raise ValueError('Dimension %d of array should have size %d to store bands)' % (banddim, nbands))
    357
    358          datatype = NumericTypeCodeToGDALTypeCode(buf_obj.dtype.type)
    359          if not datatype:
    360              raise ValueError("array does not have corresponding GDAL data type")
    361          if buf_type is not None and buf_type != datatype:
    362              raise ValueError("Specified buf_type not consistent with array type")
    363          buf_type = datatype
    364
    365      if DatasetIONumPy(ds, 0, xoff, yoff, win_xsize, win_ysize,
    366                        buf_obj, buf_type, resample_alg, callback, callback_data,
    367                        interleave, band_list) != 0:
    368          _RaiseException()
    369          return None
    370
    371      return buf_obj
    372
    373
    374 -def DatasetWriteArray(ds, array, xoff=0, yoff=0,
    375                        band_list=None,
    376                        interleave='band',
    377                        resample_alg=gdal.GRIORA_NearestNeighbour,
    378                        callback=None, callback_data=None):
    379      """Pure python implementation of writing a chunk of a GDAL file
    380      from a numpy array.  Used by the gdal.Dataset.WriteArray method."""
    381
    382      if band_list is None:
    383          band_list = list(range(1, ds.RasterCount + 1))
    384
    385      interleave = interleave.lower()
    386      if interleave == 'band':
    387          interleave = True
    388          xdim = 2
    389          ydim = 1
    390          banddim = 0
    391      elif interleave == 'pixel':
    392          interleave = False
    393          xdim = 1
    394          ydim = 0
    395          banddim = 2
    396      else:
    397          raise ValueError('Interleave should be band or pixel')
    398
    399      if len(band_list) == 1:
    400          if array is None or (len(array.shape) != 2 and len(array.shape) != 3):
    401              raise ValueError("expected array of dim 2 or 3")
    402          if len(array.shape) == 3:
    403              if array.shape[banddim] != 1:
    404                  raise ValueError("expected size of dimension %d should be 1" % banddim)
    405              array = array[banddim]
    406
    407          return BandWriteArray(ds.GetRasterBand(band_list[0]),
    408                                array,
    409                                xoff=xoff, yoff=yoff, resample_alg=resample_alg,
    410                                callback=callback, callback_data=callback_data)
    411
    412      if array is None or len(array.shape) != 3:
    413          raise ValueError("expected array of dim 3")
    414
    415      xsize = array.shape[xdim]
    416      ysize = array.shape[ydim]
    417
    418      if xsize + xoff > ds.RasterXSize or ysize + yoff > ds.RasterYSize:
    419          raise ValueError("array larger than output file, or offset off edge")
    420      if array.shape[banddim] != len(band_list):
    421          raise ValueError('Dimension %d of array should have size %d to store bands)' % (banddim, len(band_list)))
    422
    423      datatype = NumericTypeCodeToGDALTypeCode(array.dtype.type)
    424
    425  # if we receive some odd type, like int64, try casting to a very
    426  # generic type we do support (#2285)
    427      if not datatype:
    428          gdal.Debug('gdal_array', 'force array to float64')
    429          array = array.astype(numpy.float64)
    430          datatype = NumericTypeCodeToGDALTypeCode(array.dtype.type)
    431
    432      if not datatype:
    433          raise ValueError("array does not have corresponding GDAL data type")
    434
    435      ret = DatasetIONumPy(ds, 1, xoff, yoff, xsize, ysize,
    436                           array, datatype, resample_alg, callback, callback_data,
    437                           interleave, band_list)
    438      if ret != 0:
    439          _RaiseException()
    440      return ret
    441
    442
    443 -def BandReadAsArray(band, xoff=0, yoff=0, win_xsize=None, win_ysize=None,
    444                      buf_xsize=None, buf_ysize=None, buf_type=None, buf_obj=None,
    445                      resample_alg=gdal.GRIORA_NearestNeighbour,
    446                      callback=None, callback_data=None):
    447      """Pure python implementation of reading a chunk of a GDAL file
    448      into a numpy array.  Used by the gdal.Band.ReadAsArray method."""
    449
    450      if win_xsize is None:
    451          win_xsize = band.XSize
    452      if win_ysize is None:
    453          win_ysize = band.YSize
    454
    455      if buf_obj is None:
    456          if buf_xsize is None:
    457              buf_xsize = win_xsize
    458          if buf_ysize is None:
    459              buf_ysize = win_ysize
    460          if buf_type is None:
    461              buf_type = band.DataType
    462
    463          typecode = GDALTypeCodeToNumericTypeCode(buf_type)
    464          if typecode is None:
    465              buf_type = gdalconst.GDT_Float32
    466              typecode = numpy.float32
    467          else:
    468              buf_type = NumericTypeCodeToGDALTypeCode(typecode)
    469
    470          if buf_type == gdalconst.GDT_Byte and band.GetMetadataItem('PIXELTYPE', 'IMAGE_STRUCTURE') == 'SIGNEDBYTE':
    471              typecode = numpy.int8
    472          buf_obj = numpy.empty([buf_ysize, buf_xsize], dtype=typecode)
    473
    474      else:
    475          if len(buf_obj.shape) not in (2, 3):
    476              raise ValueError("expected array of dimension 2 or 3")
    477
    478          if len(buf_obj.shape) == 2:
    479              shape_buf_xsize = buf_obj.shape[1]
    480              shape_buf_ysize = buf_obj.shape[0]
    481          else:
    482              if buf_obj.shape[0] != 1:
    483                  raise ValueError("expected size of first dimension should be 0")
    484              shape_buf_xsize = buf_obj.shape[2]
    485              shape_buf_ysize = buf_obj.shape[1]
    486          if buf_xsize is not None and buf_xsize != shape_buf_xsize:
    487              raise ValueError('Specified buf_xsize not consistent with array shape')
    488          if buf_ysize is not None and buf_ysize != shape_buf_ysize:
    489              raise ValueError('Specified buf_ysize not consistent with array shape')
    490
    491          datatype = NumericTypeCodeToGDALTypeCode(buf_obj.dtype.type)
    492          if not datatype:
    493              raise ValueError("array does not have corresponding GDAL data type")
    494          if buf_type is not None and buf_type != datatype:
    495              raise ValueError("Specified buf_type not consistent with array type")
    496          buf_type = datatype
    497
    498      if BandRasterIONumPy(band, 0, xoff, yoff, win_xsize, win_ysize,
    499                           buf_obj, buf_type, resample_alg, callback, callback_data) != 0:
    500          _RaiseException()
    501          return None
    502
    503      return buf_obj
    504
    505 -def BandWriteArray(band, array, xoff=0, yoff=0,
    506                     resample_alg=gdal.GRIORA_NearestNeighbour,
    507                     callback=None, callback_data=None):
    508      """Pure python implementation of writing a chunk of a GDAL file
    509      from a numpy array.  Used by the gdal.Band.WriteArray method."""
    510
    511      if array is None or len(array.shape) != 2:
    512          raise ValueError("expected array of dim 2")
    513
    514      xsize = array.shape[1]
    515      ysize = array.shape[0]
    516
    517      if xsize + xoff > band.XSize or ysize + yoff > band.YSize:
    518          raise ValueError("array larger than output file, or offset off edge")
    519
    520      datatype = NumericTypeCodeToGDALTypeCode(array.dtype.type)
    521
    522  # if we receive some odd type, like int64, try casting to a very
    523  # generic type we do support (#2285)
    524      if not datatype:
    525          gdal.Debug('gdal_array', 'force array to float64')
    526          array = array.astype(numpy.float64)
    527          datatype = NumericTypeCodeToGDALTypeCode(array.dtype.type)
    528
    529      if not datatype:
    530          raise ValueError("array does not have corresponding GDAL data type")
    531
    532      ret = BandRasterIONumPy(band, 1, xoff, yoff, xsize, ysize,
    533                               array, datatype, resample_alg, callback, callback_data)
    534      if ret != 0:
    535          _RaiseException()
    536      return ret
    537
    538 -def _ExtendedDataTypeToNumPyDataType(dt):
    539      klass = dt.GetClass()
    540
    541      if klass == gdal.GEDTC_STRING:
    542          return numpy.bytes_, dt
    543
    544      if klass == gdal.GEDTC_NUMERIC:
    545          buf_type = dt.GetNumericDataType()
    546          typecode = GDALTypeCodeToNumericTypeCode(buf_type)
    547          if typecode is None:
    548              typecode = numpy.float32
    549              dt = gdal.ExtendedDataType.Create(gdal.GDT_Float32)
    550          else:
    551              dt = gdal.ExtendedDataType.Create(NumericTypeCodeToGDALTypeCode(typecode))
    552          return typecode, dt
    553
    554      assert klass == gdal.GEDTC_COMPOUND
    555      names = []
    556      formats = []
    557      offsets = []
    558      for comp in dt.GetComponents():
    559          names.append(comp.GetName())
    560          typecode, subdt = _ExtendedDataTypeToNumPyDataType(comp.GetType())
    561          if subdt != comp.GetType():
    562              raise Exception("Incompatible datatype")
    563          formats.append(typecode)
    564          offsets.append(comp.GetOffset())
    565
    566      return numpy.dtype({'names': names,
    567                          'formats': formats,
    568                          'offsets': offsets,
    569                          'itemsize': dt.GetSize()}), dt
    570
    571 -def ExtendedDataTypeToNumPyDataType(dt):
    572      typecode, _ = _ExtendedDataTypeToNumPyDataType(dt)
    573      return typecode
    574
    575 -def MDArrayReadAsArray(mdarray,
    576                          array_start_idx = None,
    577                          count = None,
    578                          array_step = None,
    579                          buffer_datatype = None,
    580                          buf_obj = None):
    581      if not array_start_idx:
    582          array_start_idx = [0] * mdarray.GetDimensionCount()
    583      if not count:
    584          count = [ dim.GetSize() for dim in mdarray.GetDimensions() ]
    585      if not array_step:
    586          array_step = [1] * mdarray.GetDimensionCount()
    587
    588      if buf_obj is None:
    589          if not buffer_datatype:
    590              buffer_datatype = mdarray.GetDataType()
    591          typecode, buffer_datatype = _ExtendedDataTypeToNumPyDataType(buffer_datatype)
    592          buf_obj = numpy.empty(count, dtype=typecode)
    593      else:
    594          datatype = NumericTypeCodeToGDALTypeCode(buf_obj.dtype.type)
    595          if not datatype:
    596              raise ValueError("array does not have corresponding GDAL data type")
    597
    598          buffer_datatype = gdal.ExtendedDataType.Create(datatype)
    599
    600      ret = MDArrayIONumPy(False, mdarray, buf_obj, array_start_idx, array_step, buffer_datatype)
    601      if ret != 0:
    602          _RaiseException()
    603      return buf_obj
    604
    605 -def MDArrayWriteArray(mdarray, array,
    606                          array_start_idx = None,
    607                          array_step = None):
    608      if not array_start_idx:
    609          array_start_idx = [0] * mdarray.GetDimensionCount()
    610      if not array_step:
    611          array_step = [1] * mdarray.GetDimensionCount()
    612
    613      buffer_datatype = mdarray.GetDataType()
    614      typecode = ExtendedDataTypeToNumPyDataType(buffer_datatype)
    615      if array.dtype != typecode:
    616          datatype = NumericTypeCodeToGDALTypeCode(array.dtype.type)
    617
    618  # if we receive some odd type, like int64, try casting to a very
    619  # generic type we do support (#2285)
    620          if not datatype:
    621              gdal.Debug('gdal_array', 'force array to float64')
    622              array = array.astype(numpy.float64)
    623              datatype = NumericTypeCodeToGDALTypeCode(array.dtype.type)
    624
    625          if not datatype:
    626              raise ValueError("array does not have corresponding GDAL data type")
    627
    628          buffer_datatype = gdal.ExtendedDataType.Create(datatype)
    629
    630      ret = MDArrayIONumPy(True, mdarray, array, array_start_idx, array_step, buffer_datatype)
    631      if ret != 0:
    632          _RaiseException()
    633      return ret
    634
    635 -def RATWriteArray(rat, array, field, start=0):
    636      """
    637      Pure Python implementation of writing a chunk of the RAT
    638      from a numpy array. Type of array is coerced to one of the types
    639      (int, double, string) supported. Called from RasterAttributeTable.WriteArray
    640      """
    641      if array is None:
    642          raise ValueError("Expected array of dim 1")
    643
    644  # if not the array type convert it to handle lists etc
    645      if not isinstance(array, numpy.ndarray):
    646          array = numpy.array(array)
    647
    648      if array.ndim != 1:
    649          raise ValueError("Expected array of dim 1")
    650
    651      if (start + array.size) > rat.GetRowCount():
    652          raise ValueError("Array too big to fit into RAT from start position")
    653
    654      if numpy.issubdtype(array.dtype, numpy.integer):
    655  # is some type of integer - coerce to standard int
    656  # TODO: must check this is fine on all platforms
    657  # confusingly numpy.int 64 bit even if native type 32 bit
    658          array = array.astype(numpy.int32)
    659      elif numpy.issubdtype(array.dtype, numpy.floating):
    660  # is some type of floating point - coerce to double
    661          array = array.astype(numpy.double)
    662      elif numpy.issubdtype(array.dtype, numpy.character):
    663  # cast away any kind of Unicode etc
    664          array = array.astype(bytes)
    665      else:
    666          raise ValueError("Array not of a supported type (integer, double or string)")
    667
    668      ret = RATValuesIONumPyWrite(rat, field, start, array)
    669      if ret != 0:
    670          _RaiseException()
    671      return ret
    672
    673 -def RATReadArray(rat, field, start=0, length=None):
    674      """
    675      Pure Python implementation of reading a chunk of the RAT
    676      into a numpy array. Called from RasterAttributeTable.ReadAsArray
    677      """
    678      if length is None:
    679          length = rat.GetRowCount() - start
    680
    681      ret = RATValuesIONumPyRead(rat, field, start, length)
    682      if ret is None:
    683          _RaiseException()
    684      return ret
    685
    686 -def CopyDatasetInfo(src, dst, xoff=0, yoff=0):
    687      """
    688      Copy georeferencing information and metadata from one dataset to another.
    689      src: input dataset
    690      dst: output dataset - It can be a ROI -
    691      xoff, yoff:  dst's offset with respect to src in pixel/line.
    692
    693      Notes: Destination dataset must have update access.  Certain formats
    694             do not support creation of geotransforms and/or gcps.
    695
    696      """
    697
    698      dst.SetMetadata(src.GetMetadata())
    699
    700
    701
    702  #Check for geo transform
    703      gt = src.GetGeoTransform()
    704      if gt != (0, 1, 0, 0, 0, 1):
    705          dst.SetProjection(src.GetProjectionRef())
    706
    707          if xoff == 0 and yoff == 0:
    708              dst.SetGeoTransform(gt)
    709          else:
    710              ngt = [gt[0], gt[1], gt[2], gt[3], gt[4], gt[5]]
    711              ngt[0] = gt[0] + xoff*gt[1] + yoff*gt[2]
    712              ngt[3] = gt[3] + xoff*gt[4] + yoff*gt[5]
    713              dst.SetGeoTransform((ngt[0], ngt[1], ngt[2], ngt[3], ngt[4], ngt[5]))
    714
    715  #Check for GCPs
    716      elif src.GetGCPCount() > 0:
    717
    718          if (xoff == 0) and (yoff == 0):
    719              dst.SetGCPs(src.GetGCPs(), src.GetGCPProjection())
    720          else:
    721              gcps = src.GetGCPs()
    722  #Shift gcps
    723              new_gcps = []
    724              for gcp in gcps:
    725                  ngcp = gdal.GCP()
    726                  ngcp.GCPX = gcp.GCPX
    727                  ngcp.GCPY = gcp.GCPY
    728                  ngcp.GCPZ = gcp.GCPZ
    729                  ngcp.GCPPixel = gcp.GCPPixel - xoff
    730                  ngcp.GCPLine = gcp.GCPLine - yoff
    731                  ngcp.Info = gcp.Info
    732                  ngcp.Id = gcp.Id
    733                  new_gcps.append(ngcp)
    734
    735              try:
    736                  dst.SetGCPs(new_gcps, src.GetGCPProjection())
    737              except:
    738                  print("Failed to set GCPs")
    739                  return
    740
    741      return
    742
    743  # This file is compatible with both classic and new-style classes.
    744