Exemplo n.º 1
0
def plot_bfe_row_for_var(finfo_to_season_to_diff=None, ax_list=None, season_titles=False,
                         varname="", basemap_info=None):
    cmap = cm.get_cmap("RdBu_r", 20)

    assert isinstance(basemap_info, BasemapInfo)

    xx, yy = None, None
    cs = None
    for finfo, season_to_diff in finfo_to_season_to_diff.items():
        assert isinstance(finfo, FieldInfo)

        if finfo.varname != varname:
            continue

        for season in season_to_diff:
            season_to_diff[season] = infovar.get_to_plot(varname, season_to_diff[season], difference=True,
                                                         lons=basemap_info.lons, lats=basemap_info.lats)

        clevs = get_diff_levels(season_to_diff, ncolors=cmap.N, varname=varname)
        for i, (season, diff) in enumerate(season_to_diff.items()):
            ax = ax_list[i]

            if xx is None or yy is None:
                xx, yy = basemap_info.get_proj_xy()

            print(diff.shape)




            cs = basemap_info.basemap.contourf(xx, yy, diff[:], cmap=cmap,
                                               levels=clevs,
                                               extend="both", ax=ax)
            basemap_info.basemap.drawcoastlines(ax=ax)
            # ax.set_aspect("auto")
            basemap_info.basemap.readshapefile(BASIN_BOUNDARIES_SHP[:-4], "basin", ax=ax)

            if season_titles:
                ax.set_title(season)

            if i == 0:
                ax.set_ylabel(infovar.get_long_display_label_for_var(finfo.varname))

            if finfo.varname in ["I5", ] and season.lower() in ["summer"]:
                ax.set_visible(False)

    ax = ax_list[-1]
    # ax.set_aspect(30)
    ax.set_title(infovar.get_units(varname))
    plt.colorbar(cs, cax=ax_list[-1])
Exemplo n.º 2
0
def main():
    # Define the simulations to be validated
    r_config = RunConfig(
        data_path=
        "/RESCUE/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r.hdf5",
        start_year=1990,
        end_year=2010,
        label="CRCM5-L1")
    r_config_list = [r_config]

    r_config = RunConfig(
        data_path=
        "/RESCUE/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r.hdf5",
        start_year=1990,
        end_year=2010,
        label="CRCM5-NL")
    r_config_list.append(r_config)

    bmp_info = analysis.get_basemap_info_from_hdf(file_path=r_config.data_path)
    bmp_info.should_draw_grey_map_background = True
    bmp_info.should_draw_basin_boundaries = False
    bmp_info.map_bg_color = "0.75"

    station_ids = ["104001", "093806", "093801", "081002", "081007", "080718"]

    # get river network information used in the model
    flow_directions = analysis.get_array_from_file(
        r_config.data_path, var_name=infovar.HDF_FLOW_DIRECTIONS_NAME)
    accumulation_area_km2 = analysis.get_array_from_file(
        path=r_config.data_path, var_name=infovar.HDF_ACCUMULATION_AREA_NAME)
    cell_manager = CellManager(flow_dirs=flow_directions,
                               lons2d=bmp_info.lons,
                               lats2d=bmp_info.lats,
                               accumulation_area_km2=accumulation_area_km2)

    # Get the list of stations to indicate on the bias map
    stations = cehq_station.read_station_data(start_date=None,
                                              end_date=None,
                                              selected_ids=station_ids)
    """:type : list[Station]"""

    xx, yy = bmp_info.get_proj_xy()
    station_to_modelpoint = cell_manager.get_model_points_for_stations(
        station_list=stations)
    upstream_edges = cell_manager.get_upstream_polygons_for_points(
        model_point_list=station_to_modelpoint.values(), xx=xx, yy=yy)

    bmp_info.draw_colorbar_for_each_subplot = True

    # Validate temperature, precip and swe
    obs_path_anusplin = "/home/huziy/skynet3_rech1/anusplin_links"
    obs_path_swe = "data/swe_ross_brown/swe.nc"
    model_var_to_obs_path = OrderedDict([("TT", obs_path_anusplin),
                                         ("I5", obs_path_swe)])

    model_var_to_season = OrderedDict([
        ("TT", OrderedDict([("Spring", range(3, 6))])),
        ("I5", OrderedDict([("Winter", [1, 2, 12])]))
    ])

    vname_to_obs_data = {}

    # parameters that won't change in the loop over variable names
    params_const = dict(rconfig=r_config, bmp_info=bmp_info)

    for vname, obs_path in model_var_to_obs_path.items():
        season_to_obs_data = get_seasonal_clim_obs_data(
            vname=vname,
            obs_path=obs_path,
            season_to_months=model_var_to_season[vname],
            **params_const)

        # Comment swe over lakes, since I5 calculated only for land
        if vname in [
                "I5",
        ]:
            for season in season_to_obs_data:
                season_to_obs_data[season] = maskoceans(
                    bmp_info.lons,
                    bmp_info.lats,
                    season_to_obs_data[season],
                    inlands=True)

        vname_to_obs_data[vname] = season_to_obs_data

    # Plotting
    plot_all_vars_in_one_fig = True

    fig = None
    gs = None
    if plot_all_vars_in_one_fig:
        plot_utils.apply_plot_params(font_size=12,
                                     width_pt=None,
                                     width_cm=25,
                                     height_cm=20)
        fig = plt.figure()
        ncols = len(model_var_to_obs_path) + 1
        gs = GridSpec(len(r_config_list),
                      ncols,
                      width_ratios=(ncols - 1) * [
                          1.,
                      ] + [
                          0.05,
                      ])
    else:
        plot_utils.apply_plot_params(font_size=12,
                                     width_pt=None,
                                     width_cm=25,
                                     height_cm=25)

    station_x_list = []
    station_y_list = []

    mvarname_to_cs = {}
    for row, r_config in enumerate(r_config_list):
        for col, mname in enumerate(model_var_to_obs_path):

            row_axes = [
                fig.add_subplot(gs[row, col]),
            ]

            mvarname_to_cs[mname] = compare_vars(
                vname_model=mname,
                vname_to_obs=vname_to_obs_data,
                r_config=r_config,
                season_to_months=model_var_to_season[mname],
                bmp_info_agg=bmp_info,
                axes_list=row_axes)

            # -1 in order to exclude colorbars
            for the_ax in row_axes:

                the_ax.set_title(the_ax.get_title() + ", {}".format(
                    infovar.get_long_display_label_for_var(mname)))
                # Need titles only for the first row
                if row > 0:
                    the_ax.set_title("")

                if col == 0:
                    the_ax.set_ylabel(r_config.label)
                else:
                    the_ax.set_ylabel("")

                draw_upstream_area_bounds(the_ax, upstream_edges, color="g")

                if len(station_x_list) == 0:
                    for the_station in stations:
                        xst, yst = bmp_info.basemap(the_station.longitude,
                                                    the_station.latitude)
                        station_x_list.append(xst)
                        station_y_list.append(yst)

                bmp_info.basemap.scatter(station_x_list,
                                         station_y_list,
                                         c="g",
                                         ax=the_ax,
                                         s=20,
                                         zorder=10,
                                         alpha=0.5)

    # Save the figure if necessary
    if plot_all_vars_in_one_fig:

        if not img_folder.is_dir():
            img_folder.mkdir(parents=True)

        fig_path = img_folder.joinpath("{}.png".format(
            "_".join(model_var_to_obs_path)))
        with fig_path.open("wb") as figfile:
            fig.savefig(figfile, format="png", bbox_inches="tight")

        plt.close(fig)
