| 1 | #!/usr/bin/env python
|
|---|
| 2 | ################################################################################
|
|---|
| 3 | #
|
|---|
| 4 | # MODULE: r.hypso.py
|
|---|
| 5 | #
|
|---|
| 6 | # AUTHOR(S): Margherita Di Leo, Massimo Di Stefano, Francesco Di Stefano
|
|---|
| 7 | #
|
|---|
| 8 | #
|
|---|
| 9 | # PURPOSE: Output a hypsometric and hypsographic graph
|
|---|
| 10 | #
|
|---|
| 11 | # COPYRIGHT: (c) 2010 Margherita Di Leo, Massimo Di Stefano, Francesco Di Stefano
|
|---|
| 12 | #
|
|---|
| 13 | # This program is free software under the GNU General Public
|
|---|
| 14 | # License (>=v2). Read the file COPYING that comes with GRASS
|
|---|
| 15 | # for details.
|
|---|
| 16 | #
|
|---|
| 17 | # REQUIRES: Matplotlib
|
|---|
| 18 | # http://matplotlib.sourceforge.net/
|
|---|
| 19 | #
|
|---|
| 20 | #
|
|---|
| 21 | ################################################################################
|
|---|
| 22 | #%module
|
|---|
| 23 | #% description: Outputs a hypsometric and hypsographic graph.
|
|---|
| 24 | #% keyword: raster
|
|---|
| 25 | #%end
|
|---|
| 26 |
|
|---|
| 27 | #%option G_OPT_R_ELEV
|
|---|
| 28 | #% key: map
|
|---|
| 29 | #% required: yes
|
|---|
| 30 | #%end
|
|---|
| 31 |
|
|---|
| 32 | #%option G_OPT_F_OUTPUT
|
|---|
| 33 | #% key: image
|
|---|
| 34 | #% key_desc: image
|
|---|
| 35 | #% description: Name for output graph file (png)
|
|---|
| 36 | #% required: yes
|
|---|
| 37 | #%end
|
|---|
| 38 |
|
|---|
| 39 | #%flag
|
|---|
| 40 | #% key: a
|
|---|
| 41 | #% description: Generate hypsometric curve
|
|---|
| 42 | #%end
|
|---|
| 43 |
|
|---|
| 44 | #%flag
|
|---|
| 45 | #% key: b
|
|---|
| 46 | #% description: Generate hypsographic curve
|
|---|
| 47 | #%end
|
|---|
| 48 |
|
|---|
| 49 | import sys
|
|---|
| 50 | import os
|
|---|
| 51 | import matplotlib #required by windows
|
|---|
| 52 | matplotlib.use('wx') #required by windows
|
|---|
| 53 | import matplotlib.pyplot as plt
|
|---|
| 54 | import grass.script as grass
|
|---|
| 55 | import numpy as np
|
|---|
| 56 | from operator import itemgetter
|
|---|
| 57 |
|
|---|
| 58 | def main():
|
|---|
| 59 | stats = grass.read_command('r.stats', input = options['map'], sep = 'space', nv = '*', nsteps = '255', flags = 'inc').split('\n')[:-1]
|
|---|
| 60 | res = grass.region()['nsres']
|
|---|
| 61 | zn = np.zeros((len(stats),6),float)
|
|---|
| 62 | kl = np.zeros((len(stats),2),float)
|
|---|
| 63 | prc = np.zeros((9,2),float)
|
|---|
| 64 |
|
|---|
| 65 | for i in range(len(stats)):
|
|---|
| 66 | if i == 0:
|
|---|
| 67 | zn[i,0], zn[i, 1] = list(map(float, stats[i].split(' ')))
|
|---|
| 68 | zn[i,2] = zn[i,1]
|
|---|
| 69 | else:
|
|---|
| 70 | zn[i,0], zn[i, 1] = list(map(float, stats[i].split(' ')))
|
|---|
| 71 | zn[i,2] = zn[i,1] + zn[i-1,2]
|
|---|
| 72 |
|
|---|
| 73 | totcell = sum(zn[:,1])
|
|---|
| 74 | print("Tot. cells", totcell)
|
|---|
| 75 |
|
|---|
| 76 | for i in range(len(stats)):
|
|---|
| 77 | zn[i,3] = 1 - (zn[i,2] / sum(zn[:,1]))
|
|---|
| 78 | zn[i,4] = zn[i,3] * (((res**2)/1000000)*sum(zn[:,1]))
|
|---|
| 79 | zn[i,5] = ((zn[i,0] - min(zn[:,0])) / (max(zn[:,0]) - min(zn[:,0])) )
|
|---|
| 80 | kl[i,0] = zn[i,0]
|
|---|
| 81 | kl[i,1] = 1 - (zn[i,2] / totcell)
|
|---|
| 82 |
|
|---|
| 83 | # quantiles
|
|---|
| 84 | prc[0,0] , prc[0,1] = findint(kl,0.025) , 0.025
|
|---|
| 85 | prc[1,0] , prc[1,1] = findint(kl,0.05) , 0.05
|
|---|
| 86 | prc[2,0] , prc[2,1] = findint(kl,0.1) , 0.1
|
|---|
| 87 | prc[3,0] , prc[3,1] = findint(kl,0.25) , 0.25
|
|---|
| 88 | prc[4,0] , prc[4,1] = findint(kl,0.5) , 0.5
|
|---|
| 89 | prc[5,0] , prc[5,1] = findint(kl,0.75) , 0.75
|
|---|
| 90 | prc[6,0] , prc[6,1] = findint(kl,0.9) , 0.9
|
|---|
| 91 | prc[7,0] , prc[7,1] = findint(kl,0.95) , 0.95
|
|---|
| 92 | prc[8,0] , prc[8,1] = findint(kl,0.975) , 0.975
|
|---|
| 93 |
|
|---|
| 94 | # Managing flag & plot
|
|---|
| 95 | if flags['a']:
|
|---|
| 96 | plotImage(zn[:,3], zn[:,5],options['image']+'_Hypsometric.png','-','A(i) / A','Z(i) / Zmax','Hypsometric Curve')
|
|---|
| 97 | if flags['b']:
|
|---|
| 98 | plotImage(zn[:,4], zn[:,0],options['image']+'_Hypsographic.png','-','A [km^2]','Z [m.slm]','Hypsographic Curve')
|
|---|
| 99 |
|
|---|
| 100 | print("===========================")
|
|---|
| 101 | print("Hypsometric | quantiles")
|
|---|
| 102 | print("===========================")
|
|---|
| 103 | print('%.0f' %findint(kl,0.025) , "|", 0.025)
|
|---|
| 104 | print('%.0f' %findint(kl,0.05) , "|", 0.05)
|
|---|
| 105 | print('%.0f' %findint(kl,0.1) , "|", 0.1)
|
|---|
| 106 | print('%.0f' %findint(kl,0.25) , "|", 0.25)
|
|---|
| 107 | print('%.0f' %findint(kl,0.5) , "|", 0.5)
|
|---|
| 108 | print('%.0f' %findint(kl,0.75) , "|", 0.75)
|
|---|
| 109 | print('%.0f' %findint(kl,0.9) , "|", 0.9)
|
|---|
| 110 | print('%.0f' %findint(kl,0.975) , "|", 0.975)
|
|---|
| 111 | print('\n')
|
|---|
| 112 | print('Done!')
|
|---|
| 113 | #print prc
|
|---|
| 114 |
|
|---|
| 115 |
|
|---|
| 116 | def findint(kl,f):
|
|---|
| 117 | Xf = np.abs(kl-f)
|
|---|
| 118 | Xf = np.where(Xf==Xf.min())
|
|---|
| 119 | item = itemgetter(0)(Xf)
|
|---|
| 120 | Xf = item[0] # added this further step to handle the case the function has 2 min
|
|---|
| 121 | z1 = kl[Xf][0]
|
|---|
| 122 | z2 = kl[Xf-1][0]
|
|---|
| 123 | f1 = kl[Xf][1]
|
|---|
| 124 | f2 = kl[Xf-1][1]
|
|---|
| 125 | z = z1 + ((z2 - z1) / (f2 - f1)) * (f - f1)
|
|---|
| 126 | return z
|
|---|
| 127 |
|
|---|
| 128 | def plotImage(x,y,image,type,xlabel,ylabel,title):
|
|---|
| 129 | plt.plot(x, y, type)
|
|---|
| 130 | plt.ylabel(ylabel)
|
|---|
| 131 | plt.xlabel(xlabel)
|
|---|
| 132 | plt.xlim( min(x), max(x) )
|
|---|
| 133 | plt.ylim( min(y), max(y) )
|
|---|
| 134 | plt.title(title)
|
|---|
| 135 | plt.grid(True)
|
|---|
| 136 | plt.savefig(image)
|
|---|
| 137 | plt.close('all')
|
|---|
| 138 |
|
|---|
| 139 | if __name__ == "__main__":
|
|---|
| 140 | options, flags = grass.parser()
|
|---|
| 141 | sys.exit(main())
|
|---|