wolfhece 2.2.38__py3-none-any.whl → 2.2.39__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- wolfhece/Coordinates_operations.py +5 -0
- wolfhece/GraphNotebook.py +72 -1
- wolfhece/GraphProfile.py +1 -1
- wolfhece/MulticriteriAnalysis.py +1579 -0
- wolfhece/PandasGrid.py +62 -1
- wolfhece/PyCrosssections.py +194 -43
- wolfhece/PyDraw.py +891 -73
- wolfhece/PyGui.py +913 -72
- wolfhece/PyGuiHydrology.py +528 -74
- wolfhece/PyPalette.py +26 -4
- wolfhece/PyParams.py +33 -0
- wolfhece/PyPictures.py +2 -2
- wolfhece/PyVertex.py +25 -0
- wolfhece/PyVertexvectors.py +94 -28
- wolfhece/PyWMS.py +52 -36
- wolfhece/acceptability/acceptability.py +15 -8
- wolfhece/acceptability/acceptability_gui.py +507 -360
- wolfhece/acceptability/func.py +80 -183
- wolfhece/apps/version.py +1 -1
- wolfhece/compare_series.py +480 -0
- wolfhece/drawing_obj.py +12 -1
- wolfhece/hydrology/Catchment.py +228 -162
- wolfhece/hydrology/Internal_variables.py +43 -2
- wolfhece/hydrology/Models_characteristics.py +69 -67
- wolfhece/hydrology/Optimisation.py +893 -182
- wolfhece/hydrology/PyWatershed.py +267 -165
- wolfhece/hydrology/SubBasin.py +185 -140
- wolfhece/hydrology/cst_exchanges.py +76 -1
- wolfhece/hydrology/forcedexchanges.py +413 -49
- wolfhece/hydrology/read.py +65 -5
- wolfhece/hydrometry/kiwis.py +14 -7
- wolfhece/insyde_be/INBE_func.py +746 -0
- wolfhece/insyde_be/INBE_gui.py +1776 -0
- wolfhece/insyde_be/__init__.py +3 -0
- wolfhece/interpolating_raster.py +366 -0
- wolfhece/irm_alaro.py +1457 -0
- wolfhece/irm_qdf.py +889 -57
- wolfhece/lifewatch.py +6 -3
- wolfhece/picc.py +124 -8
- wolfhece/pyLandUseFlanders.py +146 -0
- wolfhece/pydownloader.py +2 -1
- wolfhece/pywalous.py +225 -31
- wolfhece/toolshydrology_dll.py +149 -0
- wolfhece/wolf_array.py +63 -25
- {wolfhece-2.2.38.dist-info → wolfhece-2.2.39.dist-info}/METADATA +3 -1
- {wolfhece-2.2.38.dist-info → wolfhece-2.2.39.dist-info}/RECORD +49 -40
- {wolfhece-2.2.38.dist-info → wolfhece-2.2.39.dist-info}/WHEEL +0 -0
- {wolfhece-2.2.38.dist-info → wolfhece-2.2.39.dist-info}/entry_points.txt +0 -0
- {wolfhece-2.2.38.dist-info → wolfhece-2.2.39.dist-info}/top_level.txt +0 -0
@@ -25,6 +25,7 @@ from ..wolf_array import *
|
|
25
25
|
from ..PyCrosssections import crosssections as CrossSections
|
26
26
|
from ..GraphNotebook import PlotNotebook
|
27
27
|
from .read import *
|
28
|
+
from ..PyParams import Wolf_Param
|
28
29
|
|
29
30
|
LISTDEM=['dem_before_corr','dem_after_corr','dem_10m','dem_20m','crosssection']
|
30
31
|
#LISTDEM=['dem_after_corr']
|
@@ -607,17 +608,21 @@ class RiverSystem:
|
|
607
608
|
|
608
609
|
#recherche de l'index max --> à l'exutoire
|
609
610
|
self.maxlevels = self.parent.outlet.reachlevel
|
610
|
-
self.maxstrahler=0
|
611
|
-
self.reaches['indexed']={}
|
612
|
-
for i in range(1,self.maxlevels+1):
|
613
|
-
self.reaches['indexed'][i]=[]
|
614
611
|
|
615
|
-
|
616
|
-
|
617
|
-
|
618
|
-
|
619
|
-
|
620
|
-
self.
|
612
|
+
if self.maxlevels == 0:
|
613
|
+
logging.warning(_("No reaches found in the watershed. Please check the model configuration and the outlet's position."))
|
614
|
+
else:
|
615
|
+
self.maxstrahler=0
|
616
|
+
self.reaches['indexed']={}
|
617
|
+
for i in range(1,self.maxlevels+1):
|
618
|
+
self.reaches['indexed'][i]=[]
|
619
|
+
|
620
|
+
#création de listes pour chaque niveau
|
621
|
+
for curreach in self.reaches['reaches']:
|
622
|
+
curdict=self.reaches['reaches'][curreach]
|
623
|
+
listreach=curdict['baselist']
|
624
|
+
curlevel=listreach[0].reachlevel
|
625
|
+
self.reaches['indexed'][curlevel].append(curreach)
|
621
626
|
|
622
627
|
#création de listes pour chaque amont
|
623
628
|
# on parcourt toutes les mailles depuis chaque amont et on ajoute les index de biefs qui sont différents
|
@@ -632,57 +637,58 @@ class RiverSystem:
|
|
632
637
|
curdict['fromuptodown'].append(curnode.reach)
|
633
638
|
curnode=curnode.down
|
634
639
|
|
635
|
-
|
636
|
-
|
637
|
-
|
638
|
-
|
639
|
-
|
640
|
-
self.
|
641
|
-
|
642
|
-
|
643
|
-
|
644
|
-
|
645
|
-
|
646
|
-
|
647
|
-
|
648
|
-
|
649
|
-
|
650
|
-
|
651
|
-
|
652
|
-
|
653
|
-
|
654
|
-
|
655
|
-
|
656
|
-
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
664
|
-
|
665
|
-
|
666
|
-
|
667
|
-
|
668
|
-
|
669
|
-
|
670
|
-
|
671
|
-
|
672
|
-
|
673
|
-
|
674
|
-
|
675
|
-
|
676
|
-
|
677
|
-
|
678
|
-
|
679
|
-
|
680
|
-
|
681
|
-
|
682
|
-
|
683
|
-
|
684
|
-
|
685
|
-
|
640
|
+
if self.maxlevels > 0:
|
641
|
+
#création de l'indice de Strahler
|
642
|
+
self.reaches['strahler']={}
|
643
|
+
#on commence par ajouter les biefs de 1er niveau qui sont à coup sûr d'indice 1
|
644
|
+
self.reaches['strahler'][1]=self.reaches['indexed'][1]
|
645
|
+
for curreach in self.reaches['strahler'][1]:
|
646
|
+
self.set_strahler_in_nodes(curreach,1)
|
647
|
+
|
648
|
+
#on parcourt les différents niveaux
|
649
|
+
for i in range(2,self.maxlevels+1):
|
650
|
+
listlevel=self.reaches['indexed'][i]
|
651
|
+
for curreach in listlevel:
|
652
|
+
curup:Node_Watershed
|
653
|
+
curup=self.reaches['reaches'][curreach]['upstream']
|
654
|
+
upidx=list(x.strahler for x in curup.upriver)
|
655
|
+
sameidx=upidx[0]==upidx[-1]
|
656
|
+
maxidx=max(upidx)
|
657
|
+
|
658
|
+
curidx=maxidx
|
659
|
+
if sameidx:
|
660
|
+
curidx+=1
|
661
|
+
if not curidx in self.reaches['strahler'].keys():
|
662
|
+
#création de la liste du niveau supérieur
|
663
|
+
self.reaches['strahler'][curidx]=[]
|
664
|
+
self.maxstrahler=curidx
|
665
|
+
|
666
|
+
self.reaches['strahler'][curidx].append(curreach)
|
667
|
+
self.set_strahler_in_nodes(curreach,curidx)
|
668
|
+
|
669
|
+
|
670
|
+
myarray=WolfArray(mold=self.parent.subs_array)
|
671
|
+
myarray.reset()
|
672
|
+
curnode:Node_Watershed
|
673
|
+
for curreach in self.reaches['reaches']:
|
674
|
+
curdict=self.reaches['reaches'][curreach]
|
675
|
+
listreach=curdict['baselist']
|
676
|
+
for curnode in listreach:
|
677
|
+
i=curnode.i
|
678
|
+
j=curnode.j
|
679
|
+
myarray.array[i,j]=curnode.strahler
|
680
|
+
myarray.filename = self.parent.directory+'\\Characteristic_maps\\Drainage_basin.strahler'
|
681
|
+
myarray.write_all()
|
682
|
+
myarray.reset()
|
683
|
+
for curreach in self.reaches['reaches']:
|
684
|
+
curdict=self.reaches['reaches'][curreach]
|
685
|
+
listreach=curdict['baselist']
|
686
|
+
for curnode in listreach:
|
687
|
+
i=curnode.i
|
688
|
+
j=curnode.j
|
689
|
+
myarray.array[i,j]=curnode.reachlevel
|
690
|
+
myarray.filename = self.parent.directory+'\\Characteristic_maps\\Drainage_basin.reachlevel'
|
691
|
+
myarray.write_all()
|
686
692
|
|
687
693
|
def set_strahler_in_nodes(self, whichreach:int, strahler:int):
|
688
694
|
"""
|
@@ -862,7 +868,7 @@ class RiverSystem:
|
|
862
868
|
"""
|
863
869
|
#Uniquement les pentes rivières
|
864
870
|
for curlist in LISTDEM:
|
865
|
-
slopes= WolfArray(self.parent.
|
871
|
+
slopes= WolfArray(self.parent.directory+'\\Characteristic_maps\\Drainage_basin.slope')
|
866
872
|
slopes.reset()
|
867
873
|
for curreach in self.reaches['reaches']:
|
868
874
|
curdict=self.reaches['reaches'][curreach]
|
@@ -872,7 +878,7 @@ class RiverSystem:
|
|
872
878
|
ijval = np.asarray([[curnode.i, curnode.j, curnode.slopecorr[curlist]['value']] for curnode in listreach])
|
873
879
|
slopes.array[np.int32(ijval[:,0]),np.int32(ijval[:,1])]=ijval[:,2]
|
874
880
|
|
875
|
-
slopes.filename = self.parent.
|
881
|
+
slopes.filename = self.parent.directory+'\\Characteristic_maps\\Drainage_basin.slope_corr_riv_'+curlist
|
876
882
|
slopes.write_all()
|
877
883
|
|
878
884
|
def slope_correctionmin(self):
|
@@ -1224,7 +1230,7 @@ class RunoffSystem:
|
|
1224
1230
|
def write_slopes(self):
|
1225
1231
|
#Uniquement les pentes runoff
|
1226
1232
|
for curlist in LISTDEM:
|
1227
|
-
slopes= WolfArray(self.parent.
|
1233
|
+
slopes= WolfArray(self.parent.directory+'\\Characteristic_maps\\Drainage_basin.slope')
|
1228
1234
|
slopes.reset()
|
1229
1235
|
curnode:Node_Watershed
|
1230
1236
|
for curnode in self.nodes:
|
@@ -1232,7 +1238,7 @@ class RunoffSystem:
|
|
1232
1238
|
j=curnode.j
|
1233
1239
|
slopes.array[i,j]=curnode.slopecorr[curlist]['value']
|
1234
1240
|
|
1235
|
-
slopes.filename = self.parent.
|
1241
|
+
slopes.filename = self.parent.directory+'\\Characteristic_maps\\Drainage_basin.slope_corr_run_'+curlist
|
1236
1242
|
slopes.write_all()
|
1237
1243
|
|
1238
1244
|
def slope_correctionmin(self):
|
@@ -1638,12 +1644,13 @@ class SubWatershed:
|
|
1638
1644
|
|
1639
1645
|
# rivers are sorted by dem value, so the first one is the outlet
|
1640
1646
|
return self.get_list_nodes_river(reach)[0]
|
1647
|
+
|
1641
1648
|
class Watershed:
|
1642
1649
|
"""Classe bassin versant"""
|
1643
1650
|
|
1644
1651
|
header:header_wolf # header_wolf of "Drainage_basin.sub" wolf_array
|
1645
1652
|
|
1646
|
-
|
1653
|
+
directory: str # Répertoire de modélisation
|
1647
1654
|
|
1648
1655
|
outlet:Node_Watershed # exutoire
|
1649
1656
|
|
@@ -1669,7 +1676,7 @@ class Watershed:
|
|
1669
1676
|
to_update_times:bool # switch to detect if the time matrix should be updated
|
1670
1677
|
|
1671
1678
|
def __init__(self,
|
1672
|
-
|
1679
|
+
directory:str,
|
1673
1680
|
thzmin:float=None,
|
1674
1681
|
thslopemin:float=None,
|
1675
1682
|
thzmax:float=None,
|
@@ -1682,19 +1689,37 @@ class Watershed:
|
|
1682
1689
|
dir_mnt_subpixels:str=None,
|
1683
1690
|
*args, **kwargs):
|
1684
1691
|
|
1692
|
+
self.rivers = []
|
1693
|
+
self.runoff = []
|
1694
|
+
self.nodes = []
|
1695
|
+
self.subcatchments = []
|
1696
|
+
self.statisticss = {}
|
1697
|
+
self.header = None
|
1698
|
+
self.couplednodesij = []
|
1699
|
+
self.couplednodesxy = []
|
1700
|
+
self.couplednodes = []
|
1701
|
+
|
1685
1702
|
self.virtualcatchments = []
|
1686
1703
|
|
1687
1704
|
logging.info(_('Read files...'))
|
1688
1705
|
|
1689
|
-
self.
|
1690
|
-
self.dir_mnt_subpixels = dir_mnt_subpixels if dir_mnt_subpixels is not None else self.
|
1706
|
+
self.directory = os.path.normpath(directory)
|
1707
|
+
self.dir_mnt_subpixels = dir_mnt_subpixels if dir_mnt_subpixels is not None else self.directory
|
1691
1708
|
|
1692
|
-
self.subs_array = WolfArray(self.
|
1709
|
+
self.subs_array = WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.sub')
|
1693
1710
|
|
1694
|
-
self.header = self.
|
1711
|
+
self.header = header_wolf.read_header((self.directory+'\\Characteristic_maps\\Drainage_basin.b'))
|
1695
1712
|
|
1696
|
-
|
1697
|
-
|
1713
|
+
if self.subs_array.nbx == 0 or self.subs_array.nby == 0:
|
1714
|
+
logging.error(_('The Watershed sub file is empty or not valid.'))
|
1715
|
+
return
|
1716
|
+
|
1717
|
+
# Use params to get the directory and filename of forced exchanges
|
1718
|
+
_mainparams = Wolf_Param(filename = os.path.join(self.directory, "Main_model.param"), init_GUI= False, toShow= False)
|
1719
|
+
dir_fe = _mainparams[('Forced Exchanges', 'Directory')]
|
1720
|
+
fn_fe = _mainparams[('Forced Exchanges', 'Filename')]
|
1721
|
+
|
1722
|
+
isOk, fe_file = check_path(os.path.join(self.directory, dir_fe, fn_fe), prefix=self.directory)
|
1698
1723
|
self.couplednodesxy=[]
|
1699
1724
|
self.couplednodesij=[]
|
1700
1725
|
|
@@ -1703,15 +1728,19 @@ class Watershed:
|
|
1703
1728
|
lines = f.read().splitlines()
|
1704
1729
|
f.close()
|
1705
1730
|
|
1706
|
-
if lines
|
1707
|
-
|
1708
|
-
|
1709
|
-
|
1710
|
-
|
1711
|
-
|
1712
|
-
|
1713
|
-
|
1714
|
-
|
1731
|
+
if len(lines) > 1:
|
1732
|
+
|
1733
|
+
if lines[0]=='COORDINATES':
|
1734
|
+
for xy in enumerate(lines[1:]):
|
1735
|
+
xy_split = xy[1].split('\t')
|
1736
|
+
if len(xy_split)==4:
|
1737
|
+
xup,yup,xdown,ydown=xy_split
|
1738
|
+
else:
|
1739
|
+
xup,yup,xdown,ydown=xy_split[:4]
|
1740
|
+
self.couplednodesxy.append([float(xup),float(yup),float(xdown),float(ydown)])
|
1741
|
+
self.couplednodesij.append([self.subs_array.get_ij_from_xy(float(xup),float(yup)),self.subs_array.get_ij_from_xy(float(xdown),float(ydown))])
|
1742
|
+
else:
|
1743
|
+
logging.warning(_('Unknown format in Coupled_pairs.txt'))
|
1715
1744
|
|
1716
1745
|
logging.info(_('Initialization of nodes...'))
|
1717
1746
|
self.nodesindex = np.zeros([self.subs_array.nbx,self.subs_array.nby], dtype=int)
|
@@ -1753,6 +1782,13 @@ class Watershed:
|
|
1753
1782
|
|
1754
1783
|
@property
|
1755
1784
|
def nb_subs(self):
|
1785
|
+
""" Nombre de sous-bassins """
|
1786
|
+
|
1787
|
+
if self.subs_array is None:
|
1788
|
+
return 0
|
1789
|
+
if self.subs_array.array is None:
|
1790
|
+
return 0
|
1791
|
+
|
1756
1792
|
return int(ma.max(self.subs_array.array))
|
1757
1793
|
|
1758
1794
|
@property
|
@@ -1891,6 +1927,24 @@ class Watershed:
|
|
1891
1927
|
vect.find_minmax()
|
1892
1928
|
return vect
|
1893
1929
|
|
1930
|
+
def get_vector_from_xy_to_outlet(self,
|
1931
|
+
x:float,
|
1932
|
+
y:float) -> vector:
|
1933
|
+
|
1934
|
+
down_to_outlet = self.get_node_from_xy(x, y)
|
1935
|
+
|
1936
|
+
if down_to_outlet is None:
|
1937
|
+
logging.error(_('No node found at coordinates ({}, {})').format(x, y))
|
1938
|
+
return None
|
1939
|
+
|
1940
|
+
vec_to_outlet = vector(name='Vector from ({}, {}) to outlet'.format(down_to_outlet.i, down_to_outlet.j))
|
1941
|
+
|
1942
|
+
while down_to_outlet is not None:
|
1943
|
+
vec_to_outlet.add_vertex(wolfvertex(down_to_outlet.x, down_to_outlet.y, down_to_outlet.dem['dem_after_corr']))
|
1944
|
+
down_to_outlet = down_to_outlet.down
|
1945
|
+
|
1946
|
+
return vec_to_outlet
|
1947
|
+
|
1894
1948
|
def get_subwatershed(self, idx_sorted_or_name:int | str) -> SubWatershed:
|
1895
1949
|
"""
|
1896
1950
|
Récupération d'un sous-bassin sur base de l'index trié
|
@@ -1920,7 +1974,7 @@ class Watershed:
|
|
1920
1974
|
|
1921
1975
|
return None
|
1922
1976
|
|
1923
|
-
def get_node_from_ij(self, i:int,j:int):
|
1977
|
+
def get_node_from_ij(self, i:int,j:int) -> Node_Watershed:
|
1924
1978
|
"""
|
1925
1979
|
Récupération d'un objet Node_Watershed sur base des indices (i,j)
|
1926
1980
|
"""
|
@@ -1935,7 +1989,7 @@ class Watershed:
|
|
1935
1989
|
|
1936
1990
|
return self.nodes[idx]
|
1937
1991
|
|
1938
|
-
def get_node_from_xy(self, x:float, y:float):
|
1992
|
+
def get_node_from_xy(self, x:float, y:float) -> Node_Watershed:
|
1939
1993
|
"""
|
1940
1994
|
Récupération d'un objet Node_Watershed sur base des coordonnées (x,y)
|
1941
1995
|
"""
|
@@ -1947,9 +2001,9 @@ class Watershed:
|
|
1947
2001
|
Ecriture sur disque
|
1948
2002
|
"""
|
1949
2003
|
for curlist in LISTDEM:
|
1950
|
-
curpath=self.
|
2004
|
+
curpath=self.directory+'\\Characteristic_maps\\corrslopes\\'+curlist
|
1951
2005
|
os.makedirs(curpath,exist_ok=True)
|
1952
|
-
slopes= WolfArray(self.
|
2006
|
+
slopes= WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.slope')
|
1953
2007
|
|
1954
2008
|
ijval = np.asarray([[curnode.i, curnode.j, curnode.slopecorr[curlist]['value']] for curnode in self.nodes])
|
1955
2009
|
slopes.array[np.int32(ijval[:,0]),np.int32(ijval[:,1])]=ijval[:,2]
|
@@ -1962,9 +2016,9 @@ class Watershed:
|
|
1962
2016
|
Ecriture sur disque
|
1963
2017
|
"""
|
1964
2018
|
for curlist in LISTDEM:
|
1965
|
-
curpath=self.
|
2019
|
+
curpath=self.directory+'\\Characteristic_maps\\corrdem\\'+curlist
|
1966
2020
|
os.makedirs(curpath,exist_ok=True)
|
1967
|
-
dem= WolfArray(self.
|
2021
|
+
dem= WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basincorr.b')
|
1968
2022
|
|
1969
2023
|
ijval = np.asarray([[curnode.i, curnode.j, curnode.demcorr[curlist]['value']] for curnode in self.nodes])
|
1970
2024
|
dem.array[np.int32(ijval[:,0]),np.int32(ijval[:,1])]=ijval[:,2]
|
@@ -2012,10 +2066,10 @@ class Watershed:
|
|
2012
2066
|
|
2013
2067
|
self.nodes=[Node_Watershed() for i in range(self.subs_array.nbnotnull)]
|
2014
2068
|
|
2015
|
-
dem_before_corr= WolfArray(self.
|
2016
|
-
dem_after_corr= WolfArray(self.
|
2069
|
+
dem_before_corr= WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.b')
|
2070
|
+
dem_after_corr= WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basincorr.b')
|
2017
2071
|
#Tests of the existance of the delta dem
|
2018
|
-
isOk,demdeltaFile = check_path(os.path.join(self.
|
2072
|
+
isOk,demdeltaFile = check_path(os.path.join(self.directory,'Characteristic_maps\\Drainage_basindiff.b'))
|
2019
2073
|
if isOk<0:
|
2020
2074
|
logging.error("The ...dif.b file is not present! Please check the reason or launch again the hydrological preprocessing! A Null diff matrix will then be considered for the next steps.")
|
2021
2075
|
demdelta = WolfArray(mold=dem_after_corr)
|
@@ -2023,76 +2077,102 @@ class Watershed:
|
|
2023
2077
|
else:
|
2024
2078
|
demdelta = WolfArray(demdeltaFile)
|
2025
2079
|
#
|
2026
|
-
|
2027
|
-
|
2028
|
-
|
2029
|
-
|
2080
|
+
if (Path(self.directory) / 'Characteristic_maps' /'Drainage_basin.slope').exists():
|
2081
|
+
# If the slope file exists, read it
|
2082
|
+
slopes = WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.slope', masknull=False)
|
2083
|
+
else:
|
2084
|
+
slopes = None
|
2085
|
+
logging.error(_('The slope file is not present! Please check the reason or launch again the hydrological preprocessing! A Null slope matrix will then be considered for the next steps.'))
|
2086
|
+
|
2087
|
+
if (Path(self.directory) / 'Characteristic_maps' /'Drainage_basin.reachs').exists():
|
2088
|
+
# If the reaches file exists, read it
|
2089
|
+
reaches = WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.reachs')
|
2090
|
+
else:
|
2091
|
+
reaches = None
|
2092
|
+
logging.error(_('The reaches file is not present! Please check the reason or launch again the hydrological preprocessing! A Null reaches matrix will then be considered for the next steps.'))
|
2093
|
+
|
2094
|
+
if (Path(self.directory) / 'Characteristic_maps' /'Drainage_basin.cnv').exists():
|
2095
|
+
# If the cnv file exists, read it
|
2096
|
+
cnv = WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.cnv')
|
2097
|
+
else:
|
2098
|
+
cnv = None
|
2099
|
+
logging.error(_('The cnv file is not present! Please check the reason or launch again the hydrological preprocessing! A Null cnv matrix will then be considered for the next steps.'))
|
2030
2100
|
|
2101
|
+
if (Path(self.directory) / 'Characteristic_maps' /'Drainage_basin.time').exists():
|
2102
|
+
# If the time file exists, read it
|
2103
|
+
times = WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.time')
|
2104
|
+
else:
|
2105
|
+
times = None
|
2106
|
+
logging.error(_('The time file is not present! Please check the reason or launch again the hydrological preprocessing! A Null time matrix will then be considered for the next steps.'))
|
2031
2107
|
|
2032
2108
|
dem_after_corr.array.mask = self.subs_array.array.mask
|
2033
2109
|
|
2034
|
-
|
2035
|
-
|
2036
|
-
|
2037
|
-
|
2038
|
-
j=int(index[1])
|
2039
|
-
self.nodesindex[i,j]=nb
|
2040
|
-
nb+=1
|
2110
|
+
# Efficiently fill nodesindex using numpy where and flat indexing
|
2111
|
+
indices = np.argwhere(self.subs_array.array > 0)
|
2112
|
+
position = np.arange(len(indices))
|
2113
|
+
self.nodesindex[indices[:, 0], indices[:, 1]] = position
|
2041
2114
|
|
2042
|
-
|
2043
|
-
|
2044
|
-
|
2045
|
-
|
2046
|
-
|
2047
|
-
|
2048
|
-
|
2049
|
-
|
2050
|
-
|
2051
|
-
|
2052
|
-
|
2053
|
-
|
2054
|
-
|
2055
|
-
|
2056
|
-
|
2057
|
-
|
2058
|
-
|
2059
|
-
|
2060
|
-
|
2061
|
-
|
2062
|
-
|
2063
|
-
|
2064
|
-
|
2065
|
-
|
2066
|
-
|
2067
|
-
|
2068
|
-
curnode.slopecorr={}
|
2069
|
-
|
2070
|
-
|
2071
|
-
|
2072
|
-
|
2073
|
-
|
2074
|
-
curnode.demcorr={}
|
2075
|
-
|
2076
|
-
|
2077
|
-
|
2078
|
-
|
2079
|
-
|
2080
|
-
|
2081
|
-
|
2082
|
-
|
2115
|
+
def init_node(i, j):
|
2116
|
+
""" Initialisation d'un noeud
|
2117
|
+
"""
|
2118
|
+
curnode:Node_Watershed
|
2119
|
+
x, y = self.header.get_xy_from_ij(i,j)
|
2120
|
+
curnode =self.nodes[self.nodesindex[i,j]]
|
2121
|
+
|
2122
|
+
curnode.i = i
|
2123
|
+
curnode.j = j
|
2124
|
+
|
2125
|
+
curnode.x = x
|
2126
|
+
curnode.y = y
|
2127
|
+
|
2128
|
+
curnode.crosssections = None
|
2129
|
+
curnode.down = None
|
2130
|
+
|
2131
|
+
curnode.index=self.nodesindex[i,j]
|
2132
|
+
curnode.dem={}
|
2133
|
+
curnode.dem['dem_before_corr']=dem_before_corr.array[i,j]
|
2134
|
+
curnode.dem['dem_after_corr']=dem_after_corr.array[i,j]
|
2135
|
+
curnode.dem['crosssection']=99999.
|
2136
|
+
curnode.demdelta=demdelta.array[i,j]
|
2137
|
+
curnode.slope=slopes.array[i,j] if slopes is not None else 0.0
|
2138
|
+
|
2139
|
+
curnode.slopecorr={}
|
2140
|
+
for curlist in LISTDEM:
|
2141
|
+
curnode.slopecorr[curlist]={}
|
2142
|
+
curnode.slopecorr[curlist]['parts']=[]
|
2143
|
+
curnode.slopecorr[curlist]['value']=curnode.slope
|
2144
|
+
|
2145
|
+
curnode.demcorr={}
|
2146
|
+
for curlist in LISTDEM:
|
2147
|
+
curnode.demcorr[curlist]={}
|
2148
|
+
curnode.demcorr[curlist]['parts']=[]
|
2149
|
+
curnode.demcorr[curlist]['value']=curnode.dem['dem_after_corr']
|
2150
|
+
|
2151
|
+
curnode.sub=int(self.subs_array.array[i,j])
|
2152
|
+
curnode.time=times.array[i,j] if times is not None else 0.0
|
2153
|
+
curnode.uparea=cnv.array[i,j] if cnv is not None else 0.0
|
2154
|
+
|
2155
|
+
if reaches is not None:
|
2083
2156
|
curnode.river=not reaches.array.mask[i,j]
|
2084
2157
|
if curnode.river:
|
2085
2158
|
curnode.reach=int(reaches.array[i,j])
|
2086
|
-
|
2087
|
-
curnode.
|
2088
|
-
curnode.
|
2089
|
-
|
2090
|
-
|
2091
|
-
|
2159
|
+
else:
|
2160
|
+
curnode.river=False
|
2161
|
+
curnode.reach=0
|
2162
|
+
|
2163
|
+
curnode.forced=False
|
2164
|
+
|
2165
|
+
curnode.up=[]
|
2166
|
+
curnode.upriver=[]
|
2167
|
+
curnode.strahler=0
|
2168
|
+
curnode.reachlevel=0
|
2169
|
+
# nb+=1
|
2170
|
+
|
2171
|
+
all_init = list(map(lambda p: init_node(*p), tqdm(indices, 'Initialization')))
|
2092
2172
|
|
2093
2173
|
curdown:Node_Watershed
|
2094
2174
|
#Liaison échanges forcés
|
2095
|
-
incr=
|
2175
|
+
incr=self.header.dx
|
2096
2176
|
for curexch in self.couplednodesij:
|
2097
2177
|
i=int(curexch[0][0])
|
2098
2178
|
j=int(curexch[0][1])
|
@@ -2135,27 +2215,49 @@ class Watershed:
|
|
2135
2215
|
curdown.upriver.append(curnode)
|
2136
2216
|
curnode.incrs=incr
|
2137
2217
|
else:
|
2138
|
-
self.outlet
|
2218
|
+
if self.outlet is None:
|
2219
|
+
self.outlet = curnode
|
2139
2220
|
|
2140
|
-
#
|
2141
|
-
|
2221
|
+
# Recherche de la pente dans les voisins en croix dans la topo non remaniée
|
2222
|
+
import concurrent.futures
|
2223
|
+
|
2224
|
+
def compute_sloped8(args):
|
2225
|
+
curnode, dem_before_corr, resolution = args
|
2142
2226
|
if not curnode.forced:
|
2143
|
-
i=curnode.i
|
2144
|
-
j=curnode.j
|
2227
|
+
i = curnode.i
|
2228
|
+
j = curnode.j
|
2145
2229
|
|
2146
2230
|
curtop = curnode.dem['dem_before_corr']
|
2147
2231
|
|
2148
|
-
neigh = [
|
2149
|
-
|
2232
|
+
neigh = [
|
2233
|
+
[i-1, j], [i+1, j], [i, j-1], [i, j+1],
|
2234
|
+
[i-1, j-1], [i+1, j+1], [i+1, j-1], [i-1, j+1]
|
2235
|
+
]
|
2236
|
+
diff = [
|
2237
|
+
dem_before_corr.array[curi, curj] - curtop
|
2238
|
+
if not dem_before_corr.array.mask[curi, curj] else 100000.
|
2239
|
+
for curi, curj in neigh
|
2240
|
+
]
|
2150
2241
|
mindiff = np.min(diff)
|
2151
2242
|
|
2152
|
-
fact=1.
|
2153
|
-
if mindiff<0:
|
2243
|
+
fact = 1.
|
2244
|
+
if mindiff < 0:
|
2154
2245
|
index = diff.index(mindiff)
|
2155
|
-
if index>3:
|
2156
|
-
fact=np.sqrt(2)
|
2246
|
+
if index > 3:
|
2247
|
+
fact = np.sqrt(2)
|
2248
|
+
return curnode, -mindiff / (resolution * fact)
|
2249
|
+
else:
|
2250
|
+
return curnode, 0.0
|
2251
|
+
|
2252
|
+
# Prepare arguments for multiprocessing
|
2253
|
+
args_list = [(curnode, dem_before_corr, self.resolution) for curnode in self.nodes]
|
2254
|
+
|
2255
|
+
with concurrent.futures.ProcessPoolExecutor() as executor:
|
2256
|
+
results = list(tqdm(executor.map(compute_sloped8, args_list), total=len(args_list), desc='Finding slope'))
|
2157
2257
|
|
2158
|
-
|
2258
|
+
# Assign results back to nodes
|
2259
|
+
for curnode, sloped8 in results:
|
2260
|
+
curnode.sloped8 = sloped8
|
2159
2261
|
|
2160
2262
|
self.rivers=list(filter(lambda x: x.river,self.nodes))
|
2161
2263
|
self.rivers.sort(key=lambda x: x.dem['dem_after_corr'])
|
@@ -2293,7 +2395,7 @@ class Watershed:
|
|
2293
2395
|
demsubs = {}
|
2294
2396
|
|
2295
2397
|
file_10m = os.path.join(self.dir_mnt_subpixels,'mnt10m.bin')
|
2296
|
-
isOk, file_10m = check_path(file_10m, prefix=self.
|
2398
|
+
isOk, file_10m = check_path(file_10m, prefix=self.directory)
|
2297
2399
|
if isOk>=0:
|
2298
2400
|
dem_10m=WolfArray(file_10m)
|
2299
2401
|
demsubs["dem_10m"] = dem_10m
|
@@ -2301,7 +2403,7 @@ class Watershed:
|
|
2301
2403
|
logging.warning(_('No 10m DEM found'))
|
2302
2404
|
|
2303
2405
|
file_20m = os.path.join(self.dir_mnt_subpixels,'mnt20m.bin')
|
2304
|
-
isOk, file_20m = check_path(file_20m, prefix=self.
|
2406
|
+
isOk, file_20m = check_path(file_20m, prefix=self.directory)
|
2305
2407
|
if isOk>=0:
|
2306
2408
|
dem_20m=WolfArray(file_20m)
|
2307
2409
|
demsubs["dem_20m"] = dem_20m
|
@@ -2637,7 +2739,7 @@ class Watershed:
|
|
2637
2739
|
def update_times(self, wolf_time=None):
|
2638
2740
|
|
2639
2741
|
if wolf_time is None:
|
2640
|
-
wolf_time = WolfArray(self.
|
2742
|
+
wolf_time = WolfArray(self.directory+'\\Characteristic_maps\\Drainage_basin.time')
|
2641
2743
|
|
2642
2744
|
for cur_node in self.nodes:
|
2643
2745
|
cur_node.time = wolf_time[cur_node.i, cur_node.j]
|