Exemplo n.º 3
0
def plot_seasonal_mean_biases(season_to_error_field=None, varname="", basemap_info=None,
                              axes_list=None):
    assert isinstance(basemap_info, BasemapInfo)

    # Set to False if you want the limits to be recalculated from data
    manual_limits = True

    d = max([np.percentile(np.abs(field[~field.mask]), 95) for s, field in season_to_error_field.items()])

    if manual_limits and varname in ["PR", "TT", "I5"]:
        clevs = np.arange(-d, 1.1 * d, 0.1 * d)

        if varname == "PR":
            clevs = np.arange(-3, 3.5, 0.5)
        if varname == "TT":
            clevs = np.arange(-7, 8, 1)
        if varname == "I5":
            clevs = np.arange(-100, 110, 10)

    else:
        clevs = MaxNLocator(nbins=10, symmetric=True).tick_values(-d, d)
    cmap = cm.get_cmap("RdBu_r", len(clevs) - 1)

    fig = None
    fig_path = None
    if axes_list is None:
        fig_path = img_folder.joinpath("{}.png".format(varname))
        fig = plt.figure()

    nrows = 2
    ncols = 2
    gs = GridSpec(nrows, ncols=ncols + 1, width_ratios=[1, 1, 0.05])

    xx, yy = basemap_info.get_proj_xy()

    cs = None
    for i, season in enumerate(season_to_error_field):
        row = i // ncols
        col = i % ncols

        if axes_list is None:
            ax = fig.add_subplot(gs[row, col])
        else:
            ax = axes_list[i]

        basemap_info.draw_map_background(ax)

        cs = basemap_info.basemap.contourf(xx, yy, season_to_error_field[season][:], ax=ax, cmap=cmap, levels=clevs,
                                           extend="both")
        basemap_info.basemap.drawcoastlines(ax=ax, linewidth=0.3)
        ax.set_title(season)
        if i == 0:
            ax.set_ylabel(infovar.get_long_display_label_for_var(varname=varname))
        # basemap_info.basemap.colorbar(cs)

        if basemap_info.should_draw_basin_boundaries:
            basemap_info.basemap.readshapefile(BASIN_BOUNDARIES_SHP[:-4], "basin", ax=ax)

        # Hide snow plots for summer
        if varname in ["I5"] and season.lower() in ["summer"]:
            ax.set_visible(False)

        # Plot a colorbar for each subplot if required.
        if hasattr(basemap_info, "draw_colorbar_for_each_subplot"):
            if basemap_info.draw_colorbar_for_each_subplot:
                cb = basemap_info.basemap.colorbar(cs, ax=ax)
                cb.ax.set_title(infovar.get_units(var_name=varname))

    cax = fig.add_subplot(gs[:, -1]) if axes_list is None else axes_list[-1]

    # Add the colorbar if there are additional axes supplied for it
    if len(axes_list) > len(season_to_error_field):
        cax.set_title(infovar.get_units(var_name=varname))
        plt.colorbar(cs, cax=cax)

    if axes_list is None:
        with fig_path.open("wb") as figfile:
            fig.savefig(figfile, format="png", bbox_inches="tight")

        plt.close(fig)

    return cs
Exemplo n.º 4
0
def _plot_row(vname="", level=0, config_dict=None, plot_cc_only_for=None, mark_significance=True):
    """
    if plot_cc_only_for is not None, should be equal to the label of the simulation to be plotted
    """

    lons, lats = config_dict.lons, config_dict.lats

    bmp = config_dict.basemap
    """
    :type bmp: mpl_toolkits.basemap.Basemap
    """


    xx, yy = bmp(lons, lats)
    lons[lons > 180] -= 360

    fig = config_dict.fig
    gs = config_dict.gs
    """:type : matplotlib.gridspec.GridSpec """
    nrows_subplots, ncols_subplots = gs.get_geometry()


    label_base = config_dict.label_base
    label_modif = config_dict.label_modif

    the_row = config_dict.the_row
    season_to_months = config_dict.season_to_months

    if "+" in vname or "-" in vname:
        op = "+" if "+" in vname else "-"
        vname1, vname2 = vname.split(op)

        vname1 = vname1.strip()
        vname2 = vname2.strip()

        current_base = {}
        future_base = {}

        current_modif = {}
        future_modif = {}

        # vname1
        current_base1 = compute_seasonal_means_for_each_year(config_dict["Current"][label_base], var_name=vname1,
                                                             level=level,
                                                             season_to_months=season_to_months)
        future_base1 = compute_seasonal_means_for_each_year(config_dict["Future"][label_base], var_name=vname1,
                                                            level=level,
                                                            season_to_months=season_to_months)

        current_modif1 = compute_seasonal_means_for_each_year(config_dict["Current"][label_modif], var_name=vname1,
                                                              level=level,
                                                              season_to_months=season_to_months)
        future_modif1 = compute_seasonal_means_for_each_year(config_dict["Future"][label_modif], var_name=vname1,
                                                             level=level,
                                                             season_to_months=season_to_months)


        # vname2
        current_base2 = compute_seasonal_means_for_each_year(config_dict["Current"][label_base], var_name=vname2,
                                                             level=level,
                                                             season_to_months=season_to_months)
        future_base2 = compute_seasonal_means_for_each_year(config_dict["Future"][label_base], var_name=vname2,
                                                            level=level,
                                                            season_to_months=season_to_months)

        current_modif2 = compute_seasonal_means_for_each_year(config_dict["Current"][label_modif], var_name=vname2,
                                                              level=level,
                                                              season_to_months=season_to_months)
        future_modif2 = compute_seasonal_means_for_each_year(config_dict["Future"][label_modif], var_name=vname2,
                                                             level=level,
                                                             season_to_months=season_to_months)

        for season in current_base1:
            current_base[season] = eval("current_base2[season]{}current_base1[season]".format(op))
            future_base[season] = eval("future_base2[season]{}future_base1[season]".format(op))
            current_modif[season] = eval("current_modif2[season]{}current_modif1[season]".format(op))
            future_modif[season] = eval("future_modif2[season]{}future_modif1[season]".format(op))


    else:
        current_base = compute_seasonal_means_for_each_year(config_dict["Current"][label_base], var_name=vname,
                                                            level=level,
                                                            season_to_months=season_to_months)
        future_base = compute_seasonal_means_for_each_year(config_dict["Future"][label_base], var_name=vname,
                                                           level=level,
                                                           season_to_months=season_to_months)

        current_modif = compute_seasonal_means_for_each_year(config_dict["Current"][label_modif], var_name=vname,
                                                             level=level,
                                                             season_to_months=season_to_months)
        future_modif = compute_seasonal_means_for_each_year(config_dict["Future"][label_modif], var_name=vname,
                                                            level=level,
                                                            season_to_months=season_to_months)




    # Calculate the differences in cc signal
    season_to_diff = OrderedDict()

    season_to_plot_diff = OrderedDict()

    diff_max = 0
    print(list(current_base.keys()))
    # Get the ranges for colorbar and calculate p-values
    print("------------------ impacts on projected changes to {} -----------------------".format(vname))
    season_to_pvalue = OrderedDict()
    for season in list(current_base.keys()):

        _, pvalue_current = ttest_ind(current_modif[season], current_base[season], axis=0, equal_var=False)
        _, pvalue_future = ttest_ind(future_modif[season], future_base[season], axis=0, equal_var=False)

        if plot_cc_only_for is None:
            season_to_pvalue[season] = np.minimum(pvalue_current, pvalue_future)

            season_to_diff[season] = (future_modif[season] - current_modif[season]) - \
                                     (future_base[season] - current_base[season])

        else:

            if plot_cc_only_for == label_base:
                _, season_to_pvalue[season] = ttest_ind(future_base[season], current_base[season], axis=0, equal_var=False)
                c_data = current_base[season]
                f_data = future_base[season]
            else:
                _, season_to_pvalue[season] = ttest_ind(future_modif[season], current_modif[season], axis=0, equal_var=False)
                c_data = current_modif[season]
                f_data = future_modif[season]

            season_to_diff[season] = f_data - c_data


        # Convert units if required
        if vname in config_dict.multipliers:
            season_to_diff[season] *= config_dict.multipliers[vname]

        field_to_plot = infovar.get_to_plot(vname, season_to_diff[season].mean(axis=0), lons=lons, lats=lats)
        season_to_plot_diff[season] = field_to_plot


        print("{}: {}".format(season, season_to_plot_diff[season].mean()))

        if hasattr(field_to_plot, "mask"):
            diff_max = max(np.percentile(np.abs(field_to_plot[~field_to_plot.mask]), 95), diff_max)
        else:
            diff_max = max(np.percentile(np.abs(field_to_plot), 95), diff_max)

    print("--------------------------------------------------------")

    img = None
    locator = MaxNLocator(nbins=10, symmetric=True)
    clevels = locator.tick_values(-diff_max, diff_max)

    bn = BoundaryNorm(clevels, len(clevels) - 1)
    cmap = cm.get_cmap("RdBu_r", len(clevels) - 1)
    for col, season in enumerate(current_base.keys()):
        ax = fig.add_subplot(gs[the_row, col])

        if not col:
            ax.set_ylabel(infovar.get_long_display_label_for_var(vname))

        if not the_row:
            ax.set_title(season)

        img = bmp.pcolormesh(xx, yy, season_to_plot_diff[season].copy(),
                             vmin=-diff_max, vmax=diff_max,
                             cmap=cmap, norm=bn, ax=ax)


        # logging
        good_vals = season_to_plot_diff[season]
        good_vals = good_vals[~good_vals.mask]
        print("------" * 10)
        print("{}: min={}; max={}; area-avg={};".format(season, good_vals.min(), good_vals.max(), good_vals.mean()))


        bmp.readshapefile(quebec_info.BASIN_BOUNDARIES_DERIVED_10km[:-4], "basin_edge", ax=ax)

        p = season_to_pvalue[season]
        if hasattr(season_to_plot_diff[season], "mask"):
            p = np.ma.masked_where(season_to_plot_diff[season].mask, p)


        if plot_cc_only_for is not None and mark_significance:
            cs = bmp.contourf(xx, yy, p, hatches=["..."], levels=[0.05, 1], colors='none')

            if (col == ncols_subplots - 2) and (the_row == nrows_subplots - 1):
                # create a legend for the contour set
                artists, labels = cs.legend_elements()
                labels = ["not significant"]
                ax.legend(artists, labels, handleheight=1, loc="upper right",
                          bbox_to_anchor=(1.0, -0.05), borderaxespad=0., frameon=False)


        bmp.drawcoastlines(ax=ax, linewidth=0.4)
        if vname in ["I5"] and season.lower() in ["summer"]:
            ax.set_visible(False)



    cb = plt.colorbar(img, cax=fig.add_subplot(gs[the_row, len(current_base)]), extend="both")

    if hasattr(config_dict, "name_to_units") and vname in config_dict.name_to_units:
        cb.ax.set_title(config_dict.name_to_units[vname])
    else:
        cb.ax.set_title(infovar.get_units(vname))
