Advertisement
Guest User

Untitled

a guest
Aug 25th, 2016
77
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 4.25 KB | None | 0 0
  1. import gdal, ogr, osr, numpy
  2. import sys
  3.  
  4.  
  5. def zonal_stats(feat, input_zone_polygon, input_value_raster):
  6.  
  7. # Open data
  8. raster = gdal.Open(input_value_raster)
  9. shp = ogr.Open(input_zone_polygon)
  10. lyr = shp.GetLayer()
  11.  
  12. # Get raster georeference info
  13. transform = raster.GetGeoTransform()
  14. xOrigin = transform[0]
  15. yOrigin = transform[3]
  16. pixelWidth = transform[1]
  17. pixelHeight = transform[5]
  18.  
  19. # Reproject vector geometry to same projection as raster
  20. sourceSR = lyr.GetSpatialRef()
  21. targetSR = osr.SpatialReference()
  22. targetSR.ImportFromWkt(raster.GetProjectionRef())
  23. coordTrans = osr.CoordinateTransformation(sourceSR,targetSR)
  24. feat = lyr.GetNextFeature()
  25. geom = feat.GetGeometryRef()
  26. geom.Transform(coordTrans)
  27.  
  28. # Get extent of feat
  29. geom = feat.GetGeometryRef()
  30. if (geom.GetGeometryName() == 'MULTIPOLYGON'):
  31. count = 0
  32. pointsX = []; pointsY = []
  33. for polygon in geom:
  34. geomInner = geom.GetGeometryRef(count)
  35. ring = geomInner.GetGeometryRef(0)
  36. numpoints = ring.GetPointCount()
  37. for p in range(numpoints):
  38. lon, lat, z = ring.GetPoint(p)
  39. pointsX.append(lon)
  40. pointsY.append(lat)
  41. count += 1
  42. elif (geom.GetGeometryName() == 'POLYGON'):
  43. ring = geom.GetGeometryRef(0)
  44. numpoints = ring.GetPointCount()
  45. pointsX = []; pointsY = []
  46. for p in range(numpoints):
  47. lon, lat, z = ring.GetPoint(p)
  48. pointsX.append(lon)
  49. pointsY.append(lat)
  50.  
  51. else:
  52. sys.exit("ERROR: Geometry needs to be either Polygon or Multipolygon")
  53.  
  54. xmin = min(pointsX)
  55. xmax = max(pointsX)
  56. ymin = min(pointsY)
  57. ymax = max(pointsY)
  58.  
  59. # Specify offset and rows and columns to read
  60. xoff = int((xmin - xOrigin)/pixelWidth)
  61. yoff = int((yOrigin - ymax)/pixelWidth)
  62. xcount = int((xmax - xmin)/pixelWidth)+1
  63. ycount = int((ymax - ymin)/pixelWidth)+1
  64.  
  65. # Create memory target raster
  66. target_ds = gdal.GetDriverByName('MEM').Create('', xcount, ycount, 1, gdal.GDT_Byte)
  67. target_ds.SetGeoTransform((
  68. xmin, pixelWidth, 0,
  69. ymax, 0, pixelHeight,
  70. ))
  71.  
  72. # Create for target raster the same projection as for the value raster
  73. raster_srs = osr.SpatialReference()
  74. raster_srs.ImportFromWkt(raster.GetProjectionRef())
  75. target_ds.SetProjection(raster_srs.ExportToWkt())
  76.  
  77. # Rasterize zone polygon to raster
  78. gdal.RasterizeLayer(target_ds, [1], lyr, burn_values=[1])
  79.  
  80. # Read raster as arrays
  81. banddataraster = raster.GetRasterBand(1)
  82. dataraster = banddataraster.ReadAsArray(xoff, yoff, xcount, ycount).astype(numpy.float)
  83.  
  84. bandmask = target_ds.GetRasterBand(1)
  85. datamask = bandmask.ReadAsArray(0, 0, xcount, ycount).astype(numpy.float)
  86.  
  87. # Mask zone of raster
  88. zoneraster = numpy.ma.masked_array(dataraster, numpy.logical_not(datamask))
  89.  
  90. # Calculate statistics of zonal raster
  91. return numpy.average(zoneraster),numpy.mean(zoneraster),numpy.median(zoneraster),numpy.std(zoneraster),numpy.var(zoneraster)
  92.  
  93.  
  94. def loop_zonal_stats(input_zone_polygon, input_value_raster):
  95.  
  96. shp = ogr.Open(input_zone_polygon)
  97. lyr = shp.GetLayer()
  98. featList = range(lyr.GetFeatureCount())
  99. statDict = {}
  100.  
  101. for FID in featList:
  102. feat = lyr.GetFeature(FID)
  103. meanValue = zonal_stats(feat, input_zone_polygon, input_value_raster)
  104. statDict[FID] = meanValue
  105. return statDict
  106.  
  107. def main(input_zone_polygon, input_value_raster):
  108. return loop_zonal_stats(input_zone_polygon, input_value_raster)
  109.  
  110.  
  111. if __name__ == "__main__":
  112.  
  113. #
  114. # Returns for each feature a dictionary item (FID) with the statistical values in the following order: Average, Mean, Medain, Standard Deviation, Variance
  115. #
  116. # example run : $ python grid.py <full-path><output-shapefile-name>.shp xmin xmax ymin ymax gridHeight gridWidth
  117. #
  118.  
  119. if len( sys.argv ) != 3:
  120. print "[ ERROR ] you must supply two arguments: input-zone-shapefile-name.shp input-value-raster-name.tif "
  121. sys.exit( 1 )
  122. print 'Returns for each feature a dictionary item (FID) with the statistical values in the following order: Average, Mean, Medain, Standard Deviation, Variance'
  123. print main( sys.argv[1], sys.argv[2] )
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement