Example #1
0
    def flow_length_cell(i, j, ysize, xsize, fdir, cellsize, weight, length,
                         flow_dir_code='TauDEM'):
        """Calculate flow length of cell."""
        celllen = FlowModelConst.get_cell_length(flow_dir_code)
        differ = FlowModelConst.get_cell_shift(flow_dir_code)
        # print(i,j, weight[i][j])
        if i < ysize and j < xsize:
            if length[i][j] == 0:
                if weight[i][j] > 0:
                    prei = i
                    prej = j
                    wt = weight[i][j]
                    fdir_v = fdir[i][j]
                    di = differ[fdir_v][0]
                    dj = differ[fdir_v][1]
                    i = i + di
                    j = j + dj
                    relen = TerrainUtilClass.flow_length_cell(i, j, ysize, xsize, fdir, cellsize,
                                                              weight, length,
                                                              flow_dir_code)
                    # print(i, j, fdir_v)
                    length[prei][prej] = cellsize * celllen[fdir_v] * wt + relen
                    return length[prei][prej]
                else:
                    return 0
            if length[i][j] > 0:
                return length[i][j]

            if length[i][j] < 0:
                print('Error in calculating flowlen_cell function! (%d, %d)' % (i, j))
                return -1
        return 0
Example #2
0
    def flow_length_cell(i, j, ysize, xsize, fdir, cellsize, weight, length,
                         flow_dir_code="TauDEM"):
        """Calculate flow length of cell."""
        celllen = FlowModelConst.get_cell_length(flow_dir_code)
        differ = FlowModelConst.get_cell_shift(flow_dir_code)
        # print(i,j, weight[i][j])
        if i < ysize and j < xsize:
            if length[i][j] == 0:
                if weight[i][j] > 0:
                    prei = i
                    prej = j
                    wt = weight[i][j]
                    fdir_v = fdir[i][j]
                    di = differ[fdir_v][0]
                    dj = differ[fdir_v][1]
                    i = i + di
                    j = j + dj
                    relen = TerrainUtilClass.flow_length_cell(i, j, ysize, xsize, fdir, cellsize,
                                                              weight, length,
                                                              flow_dir_code)
                    # print(i, j, fdir_v)
                    length[prei][prej] = cellsize * celllen[fdir_v] * wt + relen
                    return length[prei][prej]
                else:
                    return 0
            if length[i][j] > 0:
                return length[i][j]

            if length[i][j] < 0:
                print("Error in calculating flowlen_cell function! i,j:")
                print(i, j)
                return -1
        return 0
    def subbasin_statistics(cfg, maindb):
        """
        Import subbasin numbers, outlet ID, etc. to MongoDB.
        """
        streamlink_r = cfg.spatials.stream_link
        flowdir_r = cfg.spatials.d8flow
        direction_items = dict()
        # Flow direction follows ArcGIS rule, which has been converted from TauDEM in
        #    sd_delineation.post_process_of_delineated_data()
        direction_items = FlowModelConst.get_cell_shift('ArcGIS')
        streamlink_d = RasterUtilClass.read_raster(streamlink_r)
        nodata = streamlink_d.noDataValue
        nrows = streamlink_d.nRows
        ncols = streamlink_d.nCols
        streamlink_data = streamlink_d.data
        max_subbasin_id = int(streamlink_d.get_max())
        min_subbasin_id = int(streamlink_d.get_min())
        subbasin_num = len(unique(streamlink_data)) - 1
        # print(max_subbasin_id, min_subbasin_id, subbasin_num)
        flowdir_d = RasterUtilClass.read_raster(flowdir_r)
        flowdir_data = flowdir_d.data
        i_row = -1
        i_col = -1
        for row in range(nrows):
            for col in range(ncols):
                if streamlink_data[row][col] != nodata:
                    i_row = row
                    i_col = col
                    # print(row, col)
                    break
            else:
                continue
            break
        if i_row == -1 or i_col == -1:
            raise ValueError('Stream link data invalid, please check and retry.')

        def flow_down_stream_idx(dir_value, i, j):
            """Return row and col of downstream direction."""
            drow, dcol = direction_items[int(dir_value)]
            return i + drow, j + dcol

        def find_outlet_index(r, c):
            """Find outlet's coordinate"""
            flag = True
            while flag:
                fdir = flowdir_data[r][c]
                newr, newc = flow_down_stream_idx(fdir, r, c)
                if newr < 0 or newc < 0 or newr >= nrows or newc >= ncols \
                        or streamlink_data[newr][newc] == nodata:
                    flag = False
                else:
                    # print(newr, newc, streamlink_data[newr][newc])
                    r = newr
                    c = newc
            return r, c

        o_row, o_col = find_outlet_index(i_row, i_col)
        outlet_bsn_id = int(streamlink_data[o_row][o_col])
        import_stats_dict = {SubbsnStatsName.outlet: outlet_bsn_id,
                             SubbsnStatsName.o_row: o_row,
                             SubbsnStatsName.o_col: o_col,
                             SubbsnStatsName.subbsn_max: max_subbasin_id,
                             SubbsnStatsName.subbsn_min: min_subbasin_id,
                             SubbsnStatsName.subbsn_num: subbasin_num}

        for stat, stat_v in list(import_stats_dict.items()):
            dic = {ModelParamFields.name: stat,
                   ModelParamFields.desc: stat,
                   ModelParamFields.unit: 'NONE',
                   ModelParamFields.module: 'ALL',
                   ModelParamFields.value: stat_v,
                   ModelParamFields.impact: DEFAULT_NODATA,
                   ModelParamFields.change: ModelParamFields.change_nc,
                   ModelParamFields.max: DEFAULT_NODATA,
                   ModelParamFields.min: DEFAULT_NODATA,
                   ModelParamFields.type: 'SUBBASIN'}
            curfilter = {ModelParamFields.name: dic[ModelParamFields.name]}
            # print(dic, curfilter)
            maindb[DBTableNames.main_parameter].find_one_and_replace(curfilter, dic,
                                                                     upsert=True)
        maindb[DBTableNames.main_parameter].create_index(ModelParamFields.name)
    def subbasin_statistics(cfg, maindb):
        """
        Import subbasin numbers, outlet ID, etc. to MongoDB.
        """
        streamlink_r = cfg.spatials.stream_link
        flowdir_r = cfg.spatials.d8flow
        direction_items = dict()
        # Flow direction follows ArcGIS rule, which has been converted from TauDEM in
        #    sd_delineation.post_process_of_delineated_data()
        direction_items = FlowModelConst.get_cell_shift('ArcGIS')
        streamlink_d = RasterUtilClass.read_raster(streamlink_r)
        nodata = streamlink_d.noDataValue
        nrows = streamlink_d.nRows
        ncols = streamlink_d.nCols
        streamlink_data = streamlink_d.data
        max_subbasin_id = int(streamlink_d.get_max())
        min_subbasin_id = int(streamlink_d.get_min())
        subbasin_num = len(unique(streamlink_data)) - 1
        # print(max_subbasin_id, min_subbasin_id, subbasin_num)
        flowdir_d = RasterUtilClass.read_raster(flowdir_r)
        flowdir_data = flowdir_d.data
        i_row = -1
        i_col = -1
        for row in range(nrows):
            for col in range(ncols):
                if streamlink_data[row][col] != nodata:
                    i_row = row
                    i_col = col
                    # print(row, col)
                    break
            else:
                continue
            break
        if i_row == -1 or i_col == -1:
            raise ValueError(
                'Stream link data invalid, please check and retry.')

        def flow_down_stream_idx(dir_value, i, j):
            """Return row and col of downstream direction."""
            drow, dcol = direction_items[int(dir_value)]
            return i + drow, j + dcol

        def find_outlet_index(r, c):
            """Find outlet's coordinate"""
            flag = True
            while flag:
                fdir = flowdir_data[r][c]
                newr, newc = flow_down_stream_idx(fdir, r, c)
                if newr < 0 or newc < 0 or newr >= nrows or newc >= ncols \
                    or streamlink_data[newr][newc] == nodata:
                    flag = False
                else:
                    # print(newr, newc, streamlink_data[newr][newc])
                    r = newr
                    c = newc
            return r, c

        o_row, o_col = find_outlet_index(i_row, i_col)
        outlet_bsn_id = int(streamlink_data[o_row][o_col])
        import_stats_dict = {
            SubbsnStatsName.outlet: outlet_bsn_id,
            SubbsnStatsName.o_row: o_row,
            SubbsnStatsName.o_col: o_col,
            SubbsnStatsName.subbsn_max: max_subbasin_id,
            SubbsnStatsName.subbsn_min: min_subbasin_id,
            SubbsnStatsName.subbsn_num: subbasin_num
        }

        for stat, stat_v in list(import_stats_dict.items()):
            dic = {
                ModelParamFields.name: stat,
                ModelParamFields.desc: stat,
                ModelParamFields.unit: 'NONE',
                ModelParamFields.module: 'ALL',
                ModelParamFields.value: stat_v,
                ModelParamFields.impact: DEFAULT_NODATA,
                ModelParamFields.change: ModelParamFields.change_nc,
                ModelParamFields.max: DEFAULT_NODATA,
                ModelParamFields.min: DEFAULT_NODATA,
                ModelParamFields.type: 'SUBBASIN'
            }
            curfilter = {ModelParamFields.name: dic[ModelParamFields.name]}
            # print(dic, curfilter)
            maindb[DBTableNames.main_parameter].find_one_and_replace(
                curfilter, dic, upsert=True)
        maindb[DBTableNames.main_parameter].create_index(ModelParamFields.name)