def plot_control_and_differences_in_one_panel_for_all_seasons_for_all_vars(
        varnames=None, levels=None,
        season_to_months=None,
        start_year=None,
        end_year=None):
    season_list = list(season_to_months.keys())

    pvalue_max = 0.1

    # crcm5-r vs crcm5-hcd-r
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r_spinup.hdf"
    # control_label = "CRCM5-R"
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r_spinup2.hdf", ]
    # labels = ["CRCM5-HCD-R"]

    # crcm5-hcd-rl vs crcm5-hcd-r
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r_spinup2.hdf"
    # control_label = "CRCM5-HCD-R"
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl_spinup.hdf", ]
    # labels = ["CRCM5-HCD-RL"]

    # compare simulations with and without interflow
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl_spinup.hdf"
    # control_label = "CRCM5-HCD-RL"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_do_not_discard_small.hdf", ]
    # labels = ["CRCM5-HCD-RL-INTFL"]

    # very high hydr cond
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_do_not_discard_small.hdf"
    # control_label = "CRCM5-HCD-RL-INTFL"
    ##
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_sani-10000.hdf", ]
    # labels = ["CRCM5-HCD-RL-INTFL-sani=10000"]

    # Interflow effect
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl_spinup.hdf"
    # control_label = "CRCM5-HCD-RL"
    # ##
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_spinup_ITFS.hdf5", ]
    # labels = ["ITFS"]


    # total lake effect
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r.hdf5"
    # control_label = "CRCM5-NL"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl.hdf5", ]
    # labels = ["CRCM5-L2", ]



    # lake effect (lake-atm interactions)
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r.hdf5"
    # control_label = "CRCM5-R"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r.hdf5", ]
    # labels = ["CRCM5-HCD-R", ]

    # lake effect (lake-river interactions)
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r.hdf5"
    # control_label = "CRCM5-L1"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl.hdf5", ]
    # labels = ["CRCM5-HCD-L2", ]


    # interflow effect ()
    control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl.hdf5"
    control_label = "CRCM5-L2"

    paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS.hdf5", ]
    labels = ["CRCM5-L2I", ]


    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS_avoid_truncation1979-1989.hdf5", ]
    # labels = ["CRCM5-HCD-RL-INTFb", ]



    # interflow effect (avoid truncation and bigger slopes)
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS.hdf5"
    # control_label = "CRCM5-HCD-RL-INTF"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS_avoid_truncation1979-1989.hdf5", ]
    # labels = ["CRCM5-HCD-RL-INTF-improved", ]
    #

    row_labels = [
        r"{} vs {}".format(s, control_label) for s in labels
    ]
    print(labels)

    # varnames = ["QQ", ]
    # levels = [None, ]

    assert len(levels) == len(varnames)

    lons2d, lats2d, basemap = analysis.get_basemap_from_hdf(file_path=control_path)
    x, y = basemap(lons2d, lats2d)
    # save the domain properties for reuse
    domain_props = DomainProperties()
    domain_props.basemap = basemap
    domain_props.lons2d = lons2d
    domain_props.lats2d = lats2d
    domain_props.x = x
    domain_props.y = y

    lake_fraction = analysis.get_array_from_file(path=control_path, var_name=infovar.HDF_LAKE_FRACTION_NAME)
    dpth_to_bedrock = analysis.get_array_from_file(path=control_path, var_name=infovar.HDF_DEPTH_TO_BEDROCK_NAME)

    assert dpth_to_bedrock is not None


    if lake_fraction is None:
        lake_fraction = np.zeros(lons2d.shape)

    ncolors = 10
    # +1 to include white
    diff_cmap = cm.get_cmap("RdBu", ncolors + 1)


    # Do the plotting for each variable
    fig = plt.figure()
    assert isinstance(fig, Figure)

    # plot the control data
    ncols = len(season_list) + 1  # +1 is for the colorbar
    gs = gridspec.GridSpec(len(varnames), ncols, width_ratios=[1.0, ] * (ncols - 1) + [0.07], top=0.95)


    lev_width_3d = np.ones(dpth_to_bedrock.shape + infovar.soil_layer_widths_26_to_60.shape)
    lev_width_3d *= infovar.soil_layer_widths_26_to_60[np.newaxis, np.newaxis, :]
    lev_bot_3d = lev_width_3d.cumsum(axis=2)

    correction = -lev_bot_3d + dpth_to_bedrock[:, :, np.newaxis]
    # Apply the correction only at points where the layer bottom is lower than
    # the bedrock
    lev_width_3d[correction < 0] += correction[correction < 0]
    lev_width_3d[lev_width_3d < 0] = 0


    # plot the plots one file per variable
    for var_name, level, the_row in zip(varnames, levels, list(range(len(varnames)))):
        sfmt = infovar.get_colorbar_formatter(var_name)
        season_to_control_mean = {}
        label_to_season_to_difference = {}
        label_to_season_to_significance = {}

        try:
            # Calculate the difference for each season, and save the results to dictionaries
            # to access later when plotting
            for season, months_of_interest in season_to_months.items():
                print("working on season: {0}".format(season))

                control_means = analysis.get_mean_2d_fields_for_months(path=control_path, var_name=var_name,
                                                                       months=months_of_interest,
                                                                       start_year=start_year, end_year=end_year,
                                                                       level=level)

                control_mean = np.mean(control_means, axis=0)

                control_mean = infovar.get_to_plot(var_name, control_mean,
                                                   lake_fraction=domain_props.lake_fraction,
                                                   lons=lons2d, lats=lats2d, level_width_m=lev_width_3d[:, :, level])

                # multiply by the number of days in a season for PR and TRAF to convert them into mm from mm/day
                if var_name in ["PR", "TRAF", "TDRA"]:
                    control_mean *= get_num_days(months_of_interest)
                    infovar.change_units_to(varnames=[var_name, ], new_units=r"${\rm mm}$")

                season_to_control_mean[season] = control_mean

                print("calculated mean from {0}".format(control_path))

                # calculate the difference for each simulation
                for the_path, the_label in zip(paths, row_labels):
                    modified_means = analysis.get_mean_2d_fields_for_months(path=the_path, var_name=var_name,
                                                                            months=months_of_interest,
                                                                            start_year=start_year, end_year=end_year,
                                                                            level=level)

                    tval, pval = ttest_ind(modified_means, control_means, axis=0, equal_var=False)
                    significance = ((pval <= pvalue_max) & (~control_mean.mask)).astype(int)
                    print("pval ranges: {} to {}".format(pval.min(), pval.max()))

                    modified_mean = np.mean(modified_means, axis=0)
                    if the_label not in label_to_season_to_difference:
                        label_to_season_to_difference[the_label] = OrderedDict()
                        label_to_season_to_significance[the_label] = OrderedDict()

                    modified_mean = infovar.get_to_plot(var_name, modified_mean,
                                                        lake_fraction=domain_props.lake_fraction, lons=lons2d,
                                                        lats=lats2d, level_width_m=lev_width_3d[:, :, level])

                    # multiply by the number of days in a season for PR and TRAF to convert them into mm from mm/day
                    if var_name in ["PR", "TRAF", "TDRA"]:
                        modified_mean *= get_num_days(months_of_interest)

                    diff_vals = modified_mean - control_mean

                    print("diff ranges: min: {0};  max: {1}".format(diff_vals.min(), diff_vals.max()))
                    label_to_season_to_difference[the_label][season] = diff_vals
                    label_to_season_to_significance[the_label][season] = significance

                    print("Calculated mean and diff from {0}".format(the_path))
        except NoSuchNodeError:
            print("Could not find {0}, skipping...".format(var_name))
            continue





        for the_label, data in label_to_season_to_difference.items():
            axes = []
            for col in range(ncols):
                axes.append(fig.add_subplot(gs[the_row, col]))

            # Set season titles
            if the_row == 0:
                for the_season, ax in zip(season_list, axes):
                    ax.set_title(the_season)


            _plot_row(axes, data, the_label, var_name, increments=True, domain_props=domain_props,
                      season_list=season_list, significance=label_to_season_to_significance[the_label])

            var_label = infovar.get_long_display_label_for_var(var_name)
            if var_name in ["I1"]:
                var_label = "{}\n{} layer".format(var_label, ordinal(level + 1))

            axes[0].set_ylabel(var_label)

    fig.suptitle("({}) vs ({})".format(labels[0], control_label), font_properties=FontProperties(weight="bold"))
    folderpath = os.path.join(images_folder, "seasonal_mean_maps/{0}_vs_{1}_for_{2}_{3}-{4}".format(
        "_".join(labels), control_label, "-".join(list(season_to_months.keys())), start_year, end_year))

    if not os.path.isdir(folderpath):
        os.mkdir(folderpath)

    imname = "{0}_{1}.png".format("-".join(varnames), "_".join(labels + [control_label]))
    impath = os.path.join(folderpath, imname)
    fig.savefig(impath, bbox_inches="tight")
def main():
    # Define the simulations to be validated
    r_config = RunConfig(
        data_path="/RESCUE/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r.hdf5",
        start_year=1990, end_year=2010, label="CRCM5-L1"
    )
    r_config_list = [r_config]

    r_config = RunConfig(
        data_path="/RESCUE/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r.hdf5",
        start_year=1990, end_year=2010, label="CRCM5-NL"
    )
    r_config_list.append(r_config)

    bmp_info = analysis.get_basemap_info_from_hdf(file_path=r_config.data_path)
    bmp_info.should_draw_grey_map_background = True
    bmp_info.should_draw_basin_boundaries = False
    bmp_info.map_bg_color = "0.75"

    station_ids = [
        "104001", "093806", "093801", "081002", "081007", "080718"
    ]

    # get river network information used in the model
    flow_directions = analysis.get_array_from_file(r_config.data_path, var_name=infovar.HDF_FLOW_DIRECTIONS_NAME)
    accumulation_area_km2 = analysis.get_array_from_file(path=r_config.data_path,
                                                         var_name=infovar.HDF_ACCUMULATION_AREA_NAME)
    cell_manager = CellManager(flow_dirs=flow_directions,
                               lons2d=bmp_info.lons,
                               lats2d=bmp_info.lats, accumulation_area_km2=accumulation_area_km2)

    # Get the list of stations to indicate on the bias map
    stations = cehq_station.read_station_data(
        start_date=None, end_date=None, selected_ids=station_ids
    )
    """:type : list[Station]"""

    xx, yy = bmp_info.get_proj_xy()
    station_to_modelpoint = cell_manager.get_model_points_for_stations(station_list=stations)
    upstream_edges = cell_manager.get_upstream_polygons_for_points(
        model_point_list=station_to_modelpoint.values(), xx=xx, yy=yy)

    bmp_info.draw_colorbar_for_each_subplot = True


    # Validate temperature, precip and swe
    obs_path_anusplin = "/home/huziy/skynet3_rech1/anusplin_links"
    obs_path_swe = "data/swe_ross_brown/swe.nc"
    model_var_to_obs_path = OrderedDict([
        ("TT", obs_path_anusplin),
        ("I5", obs_path_swe)
    ])

    model_var_to_season = OrderedDict([
        ("TT",
         OrderedDict([("Spring", range(3, 6))])),
        ("I5",
         OrderedDict([("Winter", [1, 2, 12])]))
    ])

    vname_to_obs_data = {}

    # parameters that won't change in the loop over variable names
    params_const = dict(rconfig=r_config, bmp_info=bmp_info)

    for vname, obs_path in model_var_to_obs_path.items():
        season_to_obs_data = get_seasonal_clim_obs_data(vname=vname,
                                                        obs_path=obs_path,
                                                        season_to_months=model_var_to_season[vname],
                                                        **params_const)

        # Comment swe over lakes, since I5 calculated only for land
        if vname in ["I5", ]:
            for season in season_to_obs_data:
                season_to_obs_data[season] = maskoceans(bmp_info.lons, bmp_info.lats,
                                                        season_to_obs_data[season],
                                                        inlands=True)

        vname_to_obs_data[vname] = season_to_obs_data


    # Plotting
    plot_all_vars_in_one_fig = True

    fig = None
    gs = None
    if plot_all_vars_in_one_fig:
        plot_utils.apply_plot_params(font_size=12, width_pt=None, width_cm=25, height_cm=20)
        fig = plt.figure()
        ncols = len(model_var_to_obs_path) + 1
        gs = GridSpec(len(r_config_list), ncols, width_ratios=(ncols - 1) * [1., ] + [0.05, ])
    else:
        plot_utils.apply_plot_params(font_size=12, width_pt=None, width_cm=25, height_cm=25)

    station_x_list = []
    station_y_list = []

    mvarname_to_cs = {}
    for row, r_config in enumerate(r_config_list):
        for col, mname in enumerate(model_var_to_obs_path):

            row_axes = [fig.add_subplot(gs[row, col]), ]

            mvarname_to_cs[mname] = compare_vars(vname_model=mname, vname_to_obs=vname_to_obs_data,
                                                 r_config=r_config,
                                                 season_to_months=model_var_to_season[mname],
                                                 bmp_info_agg=bmp_info,
                                                 axes_list=row_axes)

            # -1 in order to exclude colorbars
            for the_ax in row_axes:


                the_ax.set_title(the_ax.get_title() + ", {}".format(infovar.get_long_display_label_for_var(mname)))
                # Need titles only for the first row
                if row > 0:
                    the_ax.set_title("")



                if col == 0:
                    the_ax.set_ylabel(r_config.label)
                else:
                    the_ax.set_ylabel("")


                draw_upstream_area_bounds(the_ax, upstream_edges, color="g")

                if len(station_x_list) == 0:
                    for the_station in stations:
                        xst, yst = bmp_info.basemap(the_station.longitude, the_station.latitude)
                        station_x_list.append(xst)
                        station_y_list.append(yst)

                bmp_info.basemap.scatter(station_x_list, station_y_list, c="g", ax=the_ax, s=20, zorder=10, alpha=0.5)






    # Save the figure if necessary
    if plot_all_vars_in_one_fig:

        if not img_folder.is_dir():
            img_folder.mkdir(parents=True)

        fig_path = img_folder.joinpath("{}.png".format("_".join(model_var_to_obs_path)))
        with fig_path.open("wb") as figfile:
            fig.savefig(figfile, format="png", bbox_inches="tight")

        plt.close(fig)
Exemplo n.º 7
0
def plot_control_and_differences_in_one_panel_for_all_seasons_for_all_vars(
        varnames=None,
        levels=None,
        season_to_months=None,
        start_year=None,
        end_year=None):
    season_list = list(season_to_months.keys())

    pvalue_max = 0.1

    # crcm5-r vs crcm5-hcd-r
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r_spinup.hdf"
    # control_label = "CRCM5-R"
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r_spinup2.hdf", ]
    # labels = ["CRCM5-HCD-R"]

    # crcm5-hcd-rl vs crcm5-hcd-r
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r_spinup2.hdf"
    # control_label = "CRCM5-HCD-R"
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl_spinup.hdf", ]
    # labels = ["CRCM5-HCD-RL"]

    # compare simulations with and without interflow
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl_spinup.hdf"
    # control_label = "CRCM5-HCD-RL"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_do_not_discard_small.hdf", ]
    # labels = ["CRCM5-HCD-RL-INTFL"]

    # very high hydr cond
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_do_not_discard_small.hdf"
    # control_label = "CRCM5-HCD-RL-INTFL"
    ##
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_sani-10000.hdf", ]
    # labels = ["CRCM5-HCD-RL-INTFL-sani=10000"]

    # Interflow effect
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl_spinup.hdf"
    # control_label = "CRCM5-HCD-RL"
    # ##
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_spinup_ITFS.hdf5", ]
    # labels = ["ITFS"]

    # total lake effect
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r.hdf5"
    # control_label = "CRCM5-NL"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl.hdf5", ]
    # labels = ["CRCM5-L2", ]

    # lake effect (lake-atm interactions)
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-r.hdf5"
    # control_label = "CRCM5-R"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r.hdf5", ]
    # labels = ["CRCM5-HCD-R", ]

    # lake effect (lake-river interactions)
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-r.hdf5"
    # control_label = "CRCM5-L1"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl.hdf5", ]
    # labels = ["CRCM5-HCD-L2", ]

    # interflow effect ()
    control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl.hdf5"
    control_label = "CRCM5-L2"

    paths = [
        "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS.hdf5",
    ]
    labels = [
        "CRCM5-L2I",
    ]

    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS_avoid_truncation1979-1989.hdf5", ]
    # labels = ["CRCM5-HCD-RL-INTFb", ]

    # interflow effect (avoid truncation and bigger slopes)
    # control_path = "/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS.hdf5"
    # control_label = "CRCM5-HCD-RL-INTF"
    #
    # paths = ["/skynet3_rech1/huziy/hdf_store/quebec_0.1_crcm5-hcd-rl-intfl_ITFS_avoid_truncation1979-1989.hdf5", ]
    # labels = ["CRCM5-HCD-RL-INTF-improved", ]
    #

    row_labels = [r"{} vs {}".format(s, control_label) for s in labels]
    print(labels)

    # varnames = ["QQ", ]
    # levels = [None, ]

    assert len(levels) == len(varnames)

    lons2d, lats2d, basemap = analysis.get_basemap_from_hdf(
        file_path=control_path)
    x, y = basemap(lons2d, lats2d)
    # save the domain properties for reuse
    domain_props = DomainProperties()
    domain_props.basemap = basemap
    domain_props.lons2d = lons2d
    domain_props.lats2d = lats2d
    domain_props.x = x
    domain_props.y = y

    lake_fraction = analysis.get_array_from_file(
        path=control_path, var_name=infovar.HDF_LAKE_FRACTION_NAME)
    dpth_to_bedrock = analysis.get_array_from_file(
        path=control_path, var_name=infovar.HDF_DEPTH_TO_BEDROCK_NAME)

    assert dpth_to_bedrock is not None

    if lake_fraction is None:
        lake_fraction = np.zeros(lons2d.shape)

    ncolors = 10
    # +1 to include white
    diff_cmap = cm.get_cmap("RdBu", ncolors + 1)

    # Do the plotting for each variable
    fig = plt.figure()
    assert isinstance(fig, Figure)

    # plot the control data
    ncols = len(season_list) + 1  # +1 is for the colorbar
    gs = gridspec.GridSpec(len(varnames),
                           ncols,
                           width_ratios=[
                               1.0,
                           ] * (ncols - 1) + [0.07],
                           top=0.95)

    lev_width_3d = np.ones(dpth_to_bedrock.shape +
                           infovar.soil_layer_widths_26_to_60.shape)
    lev_width_3d *= infovar.soil_layer_widths_26_to_60[np.newaxis,
                                                       np.newaxis, :]
    lev_bot_3d = lev_width_3d.cumsum(axis=2)

    correction = -lev_bot_3d + dpth_to_bedrock[:, :, np.newaxis]
    # Apply the correction only at points where the layer bottom is lower than
    # the bedrock
    lev_width_3d[correction < 0] += correction[correction < 0]
    lev_width_3d[lev_width_3d < 0] = 0

    # plot the plots one file per variable
    for var_name, level, the_row in zip(varnames, levels,
                                        list(range(len(varnames)))):
        sfmt = infovar.get_colorbar_formatter(var_name)
        season_to_control_mean = {}
        label_to_season_to_difference = {}
        label_to_season_to_significance = {}

        try:
            # Calculate the difference for each season, and save the results to dictionaries
            # to access later when plotting
            for season, months_of_interest in season_to_months.items():
                print("working on season: {0}".format(season))

                control_means = analysis.get_mean_2d_fields_for_months(
                    path=control_path,
                    var_name=var_name,
                    months=months_of_interest,
                    start_year=start_year,
                    end_year=end_year,
                    level=level)

                control_mean = np.mean(control_means, axis=0)

                control_mean = infovar.get_to_plot(
                    var_name,
                    control_mean,
                    lake_fraction=domain_props.lake_fraction,
                    lons=lons2d,
                    lats=lats2d,
                    level_width_m=lev_width_3d[:, :, level])

                # multiply by the number of days in a season for PR and TRAF to convert them into mm from mm/day
                if var_name in ["PR", "TRAF", "TDRA"]:
                    control_mean *= get_num_days(months_of_interest)
                    infovar.change_units_to(varnames=[
                        var_name,
                    ],
                                            new_units=r"${\rm mm}$")

                season_to_control_mean[season] = control_mean

                print("calculated mean from {0}".format(control_path))

                # calculate the difference for each simulation
                for the_path, the_label in zip(paths, row_labels):
                    modified_means = analysis.get_mean_2d_fields_for_months(
                        path=the_path,
                        var_name=var_name,
                        months=months_of_interest,
                        start_year=start_year,
                        end_year=end_year,
                        level=level)

                    tval, pval = ttest_ind(modified_means,
                                           control_means,
                                           axis=0,
                                           equal_var=False)
                    significance = ((pval <= pvalue_max) &
                                    (~control_mean.mask)).astype(int)
                    print("pval ranges: {} to {}".format(
                        pval.min(), pval.max()))

                    modified_mean = np.mean(modified_means, axis=0)
                    if the_label not in label_to_season_to_difference:
                        label_to_season_to_difference[the_label] = OrderedDict(
                        )
                        label_to_season_to_significance[
                            the_label] = OrderedDict()

                    modified_mean = infovar.get_to_plot(
                        var_name,
                        modified_mean,
                        lake_fraction=domain_props.lake_fraction,
                        lons=lons2d,
                        lats=lats2d,
                        level_width_m=lev_width_3d[:, :, level])

                    # multiply by the number of days in a season for PR and TRAF to convert them into mm from mm/day
                    if var_name in ["PR", "TRAF", "TDRA"]:
                        modified_mean *= get_num_days(months_of_interest)

                    diff_vals = modified_mean - control_mean

                    print("diff ranges: min: {0};  max: {1}".format(
                        diff_vals.min(), diff_vals.max()))
                    label_to_season_to_difference[the_label][
                        season] = diff_vals
                    label_to_season_to_significance[the_label][
                        season] = significance

                    print("Calculated mean and diff from {0}".format(the_path))
        except NoSuchNodeError:
            print("Could not find {0}, skipping...".format(var_name))
            continue

        for the_label, data in label_to_season_to_difference.items():
            axes = []
            for col in range(ncols):
                axes.append(fig.add_subplot(gs[the_row, col]))

            # Set season titles
            if the_row == 0:
                for the_season, ax in zip(season_list, axes):
                    ax.set_title(the_season)

            _plot_row(axes,
                      data,
                      the_label,
                      var_name,
                      increments=True,
                      domain_props=domain_props,
                      season_list=season_list,
                      significance=label_to_season_to_significance[the_label])

            var_label = infovar.get_long_display_label_for_var(var_name)
            if var_name in ["I1"]:
                var_label = "{}\n{} layer".format(var_label,
                                                  ordinal(level + 1))

            axes[0].set_ylabel(var_label)

    fig.suptitle("({}) vs ({})".format(labels[0], control_label),
                 font_properties=FontProperties(weight="bold"))
    folderpath = os.path.join(
        images_folder, "seasonal_mean_maps/{0}_vs_{1}_for_{2}_{3}-{4}".format(
            "_".join(labels), control_label,
            "-".join(list(season_to_months.keys())), start_year, end_year))

    if not os.path.isdir(folderpath):
        os.mkdir(folderpath)

    imname = "{0}_{1}.png".format("-".join(varnames),
                                  "_".join(labels + [control_label]))
    impath = os.path.join(folderpath, imname)
    fig.savefig(impath, bbox_inches="tight")
Exemplo n.º 8
0
def _plot_var(vname="", level=0, config_dict=None, data_dict=None):
    modif_label = config_dict.label_modif
    base_label = config_dict.label_base

    base_config_c, modif_config_c = [
        config_dict["Current"][the_label]
        for the_label in [base_label, modif_label]
    ]
    base_config_f, modif_config_f = [
        config_dict["Future"][the_label]
        for the_label in [base_label, modif_label]
    ]

    bmp = config_dict.basemap
    lons = config_dict.lons
    lons[lons > 180] -= 360

    lats = config_dict.lats
    xx, yy = bmp(lons, lats)

    i_to_label = {
        0: base_label,
        1: modif_label,
        2: "{}\n--\n{}".format(modif_label, base_label)
    }

    j_to_title = {
        0:
        "Current ({}-{})".format(base_config_c.start_year,
                                 base_config_c.end_year),
        1:
        "Future ({}-{})".format(base_config_f.start_year,
                                base_config_f.end_year),
        2:
        "Future - Current"
    }

    # Create a folder for images
    img_folder = os.path.join("cc_paper",
                              "{}_vs_{}".format(modif_label, base_label))
    if not os.path.isdir(img_folder):
        os.makedirs(img_folder)

    nrows = ncols = 3
    plot_utils.apply_plot_params(font_size=10,
                                 width_pt=None,
                                 width_cm=27,
                                 height_cm=20)

    field_cmap = cm.get_cmap("jet", 20)
    diff_cmap = cm.get_cmap("RdBu_r", 20)

    for season in list(data_dict[base_config_c].keys()):

        fig = plt.figure()
        fig.suptitle("{} ({})".format(
            infovar.get_long_display_label_for_var(vname), season),
                     font_properties=FontProperties(weight="bold"))

        gs = GridSpec(nrows=nrows, ncols=ncols)

        mean_c_base = data_dict[base_config_c][season].mean(axis=0)
        mean_f_base = data_dict[base_config_f][season].mean(axis=0)

        mean_c_modif = data_dict[modif_config_c][season].mean(axis=0)
        mean_f_modif = data_dict[modif_config_f][season].mean(axis=0)

        print("------------ {}, {} --------------".format(vname, season))
        print("data_dict[base_config_c][season].shape = {}".format(
            data_dict[base_config_c][season].shape))
        _, p_signif_base_cc = ttest_ind(data_dict[base_config_c][season],
                                        data_dict[base_config_f][season],
                                        axis=0,
                                        equal_var=False)
        _, p_signif_current = ttest_ind(data_dict[base_config_c][season],
                                        data_dict[modif_config_c][season],
                                        axis=0,
                                        equal_var=False)

        print("Base p-value ranges: {} to {}".format(p_signif_base_cc.min(),
                                                     p_signif_base_cc.max()))
        _, p_signif_modif_cc = ttest_ind(data_dict[modif_config_c][season],
                                         data_dict[modif_config_f][season],
                                         axis=0,
                                         equal_var=False)
        _, p_signif_future = ttest_ind(data_dict[base_config_f][season],
                                       data_dict[modif_config_f][season],
                                       axis=0,
                                       equal_var=False)

        ij_to_pvalue = {
            (0, 2): p_signif_base_cc,
            (1, 2): p_signif_modif_cc,
            (2, 0): p_signif_current,
            (2, 1): p_signif_future,
            # (2, 2): np.minimum(p_signif_current, p_signif_future)
        }

        ij_to_data = {
            (0, 0): mean_c_base,
            (1, 0): mean_c_modif,
            (0, 1): mean_f_base,
            (1, 1): mean_f_modif
        }

        # Apply multipliers for unit conversion
        for k in list(ij_to_data.keys()):
            ij_to_data[k] *= multiplier_dict.get(vname, 1)

            # mask oceans
            mask_inland = vname in ["STFL", "STFA"] or vname.startswith("I")
            ij_to_data[k] = maskoceans(lonsin=lons,
                                       latsin=lats,
                                       datain=ij_to_data[k],
                                       inlands=mask_inland)

        # get all means to calculate the ranges of mean fields
        all_means = []
        for vals in ij_to_data.values():
            all_means.extend(vals[~vals.mask])

        if vname == "PR":
            # mm/day
            minval = 0
            maxval = 5
            extend_val = "max"
        else:
            minval = np.percentile(all_means, 1)
            maxval = np.percentile(all_means, 95)
            extend_val = "neither"

        d1 = ij_to_data[0, 1] - ij_to_data[0, 0]
        d2 = ij_to_data[1, 1] - ij_to_data[1, 0]
        all_cc_diffs = np.ma.asarray([d1, d2])
        mindiff_cc = np.percentile(all_cc_diffs[~all_cc_diffs.mask], 1)
        maxdiff_cc = np.percentile(all_cc_diffs[~all_cc_diffs.mask], 99)

        maxdiff_cc = max(np.ma.abs(maxdiff_cc), np.ma.abs(mindiff_cc))

        # Limit the temperature change scale
        if vname == "TT":
            maxdiff_cc = min(maxdiff_cc, 10)

        mindiff_cc = -maxdiff_cc

        # Add all differences due to changed processes in a list
        all_proc_diffs = []

        d1 = ij_to_data[1, 0] - ij_to_data[0, 0]
        d2 = ij_to_data[1, 1] - ij_to_data[0, 1]
        all_proc_diffs.extend([d1, d2])
        all_proc_diffs.append(d2 - d1)
        all_proc_diffs = np.ma.asarray(all_proc_diffs)

        mindiff_proc = np.percentile(all_proc_diffs[~all_proc_diffs.mask], 1)
        maxdiff_proc = np.percentile(all_proc_diffs[~all_proc_diffs.mask], 95)

        maxdiff_proc = max(np.abs(maxdiff_proc), np.abs(mindiff_proc))
        mindiff_proc = -maxdiff_proc

        plot_data = []
        for row in range(nrows - 1):
            row_data = []
            for col in range(ncols - 1):
                row_data.append(ij_to_data[row, col])
            plot_data.append(row_data + [
                0,
            ])

        # calculate differences between different model configurations
        row = 2
        plot_data.append([0, 0, 0])
        for col in range(2):
            plot_data[row][col] = plot_data[1][col] - plot_data[0][col]

        # calculate CC
        col = 2
        for row in range(3):
            plot_data[row][col] = plot_data[row][1] - plot_data[row][0]

        # Do the plotting
        for i in range(nrows):
            for j in range(ncols):

                ax = fig.add_subplot(gs[i, j])
                plotting_values = (i < 2) and (j < 2)

                if plotting_values:
                    the_min, the_max = minval, maxval
                elif i == nrows - 1:
                    the_min, the_max = mindiff_proc, maxdiff_proc
                else:
                    the_min, the_max = mindiff_cc, maxdiff_cc

                the_cmap = field_cmap if plotting_values else diff_cmap

                locator = MaxNLocator(nbins=the_cmap.N // 2,
                                      symmetric=not plotting_values)
                bounds = locator.tick_values(the_min, the_max)

                if vname in ["STFA", "STFL"] and plotting_values:
                    the_min = 1.0e-5
                    the_max = 1.0e4

                    locator = LogLocator(numticks=11)
                    bounds = locator.tick_values(the_min, the_max)

                    print(bounds)

                    norm = LogNorm(vmin=bounds[0], vmax=bounds[-1])

                    plot_data[i][j] = np.ma.masked_where(
                        plot_data[i][j] <= the_min, plot_data[i][j])
                    print("the_max = {}".format(the_max))

                    the_cmap = cm.get_cmap("jet", len(bounds) - 1)

                else:
                    norm = BoundaryNorm(bounds, the_cmap.N)

                extend = "both" if not plotting_values else extend_val

                if plotting_values:
                    print(i, j, the_min, the_max)

                im = bmp.pcolormesh(xx,
                                    yy,
                                    plot_data[i][j][:, :],
                                    cmap=the_cmap,
                                    norm=norm)

                if (i, j) in ij_to_pvalue:
                    p = ij_to_pvalue[i, j]
                    # not_signif = (p > 0.2)
                    # not_signif = np.ma.masked_where(~not_signif, not_signif) * 0.75
                    # not_signif = np.ma.masked_where(plot_data[i][j].mask, not_signif)
                    # bmp.pcolormesh(xx, yy, not_signif, vmin=0, vmax=1, cmap=cm.get_cmap("gray", 20))
                    p = np.ma.masked_where(plot_data[i][j].mask, p)
                    cs = bmp.contourf(xx,
                                      yy,
                                      p,
                                      hatches=["..."],
                                      levels=[0.1, 1],
                                      colors='none')
                    # create a legend for the contour set
                    # artists, labels = cs.legend_elements()
                    # ax.legend(artists, labels, handleheight=2)

                bmp.colorbar(im, ticks=bounds, extend=extend)
                bmp.drawcoastlines(ax=ax, linewidth=0.5)

                ax.set_title(j_to_title.get(j, "") if i == 0 else "")
                ax.set_ylabel(i_to_label.get(i, "") if j == 0 else "")

        # Save the image to the file
        img_name = "{}_{}_{}-{}_{}-{}.png".format(vname + str(level), season,
                                                  base_config_f.start_year,
                                                  base_config_f.end_year,
                                                  base_config_c.start_year,
                                                  base_config_c.end_year)

        img_path = os.path.join(img_folder, img_name)
        fig.savefig(img_path, bbox_inches="tight")
        plt.close(fig)
def _plot_var(vname="", level=0, config_dict=None, data_dict=None):
    modif_label = config_dict.label_modif
    base_label = config_dict.label_base

    base_config_c, modif_config_c = [config_dict["Current"][the_label] for the_label in [base_label, modif_label]]
    base_config_f, modif_config_f = [config_dict["Future"][the_label] for the_label in [base_label, modif_label]]

    bmp = config_dict.basemap
    lons = config_dict.lons
    lons[lons > 180] -= 360

    lats = config_dict.lats
    xx, yy = bmp(lons, lats)

    i_to_label = {
        0: base_label,
        1: modif_label,
        2: "{}\n--\n{}".format(modif_label, base_label)
    }

    j_to_title = {
        0: "Current ({}-{})".format(base_config_c.start_year, base_config_c.end_year),
        1: "Future ({}-{})".format(base_config_f.start_year, base_config_f.end_year),
        2: "Future - Current"
    }

    # Create a folder for images
    img_folder = os.path.join("cc_paper", "{}_vs_{}".format(modif_label, base_label))
    if not os.path.isdir(img_folder):
        os.makedirs(img_folder)

    nrows = ncols = 3
    plot_utils.apply_plot_params(font_size=10, width_pt=None, width_cm=27, height_cm=20)

    field_cmap = cm.get_cmap("jet", 20)
    diff_cmap = cm.get_cmap("RdBu_r", 20)

    for season in list(data_dict[base_config_c].keys()):

        fig = plt.figure()
        fig.suptitle(
            "{} ({})".format(infovar.get_long_display_label_for_var(vname), season),
            font_properties=FontProperties(weight="bold"))

        gs = GridSpec(nrows=nrows, ncols=ncols)

        mean_c_base = data_dict[base_config_c][season].mean(axis=0)
        mean_f_base = data_dict[base_config_f][season].mean(axis=0)


        mean_c_modif = data_dict[modif_config_c][season].mean(axis=0)
        mean_f_modif = data_dict[modif_config_f][season].mean(axis=0)


        print("------------ {}, {} --------------".format(vname, season))
        print("data_dict[base_config_c][season].shape = {}".format(data_dict[base_config_c][season].shape))
        _, p_signif_base_cc = ttest_ind(data_dict[base_config_c][season], data_dict[base_config_f][season], axis=0, equal_var=False)
        _, p_signif_current = ttest_ind(data_dict[base_config_c][season], data_dict[modif_config_c][season], axis=0, equal_var=False)

        print("Base p-value ranges: {} to {}".format(p_signif_base_cc.min(), p_signif_base_cc.max()))
        _, p_signif_modif_cc = ttest_ind(data_dict[modif_config_c][season], data_dict[modif_config_f][season], axis=0, equal_var=False)
        _, p_signif_future = ttest_ind(data_dict[base_config_f][season], data_dict[modif_config_f][season], axis=0, equal_var=False)

        ij_to_pvalue = {
            (0, 2): p_signif_base_cc,
            (1, 2): p_signif_modif_cc,
            (2, 0): p_signif_current,
            (2, 1): p_signif_future,
            # (2, 2): np.minimum(p_signif_current, p_signif_future)
        }

        ij_to_data = {
            (0, 0): mean_c_base, (1, 0): mean_c_modif,
            (0, 1): mean_f_base, (1, 1): mean_f_modif
        }

        # Apply multipliers for unit conversion
        for k in list(ij_to_data.keys()):
            ij_to_data[k] *= multiplier_dict.get(vname, 1)

            # mask oceans
            mask_inland = vname in ["STFL", "STFA"] or vname.startswith("I")
            ij_to_data[k] = maskoceans(lonsin=lons, latsin=lats, datain=ij_to_data[k], inlands=mask_inland)

        # get all means to calculate the ranges of mean fields
        all_means = []
        for vals in ij_to_data.values():
            all_means.extend(vals[~vals.mask])

        if vname == "PR":
            # mm/day
            minval = 0
            maxval = 5
            extend_val = "max"
        else:
            minval = np.percentile(all_means, 1)
            maxval = np.percentile(all_means, 95)
            extend_val = "neither"


        d1 = ij_to_data[0, 1] - ij_to_data[0, 0]
        d2 = ij_to_data[1, 1] - ij_to_data[1, 0]
        all_cc_diffs = np.ma.asarray([d1, d2])
        mindiff_cc = np.percentile(all_cc_diffs[~all_cc_diffs.mask], 1)
        maxdiff_cc = np.percentile(all_cc_diffs[~all_cc_diffs.mask], 99)

        maxdiff_cc = max(np.ma.abs(maxdiff_cc), np.ma.abs(mindiff_cc))

        # Limit the temperature change scale
        if vname == "TT":
            maxdiff_cc = min(maxdiff_cc, 10)


        mindiff_cc = -maxdiff_cc


        # Add all differences due to changed processes in a list
        all_proc_diffs = []

        d1 = ij_to_data[1, 0] - ij_to_data[0, 0]
        d2 = ij_to_data[1, 1] - ij_to_data[0, 1]
        all_proc_diffs.extend([d1, d2])
        all_proc_diffs.append(d2 - d1)
        all_proc_diffs = np.ma.asarray(all_proc_diffs)


        mindiff_proc = np.percentile(all_proc_diffs[~all_proc_diffs.mask], 1)
        maxdiff_proc = np.percentile(all_proc_diffs[~all_proc_diffs.mask], 95)

        maxdiff_proc = max(np.abs(maxdiff_proc), np.abs(mindiff_proc))
        mindiff_proc = -maxdiff_proc

        plot_data = []
        for row in range(nrows - 1):
            row_data = []
            for col in range(ncols - 1):
                row_data.append(ij_to_data[row, col])
            plot_data.append(row_data + [0, ])

        # calculate differences between different model configurations
        row = 2
        plot_data.append([0, 0, 0])
        for col in range(2):
            plot_data[row][col] = plot_data[1][col] - plot_data[0][col]

        # calculate CC
        col = 2
        for row in range(3):
            plot_data[row][col] = plot_data[row][1] - plot_data[row][0]


        # Do the plotting
        for i in range(nrows):
            for j in range(ncols):

                ax = fig.add_subplot(gs[i, j])
                plotting_values = (i < 2) and (j < 2)

                if plotting_values:
                    the_min, the_max = minval, maxval
                elif i == nrows - 1:
                    the_min, the_max = mindiff_proc, maxdiff_proc
                else:
                    the_min, the_max = mindiff_cc, maxdiff_cc

                the_cmap = field_cmap if plotting_values else diff_cmap

                locator = MaxNLocator(nbins=the_cmap.N // 2, symmetric=not plotting_values)
                bounds = locator.tick_values(the_min, the_max)

                if vname in ["STFA", "STFL"] and plotting_values:
                    the_min = 1.0e-5
                    the_max = 1.0e4

                    locator = LogLocator(numticks=11)
                    bounds = locator.tick_values(the_min, the_max)

                    print(bounds)

                    norm = LogNorm(vmin=bounds[0], vmax=bounds[-1])

                    plot_data[i][j] = np.ma.masked_where(plot_data[i][j] <= the_min, plot_data[i][j])
                    print("the_max = {}".format(the_max))

                    the_cmap = cm.get_cmap("jet", len(bounds) - 1)

                else:
                    norm = BoundaryNorm(bounds, the_cmap.N)

                extend = "both" if not plotting_values else extend_val

                if plotting_values:
                    print(i, j, the_min, the_max)

                im = bmp.pcolormesh(xx, yy, plot_data[i][j][:, :], cmap=the_cmap, norm=norm)

                if (i, j) in ij_to_pvalue:
                    p = ij_to_pvalue[i, j]
                    # not_signif = (p > 0.2)
                    # not_signif = np.ma.masked_where(~not_signif, not_signif) * 0.75
                    # not_signif = np.ma.masked_where(plot_data[i][j].mask, not_signif)
                    # bmp.pcolormesh(xx, yy, not_signif, vmin=0, vmax=1, cmap=cm.get_cmap("gray", 20))
                    p = np.ma.masked_where(plot_data[i][j].mask, p)
                    cs = bmp.contourf(xx, yy, p, hatches=["..."], levels=[0.1, 1], colors='none')
                    # create a legend for the contour set
                    # artists, labels = cs.legend_elements()
                    # ax.legend(artists, labels, handleheight=2)


                bmp.colorbar(im, ticks=bounds, extend=extend)
                bmp.drawcoastlines(ax=ax, linewidth=0.5)

                ax.set_title(j_to_title.get(j, "") if i == 0 else "")
                ax.set_ylabel(i_to_label.get(i, "") if j == 0 else "")

        # Save the image to the file
        img_name = "{}_{}_{}-{}_{}-{}.png".format(
            vname + str(level), season,
            base_config_f.start_year, base_config_f.end_year,
            base_config_c.start_year, base_config_c.end_year)

        img_path = os.path.join(img_folder, img_name)
        fig.savefig(img_path, bbox_inches="tight")
        plt.close(fig)
Exemplo n.º 10
0
def plot_bfe_row_for_var(finfo_to_season_to_diff=None,
                         ax_list=None,
                         season_titles=False,
                         varname="",
                         basemap_info=None):
    cmap = cm.get_cmap("RdBu_r", 20)

    assert isinstance(basemap_info, BasemapInfo)

    xx, yy = None, None
    cs = None
    for finfo, season_to_diff in finfo_to_season_to_diff.items():
        assert isinstance(finfo, FieldInfo)

        if finfo.varname != varname:
            continue

        for season in season_to_diff:
            season_to_diff[season] = infovar.get_to_plot(
                varname,
                season_to_diff[season],
                difference=True,
                lons=basemap_info.lons,
                lats=basemap_info.lats)

        clevs = get_diff_levels(season_to_diff,
                                ncolors=cmap.N,
                                varname=varname)
        for i, (season, diff) in enumerate(season_to_diff.items()):
            ax = ax_list[i]

            if xx is None or yy is None:
                xx, yy = basemap_info.get_proj_xy()

            print(diff.shape)

            cs = basemap_info.basemap.contourf(xx,
                                               yy,
                                               diff[:],
                                               cmap=cmap,
                                               levels=clevs,
                                               extend="both",
                                               ax=ax)
            basemap_info.basemap.drawcoastlines(ax=ax)
            # ax.set_aspect("auto")
            basemap_info.basemap.readshapefile(BASIN_BOUNDARIES_SHP[:-4],
                                               "basin",
                                               ax=ax)

            if season_titles:
                ax.set_title(season)

            if i == 0:
                ax.set_ylabel(
                    infovar.get_long_display_label_for_var(finfo.varname))

            if finfo.varname in [
                    "I5",
            ] and season.lower() in ["summer"]:
                ax.set_visible(False)

    ax = ax_list[-1]
    # ax.set_aspect(30)
    ax.set_title(infovar.get_units(varname))
    plt.colorbar(cs, cax=ax_list[-1])
def plot_seasonal_mean_biases(season_to_error_field=None,
                              varname="",
                              basemap_info=None,
                              axes_list=None):
    assert isinstance(basemap_info, BasemapInfo)

    # Set to False if you want the limits to be recalculated from data
    manual_limits = True

    d = max([
        np.percentile(np.abs(field[~field.mask]), 95)
        for s, field in season_to_error_field.items()
    ])

    if manual_limits and varname in ["PR", "TT", "I5"]:
        clevs = np.arange(-d, 1.1 * d, 0.1 * d)

        if varname == "PR":
            clevs = np.arange(-3, 3.5, 0.5)
        if varname == "TT":
            clevs = np.arange(-7, 8, 1)
        if varname == "I5":
            clevs = np.arange(-100, 110, 10)

    else:
        clevs = MaxNLocator(nbins=10, symmetric=True).tick_values(-d, d)
    cmap = cm.get_cmap("RdBu_r", len(clevs) - 1)

    fig = None
    fig_path = None
    if axes_list is None:
        fig_path = img_folder.joinpath("{}.png".format(varname))
        fig = plt.figure()

    nrows = 2
    ncols = 2
    gs = GridSpec(nrows, ncols=ncols + 1, width_ratios=[1, 1, 0.05])

    xx, yy = basemap_info.get_proj_xy()

    cs = None
    for i, season in enumerate(season_to_error_field):
        row = i // ncols
        col = i % ncols

        if axes_list is None:
            ax = fig.add_subplot(gs[row, col])
        else:
            ax = axes_list[i]

        basemap_info.draw_map_background(ax)

        cs = basemap_info.basemap.contourf(xx,
                                           yy,
                                           season_to_error_field[season][:],
                                           ax=ax,
                                           cmap=cmap,
                                           levels=clevs,
                                           extend="both")
        basemap_info.basemap.drawcoastlines(ax=ax, linewidth=0.3)
        ax.set_title(season)
        if i == 0:
            ax.set_ylabel(
                infovar.get_long_display_label_for_var(varname=varname))
        # basemap_info.basemap.colorbar(cs)

        if basemap_info.should_draw_basin_boundaries:
            basemap_info.basemap.readshapefile(BASIN_BOUNDARIES_SHP[:-4],
                                               "basin",
                                               ax=ax)

        # Hide snow plots for summer
        if varname in ["I5"] and season.lower() in ["summer"]:
            ax.set_visible(False)

        # Plot a colorbar for each subplot if required.
        if hasattr(basemap_info, "draw_colorbar_for_each_subplot"):
            if basemap_info.draw_colorbar_for_each_subplot:
                cb = basemap_info.basemap.colorbar(cs, ax=ax)
                cb.ax.set_title(infovar.get_units(var_name=varname))

    cax = fig.add_subplot(gs[:, -1]) if axes_list is None else axes_list[-1]

    # Add the colorbar if there are additional axes supplied for it
    if len(axes_list) > len(season_to_error_field):
        cax.set_title(infovar.get_units(var_name=varname))
        plt.colorbar(cs, cax=cax)

    if axes_list is None:
        with fig_path.open("wb") as figfile:
            fig.savefig(figfile, format="png", bbox_inches="tight")

        plt.close(fig)

    return cs