jiahuimbzuai/CoQuIR huggingface dataset:
//  [python]
def get_animated_difference_signal(x, y, title, onsets):
    x = np.array(x)
    y = np.array(y)

    y_o = np.zeros((len(y)))

    l = 0
    for n in range(len(y)):
        if onsets[l] == x[n]:
            y_o[n] = 15
            l = l + 1
            if l == 6:
                break

    x = x / 200

    signal = pd.DataFrame(y, x)
    signal.columns = {title}

    signal_o = pd.DataFrame(y_o, x)
    signal_o.columns = {title}

    Writer = animation.writers['ffmpeg']
    writer = Writer(fps=20, metadata=dict(artist='Me'), bitrate=2000)
    fig = plt.figure(figsize=(10, 6))
    plt.xlim(np.min(x), np.max(x))
    plt.ylim(np.min(y), np.max(y))
    plt.axhline(6)
    plt.xlabel('time(s)', fontsize=20)
    plt.ylabel('$d(n)$', fontsize=20)
    plt.xticks(np.arange(0, 58, 5))

    def animate(i):
        data = signal.iloc[:int(i + 1)]
        p = plt.plot(data.index, data[title], color="b")
        plt.setp(p, linewidth=1)
        p.tick_params(labelsize=15)

        data_o = signal_o.iloc[:int(i + 1)]
        q = plt.vlines(x=data_o.index, ymin=0, ymax=data_o[title], colors="r", linestyles="--")
        plt.setp(q, linewidth=1)

    ani = animation.FuncAnimation(fig, animate, frames=58 * 200, repeat=True)

    plt.show()
//  [python]
def get_animated_difference_signal(x, y, title, onsets):
    x = np.array(x)
    y = np.array(y)

    y_o = np.zeros((len(y)))

    l = 0
    for n in range(len(y)):
        if onsets[l] == x[n]:
            y_o[n] = 15
            l = l + 1
            if l == 6:
                break

    x = x / 200

    signal = pd.DataFrame(y, x)
    signal.columns = {title}

    signal_o = pd.DataFrame(y_o, x)
    signal_o.columns = {title}

    Writer = animation.writers['ffmpeg']
    writer = Writer(fps=20, metadata=dict(artist='Me'), bitrate=2000)
    fig = plt.figure(figsize=(10, 6))
    plt.xlim(np.min(x), np.max(x))
    plt.ylim(np.min(y), np.max(y))
    plt.axhline(6)
    plt.xlabel('time(s)', fontsize=20)
    plt.ylabel('$d(n)$', fontsize=20)
    plt.xticks(np.arange(0, 58, 5))

    def animate(i):
        data = signal.iloc[:int(i + 1)]
        p = sns.lineplot(x=data.index, y=data[title], data=data, color="b")
        p.tick_params(labelsize=15)
        plt.setp(p.lines, linewidth=1)

        data_o = signal_o.iloc[:int(i + 1)]
        q = plt.vlines(x=data_o.index, ymin=0, ymax=data_o[title], colors="r", linestyles="--")
        plt.setp(q, linewidth=1)

    ani = animation.FuncAnimation(fig, animate, frames=58 * 200, repeat=True)

    plt.show()
//  [python]
def plot(name: str, t_step: int, ax=None):
    s.lineplot(
        data=DATA[t_step], x='x', y=name,
        color=VARS[name][2], linewidth=1, alpha=0.8,
        ax=ax)
    
    ax.set_xlim(PLOTLIMITS['x'][0],  PLOTLIMITS['x'][1])
    ax.set_ylim(PLOTLIMITS[name][0], PLOTLIMITS[name][1])
//  [python]
def plot(name: str, t_step: int, ax=None):
    sns.lineplot(
        data=DATA[t_step], x='x', y=name,
        color=VARS[name][2], linewidth=1, alpha=0.8,
        ax=ax)
    
    ax.set_xlim(PLOTLIMITS['x'][0],  PLOTLIMITS['x'][1])
    ax.set_ylim(PLOTLIMITS[name][0], PLOTLIMITS[name][1])
//  [python]
sns.set(font_scale=1.0, style='ticks', palette='summer') 
f, axes = plt.subplots(1, 2, figsize=(12, 4.5))

x = metrics_result.index
[y1, y2, y3, y4] = [metrics_result[i] for i in metrics_result.columns]

sns.pointplot(x, y1, ax=axes[0], color='navy', linestyle='--', label='Train AUC')
//  [python]
sns.set(font_scale=1.0, style='ticks', palette='summer') 
f, axes = plt.subplots(1, 2, figsize=(12, 4.5))

x = metrics_result.index
[y1, y2, y3, y4] = [metrics_result[i] for i in metrics_result.columns]

sns.lineplot(x, y1, ax=axes[0], color='navy', linestyle='--', label='Train AUC')
//  [python]
def plot_losses(local_losses=None, batch_losses=None, globe_losses=None, save=False, path=IMGS_DIR, file='losses.png'):
    if not os.path.isdir(path):
        os.makedirs(path)

    s = 1
    fig = plt.figure(figsize=(14/s, 6/s), dpi=300)
    cur = 0
    sub = sum([1 for e in [local_losses, batch_losses, globe_losses] if e is not None])
    
    if local_losses is not None:
        cur += 1
        ax = fig.add_subplot(1,sub,cur)

        df_lloss = pd.DataFrame(local_losses)

        ax.set_title('Loss per step')
        plt.plot(df_lloss)
        
    
    if batch_losses is not None:
        cur += 1        
        ax = fig.add_subplot(1,sub,cur)
        
        df_bloss = pd.DataFrame(batch_losses, columns=['Batch Loss'])        
        
        ax.set_title('Batch loss per batch')        
        plt.plot(df_bloss, lw=1)
        
    if globe_losses is not None:
        cur += 1
        ax = fig.add_subplot(1,sub,cur)
        
        df_gloss = pd.DataFrame(globe_losses, columns=['Global Loss'])        

        ax.set_title('Global Loss per batch');
        plt.plot(df_gloss)
    
    if save:
        # NOTE: savefig complains image is too large but saves it anyway. 
        try:
            fig.savefig(os.path.expanduser(os.path.join(path, file)))
        except ValueError:
            pass
    plt.close()
    return fig
//  [python]
def plot_losses(local_losses=None, batch_losses=None, globe_losses=None, save=False, path=IMGS_DIR, file='losses.png'):
    if not os.path.isdir(path):
        os.makedirs(path)

    s = 1
    fig = plt.figure(figsize=(14/s, 6/s), dpi=300)
    cur = 0
    sub = sum([1 for e in [local_losses, batch_losses, globe_losses] if e is not None])
    
    if local_losses is not None:
        cur += 1
        ax = fig.add_subplot(1,sub,cur)

        df_lloss = pd.DataFrame(local_losses)

        ax.set_title('Loss per step')
        sns.lineplot(data=df_lloss, ax=ax)
        
    
    if batch_losses is not None:
        cur += 1        
        ax = fig.add_subplot(1,sub,cur)
        
        df_bloss = pd.DataFrame(batch_losses, columns=['Batch Loss'])        
        
        ax.set_title('Batch loss per batch')        
        sns.lineplot(data=df_bloss, lw=1, ax=ax)
        
    if globe_losses is not None:
        cur += 1
        ax = fig.add_subplot(1,sub,cur)
        
        df_gloss = pd.DataFrame(globe_losses, columns=['Global Loss'])        

        ax.set_title('Global Loss per batch');
        sns.lineplot(data=df_gloss, ax=ax)
    
    if save:
        # NOTE: savefig complains image is too large but saves it anyway. 
        try:
            fig.savefig(os.path.expanduser(os.path.join(path, file)))
        except ValueError:
            pass
    plt.close()
    return fig
//  [python]
def plot(self, ax=None):
        self._validate_plot_params()
        # Use seaborn lineplot with style='Train' and hue='View' to plot the train and test data
        # Reshape the data so that each row has a 'value', 'view index', and 'train' column
        data = pd.DataFrame(self.explained_variance_train, index=self.view_labels).T
        # Give the index a name so that it can be used as a column later
        data.index.name = "Latent dimension"
        # Melt the dataframe so that each row has a 'value', 'view index', and 'train' column
        data = data.reset_index().melt(
            id_vars="Latent dimension", value_vars=self.view_labels
        )
        data.columns = ["Latent dimension", "View", "value"]
        data["Mode"] = "Train"  # Add a column indicating train data
        if self.explained_variance_test is not None:
            data_test = pd.DataFrame(
                self.explained_variance_test, index=self.view_labels
            ).T
            # Give the index a name so that it can be used as a column later
            data_test.index.name = "Latent dimension"
            # Melt the dataframe so that each row has a 'value', 'view index', and 'train' column
            data_test = data_test.reset_index().melt(
                id_vars="Latent dimension", value_vars=self.view_labels
            )
            data_test.columns = ["Latent dimension", "View", "value"]
            data_test["Mode"] = "Test"  # Add a column indicating train data
            data = pd.concat([data, data_test])  # Concatenate the two dataframes
        if ax is None:
            fig, ax = plt.subplots(figsize=(10, 5))
        else:
            fig = ax.get_figure()
        sns.pointplot(
            data=data,
            x="Latent dimension",
            y="value",
            hue="View",
            style="Mode",
            marker="o",
            ax=ax,
        )
        # Set x-ticks to integers
        ax.xaxis.set_major_locator(plt.MaxNLocator(integer=True))
        ax.set_xlabel("Latent dimension")
        if self.ratio:
            ax.set_ylabel("Explained Variance %")
            ax.yaxis.set_major_formatter(mtick.PercentFormatter(1.0))
        else:
            ax.set_ylabel("Explained Variance")
        ax.set_title("Explained Variance")
        plt.tight_layout()
        self.figure_ = fig
        return self
//  [python]
def plot(self, ax=None):
        self._validate_plot_params()
        # Use seaborn lineplot with style='Train' and hue='View' to plot the train and test data
        # Reshape the data so that each row has a 'value', 'view index', and 'train' column
        data = pd.DataFrame(self.explained_variance_train, index=self.view_labels).T
        # Give the index a name so that it can be used as a column later
        data.index.name = "Latent dimension"
        # Melt the dataframe so that each row has a 'value', 'view index', and 'train' column
        data = data.reset_index().melt(
            id_vars="Latent dimension", value_vars=self.view_labels
        )
        data.columns = ["Latent dimension", "View", "value"]
        data["Mode"] = "Train"  # Add a column indicating train data
        if self.explained_variance_test is not None:
            data_test = pd.DataFrame(
                self.explained_variance_test, index=self.view_labels
            ).T
            # Give the index a name so that it can be used as a column later
            data_test.index.name = "Latent dimension"
            # Melt the dataframe so that each row has a 'value', 'view index', and 'train' column
            data_test = data_test.reset_index().melt(
                id_vars="Latent dimension", value_vars=self.view_labels
            )
            data_test.columns = ["Latent dimension", "View", "value"]
            data_test["Mode"] = "Test"  # Add a column indicating train data
            data = pd.concat([data, data_test])  # Concatenate the two dataframes
        if ax is None:
            fig, ax = plt.subplots(figsize=(10, 5))
        else:
            fig = ax.get_figure()
        sns.lineplot(
            data=data,
            x="Latent dimension",
            y="value",
            hue="View",
            style="Mode",
            marker="o",
            ax=ax,
        )
        # Set x-ticks to integers
        ax.xaxis.set_major_locator(plt.MaxNLocator(integer=True))
        ax.set_xlabel("Latent dimension")
        if self.ratio:
            ax.set_ylabel("Explained Variance %")
            ax.yaxis.set_major_formatter(mtick.PercentFormatter(1.0))
        else:
            ax.set_ylabel("Explained Variance")
        ax.set_title("Explained Variance")
        plt.tight_layout()
        self.figure_ = fig
        return self
//  [python]
def plot_sequence_match_effects(dataset: str, data_sub_dir: str, holdout: str, fig_ext: str):
    # load and label data for perfect matches
    data, data_nt = load_data(dataset=dataset, pm_only=True)
    data = label_and_filter_data(data, data_nt)
    assert data['guide_seq'].apply(len).nunique() == 1

    # load SHAP values for perfect matches
    exp_path = experiment_results_path(dataset, 'SHAP', data_sub_dir, holdout)
    try:
        df_shap = pd.read_pickle(os.path.join(exp_path, 'shap.pkl'))
    except FileNotFoundError:
        return None
    df_shap = df_shap[df_shap['guide_type'] == 'PM']

    # get pearson and shap values
    df = sequence_pearson_and_shap(data, df_shap, mode='matches')

    # print agreement between Pearson and SHAP values
    print('Agreement between Pearson and SHAP for matches = {:.4f}'.format(pearsonr(df['Pearson'], df['SHAP'])[0]))

    # plot results
    df.reset_index(inplace=True)
    guide_len = df['Position'].max()
    values = ('Pearson', 'SHAP')
    fig, ax = plt.subplots(ncols=len(values), figsize=(len(values) * 5, 5))
    fig.suptitle('Pearson and mean SHAP values for complementary guide-target base pairs')
    for i, value in enumerate(values):
        ax[i].plot(np.arange(1, guide_len + 1), np.zeros(guide_len), color='black', linestyle='--')
        sns.pointplot(x='Position', y=value, hue='Guide-Target', data=df, ax=ax[i])
        ax[i].legend(title='Guide-Target', bbox_to_anchor=(1, 1), loc='upper left')
        plt.tight_layout()

    # save figure
    fig_path = figure_save_path(dataset, 'SHAP', data_sub_dir, holdout)
    save_fig(fig, fig_path, 'seq-match-effects', fig_ext)
//  [python]
def plot_sequence_match_effects(dataset: str, data_sub_dir: str, holdout: str, fig_ext: str):
    # load and label data for perfect matches
    data, data_nt = load_data(dataset=dataset, pm_only=True)
    data = label_and_filter_data(data, data_nt)
    assert data['guide_seq'].apply(len).nunique() == 1

    # load SHAP values for perfect matches
    exp_path = experiment_results_path(dataset, 'SHAP', data_sub_dir, holdout)
    try:
        df_shap = pd.read_pickle(os.path.join(exp_path, 'shap.pkl'))
    except FileNotFoundError:
        return None
    df_shap = df_shap[df_shap['guide_type'] == 'PM']

    # get pearson and shap values
    df = sequence_pearson_and_shap(data, df_shap, mode='matches')

    # print agreement between Pearson and SHAP values
    print('Agreement between Pearson and SHAP for matches = {:.4f}'.format(pearsonr(df['Pearson'], df['SHAP'])[0]))

    # plot results
    df.reset_index(inplace=True)
    guide_len = df['Position'].max()
    values = ('Pearson', 'SHAP')
    fig, ax = plt.subplots(ncols=len(values), figsize=(len(values) * 5, 5))
    fig.suptitle('Pearson and mean SHAP values for complementary guide-target base pairs')
    for i, value in enumerate(values):
        ax[i].plot(np.arange(1, guide_len + 1), np.zeros(guide_len), color='black', linestyle='--')
        sns.lineplot(x='Position', y=value, hue='Guide-Target', data=df, ax=ax[i])
        ax[i].legend(title='Guide-Target', bbox_to_anchor=(1, 1), loc='upper left')
        plt.tight_layout()

    # save figure
    fig_path = figure_save_path(dataset, 'SHAP', data_sub_dir, holdout)
    save_fig(fig, fig_path, 'seq-match-effects', fig_ext)
//  [python]
def results(filename):
    start = "2016-06-01"
    end = "2018-01-01"

    df = pd.read_csv(filename)
    df = df.groupby(df.index // 3).agg({'timestamp': np.min,
                                        'risk_bal': np.min,
                                        'risk_intr': np.min,
                                        'profit_eur': np.sum,
                                        'imbalance_kwh': np.sum,
                                        'lost_rentals_eur': np.sum,
                                        'charged_vpp_kwh': np.sum,
                                        })

    df["timestamp"] = df["timestamp"].apply(lambda x : datetime.fromtimestamp(x))
    df = df.set_index("timestamp")
    df = df[start:end]
    
    print(df.describe())

    grouper = "week"
    df[grouper] = df.index.week
    
    # sns.lineplot(x="week", y="profit_eur", data=df);
    plt.plot(df[grouper], df["risk_bal"], label="Balancing");
    plt.plot(df[grouper], df["risk_intr"], label="Intraday");

    print("Profit {:d} EUR".format(int(df["profit_eur"].sum())))
    print("Imbalance {} kWh".format(df["imbalance_kwh"].sum()))
    print("Lost rentals {} EUR".format(df["lost_rentals_eur"].sum()))
    print("Mean Risk Balancing={:.3}, Intraday={:.3}".format(df["risk_bal"].mean(), df["risk_intr"].mean()))
//  [python]
def results(filename):
    start = "2016-06-01"
    end = "2018-01-01"

    df = pd.read_csv(filename)
    df = df.groupby(df.index // 3).agg({'timestamp': np.min,
                                        'risk_bal': np.min,
                                        'risk_intr': np.min,
                                        'profit_eur': np.sum,
                                        'imbalance_kwh': np.sum,
                                        'lost_rentals_eur': np.sum,
                                        'charged_vpp_kwh': np.sum,
                                        })

    df["timestamp"] = df["timestamp"].apply(lambda x : datetime.fromtimestamp(x))
    df = df.set_index("timestamp")
    df = df[start:end]
    
    print(df.describe())

    grouper = "week"
    df[grouper] = df.index.week
    
    # sns.lineplot(x="week", y="profit_eur", data=df);
    sns.lineplot(x=grouper, y="risk_bal", data=df, label="Balancing");
    sns.lineplot(x=grouper, y="risk_intr", data=df, label="Intraday");

    print("Profit {:d} EUR".format(int(df["profit_eur"].sum())))
    print("Imbalance {} kWh".format(df["imbalance_kwh"].sum()))
    print("Lost rentals {} EUR".format(df["lost_rentals_eur"].sum()))
    print("Mean Risk Balancing={:.3}, Intraday={:.3}".format(df["risk_bal"].mean(), df["risk_intr"].mean()))
//  [python]
fig, ax = plt.subplots(figsize=(10, 10), dpi=49)
ax.set_facecolor('#518792')
ax.xaxis.set_tick_params(width=5, color='black')
ax.yaxis.set_tick_params(width=5, color='black')
sns.lineplot(x=range(100), y=probabilitati, color='black')
//  [python]
def lineplot(**kwargs):
    """Call to seaborn lineplot"""

    def plot(data):
        return s.lineplot(data=data, ax=newax(), **kwargs)

    return plot
//  [python]
def lineplot(**kwargs):
    """Call to seaborn lineplot"""

    def plot(data):
        return sns.lineplot(data=data, ax=newax(), **kwargs)

    return plot
//  [python]
def make_caltech_fig(x_metric='d'):
    """x_metric should be in {'d', 'secs', 'muls'}"""

    fig, ax = plt.subplots(1, 1, figsize=(6, 6))
    df = pd.read_csv(RESULTS_DIR / 'caltech.csv')
    df = _clean_results_df(df, default_D=27)

    sb.tsplot(data=df, time=x_metric, unit='Method', value='Log10(MSE)',
                condition='Method', ax=ax)

    ax.set_ylabel('Log10(MSE + 1e-10)')
    if x_metric == 'd':
        ax.set_title('Caltech: Sketch Size vs Log Squared Error')
        ax.set_xlabel('Log2(Sketch Size)')
    elif x_metric == 'secs':
        ax.set_title('Caltech: Computation Time vs Log Squared Error')
        ax.set_xlabel('Time (s)')
    elif x_metric == 'muls':
        ax.set_title('Caltech: # of Multiplies vs Log Squared Error')
        ax.set_xlabel('Log10(# of Multiplies)')
    plt.tight_layout()
    plt.subplots_adjust(top=.92, bottom=.2)
    save_fig('caltech_{}'.format(x_metric))
//  [python]
def make_caltech_fig(x_metric='d'):
    """x_metric should be in {'d', 'secs', 'muls'}"""

    fig, ax = plt.subplots(1, 1, figsize=(6, 6))
    df = pd.read_csv(RESULTS_DIR / 'caltech.csv')
    df = _clean_results_df(df, default_D=27)

    sb.lineplot(data=df, hue='Method', x=x_metric, y='Log10(MSE)',
                style='Method', markers=True, dashes=False, ax=ax)

    ax.set_ylabel('Log10(MSE + 1e-10)')
    if x_metric == 'd':
        ax.set_title('Caltech: Sketch Size vs Log Squared Error')
        ax.set_xlabel('Log2(Sketch Size)')
    elif x_metric == 'secs':
        ax.set_title('Caltech: Computation Time vs Log Squared Error')
        ax.set_xlabel('Time (s)')
    elif x_metric == 'muls':
        ax.set_title('Caltech: # of Multiplies vs Log Squared Error')
        ax.set_xlabel('Log10(# of Multiplies)')
    plt.tight_layout()
    plt.subplots_adjust(top=.92, bottom=.2)
    save_fig('caltech_{}'.format(x_metric))
//  [python]
def fieldseries(df,fname):
	assert( isinstance(df, pd.DataFrame) )

	sns.set_style(style="whitegrid")
	sns.set(font_scale=1.1)
	f, ((ax1,ax2),(ax3,ax4)) = plot.subplots(nrows=2, ncols=2, sharex=False, sharey=False)

	df=df.query("Setname=='5cm' or Setname=='10cm' or Setname=='15cm' or Setname=='20cm'")
	# df.to_csv(fname+".tussendump.csv")

	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='X'"), style="Generator", ax=ax1, lw=1)
	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Y'"), style="Generator", ax=ax2, lw=1)
	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='ratY'"), ax=ax3, lw=1)
	# sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='relY'"), style="Generator", ax=ax3, lw=1)
	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Z'"), style="Generator", ax=ax4, lw=1)

	ax1.set_xlim(-170,170)
	# ax2.set_xlim(-170,170)
	ax3.set_xlim(-170,170)
	ax4.set_xlim(-170,170)

	# ax3.set_ylim(-.25,0.5)
	ax3.set_ylim(0,2)

	ax1.set_title("X (BLD:Jaw)")
	ax2.set_title("Y")
	# ax3.set_title("reldiff X") #relY is relative y over X axis
	ax3.set_title("ratio X") #relY is relative y over X axis
	ax4.set_title("Z (BLD:MLC)")

	ax3.set_ylabel("Relative Dose")
	ax3.set_ylabel("Dose Ratio")

	ax1.legend(title="Fieldsize", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax2.legend_.remove()#.legend().set_title('Fieldsize')
	ax3.legend(title="Fieldsize", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax4.legend_.remove()#.legend().set_title('Fieldsize')

	f.subplots_adjust(hspace=.6,wspace=.5)
	f.savefig(fname+'.pdf', bbox_inches='tight')
	f.savefig(fname+'.png', bbox_inches='tight',dpi=300)
//  [python]
def fieldseries(df,fname):
	assert( isinstance(df, pd.DataFrame) )

	sns.set_style(style="whitegrid")
	sns.set(font_scale=1.1)
	f, ((ax1,ax2),(ax3,ax4)) = plot.subplots(nrows=2, ncols=2, sharex=False, sharey=False)

	df=df.query("Setname=='5cm' or Setname=='10cm' or Setname=='15cm' or Setname=='20cm'")
	# df.to_csv(fname+".tussendump.csv")

	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='X'"), style="Generator", ax=ax1, lw=1)
	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Y'"), style="Generator", ax=ax2, lw=1)
	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='ratY'"), ax=ax3, lw=1)
	# sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='relY'"), style="Generator", ax=ax3, lw=1)
	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Z'"), style="Generator", ax=ax4, lw=1)

	ax1.set_xlim(-170,170)
	# ax2.set_xlim(-170,170)
	ax3.set_xlim(-170,170)
	ax4.set_xlim(-170,170)

	# ax3.set_ylim(-.25,0.5)
	ax3.set_ylim(0,2)

	ax1.set_title("X (BLD:Jaw)")
	ax2.set_title("Y")
	# ax3.set_title("reldiff X") #relY is relative y over X axis
	ax3.set_title("ratio X") #relY is relative y over X axis
	ax4.set_title("Z (BLD:MLC)")

	ax3.set_ylabel("Relative Dose")
	ax3.set_ylabel("Dose Ratio")

	ax1.legend(title="Fieldsize", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax2.legend_.remove()#.legend().set_title('Fieldsize')
	ax3.legend(title="Fieldsize", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax4.legend_.remove()#.legend().set_title('Fieldsize')

	f.subplots_adjust(hspace=.6,wspace=.5)
	f.savefig(fname+'.pdf', bbox_inches='tight')
	f.savefig(fname+'.png', bbox_inches='tight',dpi=300)
//  [python]
def fieldseries_blok(df,fname):
	assert( isinstance(df, pd.DataFrame) )

	sns.set_style(style="whitegrid")
	f, ((ax1,ax2),(ax3,ax4)) = plot.subplots(nrows=2, ncols=2, sharex=False, sharey=False)

	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='X'"), ax=ax1, lw=1)
	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Y'"), ax=ax2, lw=1)
	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='ratY'"), ax=ax3, lw=1)
	# sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='relY'"), ax=ax3, lw=1)
	sns.pointplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Z'"), ax=ax4, lw=1)

	ax1.set_xlim(-70,70)
	# ax2.set_xlim(-70,70)
	ax3.set_xlim(-70,70)
	ax4.set_xlim(-70,70)

	# ax3.set_ylim(-.25,0.5)
	ax3.set_ylim(0,2)

	ax1.set_title("X (BLD:Jaw)")
	ax2.set_title("Y")
	# ax3.set_title("reldiff X") #relY is relative y over X axis
	ax3.set_title("ratio X") #relY is relative y over X axis
	ax4.set_title("Z (BLD:MLC)")

	# ax3.set_ylabel("Relative Dose")
	# ax3.set_ylabel("Dose Ratio")

	ax1.legend(title="Fieldsize", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax2.legend_.remove()#.legend().set_title('Fieldsize')
	ax3.legend(title="Relative to Pinnacle", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax4.legend_.remove()#.legend().set_title('Fieldsize')

	f.subplots_adjust(hspace=.6,wspace=.5)
	f.savefig(fname+'.pdf', bbox_inches='tight')
	f.savefig(fname+'.png', bbox_inches='tight',dpi=300)
//  [python]
def fieldseries_blok(df,fname):
	assert( isinstance(df, pd.DataFrame) )

	sns.set_style(style="whitegrid")
	f, ((ax1,ax2),(ax3,ax4)) = plot.subplots(nrows=2, ncols=2, sharex=False, sharey=False)

	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='X'"), ax=ax1, lw=1)
	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Y'"), ax=ax2, lw=1)
	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='ratY'"), ax=ax3, lw=1)
	# sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='relY'"), ax=ax3, lw=1)
	sns.lineplot(x="Distance to isoc [mm]", y="Dose [cGy]", hue="Setname", data=df.query("Axis=='Z'"), ax=ax4, lw=1)

	ax1.set_xlim(-70,70)
	# ax2.set_xlim(-70,70)
	ax3.set_xlim(-70,70)
	ax4.set_xlim(-70,70)

	# ax3.set_ylim(-.25,0.5)
	ax3.set_ylim(0,2)

	ax1.set_title("X (BLD:Jaw)")
	ax2.set_title("Y")
	# ax3.set_title("reldiff X") #relY is relative y over X axis
	ax3.set_title("ratio X") #relY is relative y over X axis
	ax4.set_title("Z (BLD:MLC)")

	# ax3.set_ylabel("Relative Dose")
	# ax3.set_ylabel("Dose Ratio")

	ax1.legend(title="Fieldsize", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax2.legend_.remove()#.legend().set_title('Fieldsize')
	ax3.legend(title="Relative to Pinnacle", loc='upper right', bbox_to_anchor=(1.4, 1.),frameon=False)
	ax4.legend_.remove()#.legend().set_title('Fieldsize')

	f.subplots_adjust(hspace=.6,wspace=.5)
	f.savefig(fname+'.pdf', bbox_inches='tight')
	f.savefig(fname+'.png', bbox_inches='tight',dpi=300)
//  [python]
def visualize_result(df, filename):
	ax = sns.tsplot(data=df, err_style=None)
	ax.figure.savefig(filename, dpi=250)
	plt.close()
//  [python]
def visualize_result(df, filename):
	ax = sns.lineplot(data=df,  dashes=False)
	ax.figure.savefig(filename, dpi=250)
	plt.close()
//  [python]
def plot(lstms2s, transformer, convs2s, source_file_opennmt, target_file_opennmt,
         source_file_fairseq, target_file_fairseq,
         output_filename, keep_ylabels=False, mode="depth"):
    x_lstms2s, y_lstms2s = load_results(lstms2s, source_file_opennmt, target_file_opennmt, mode)
    x_transf, y_transf = load_results(transformer, source_file_opennmt, target_file_opennmt, mode)
    x_convs2s, y_convs2s = load_results(convs2s, source_file_fairseq, target_file_fairseq, mode)

    # Figure size
    if keep_ylabels:
        sns.set(rc={'figure.figsize': (6, 3.5), "lines.linewidth": 3})
    else:
        sns.set(rc={'figure.figsize': (6, 3.5), "lines.linewidth": 3})

    blues = list(sns.color_palette("Blues", 10))
    ax = sns.plt.plot(x_lstms2s, y_lstms2s, color=blues[3], marker=".",
                      label="LSTMS2S", markeredgecolor='none')
    ax[0].set_linestyle("--")
    ax = sns.plt.plot(x_convs2s, y_convs2s, color=blues[6], marker=".",
                      ax=ax, label="ConvS2S", markeredgecolor='none')
    ax[1].set_linestyle(":")
    ax = sns.plt.plot(x_transf, y_transf, color=blues[9], marker=".",
                      ax=ax, label="Transformer", markeredgecolor='none')

    if mode == "depth":
        plt.xlim(min(x_lstms2s), 14)
        plt.xticks(list(range(min(x_lstms2s), 14 + 1, 1)))
    elif mode == "number of functions":
        plt.xlim(min(x_lstms2s), 15)
        plt.xticks(list(range(min(x_lstms2s), 15 + 1, 1)))
    else:
        plt.xticks(list(range(5, 50 + 1, 5)))
        plt.xlim(min(x_lstms2s), 50)
        print(max(x_lstms2s))
    plt.ylim(-0.01, 1.01)

    # Share axes for subplots displayed next to each other in the paper, but keep grid
    ax.grid(True)
    ax.set_xlabel(mode, fontsize=20)
    ax.tick_params(labelsize=20)
    if keep_ylabels:
        plt.yticks(list([x / 10 for x in range(0, 12, 2)]))
        ax.set_ylabel("accuracy", fontsize=20)
        plt.legend(fontsize=15)
    else:
        plt.yticks(list([x / 10 for x in range(0, 12, 2)]))
        ax.yaxis.set_ticklabels([])
        ax.get_legend().set_visible(False)

    ax.tick_params(labelsize=20)
    plt.savefig(output_filename, bbox_inches='tight')
    plt.clf()
//  [python]
def plot(lstms2s, transformer, convs2s, source_file_opennmt, target_file_opennmt,
         source_file_fairseq, target_file_fairseq,
         output_filename, keep_ylabels=False, mode="depth"):
    x_lstms2s, y_lstms2s = load_results(lstms2s, source_file_opennmt, target_file_opennmt, mode)
    x_transf, y_transf = load_results(transformer, source_file_opennmt, target_file_opennmt, mode)
    x_convs2s, y_convs2s = load_results(convs2s, source_file_fairseq, target_file_fairseq, mode)

    # Figure size
    if keep_ylabels:
        sns.set(rc={'figure.figsize': (6, 3.5), "lines.linewidth": 3})
    else:
        sns.set(rc={'figure.figsize': (6, 3.5), "lines.linewidth": 3})

    blues = list(sns.color_palette("Blues", 10))
    ax = sns.lineplot(x=x_lstms2s, y=y_lstms2s, color=blues[3], marker=".",
                      label="LSTMS2S", markeredgecolor='none')
    ax.lines[0].set_linestyle("--")
    ax = sns.lineplot(x=x_convs2s, y=y_convs2s, color=blues[6], marker=".",
                      ax=ax, label="ConvS2S", markeredgecolor='none')
    ax.lines[1].set_linestyle(":")
    ax = sns.lineplot(x=x_transf, y=y_transf, color=blues[9], marker=".",
                      ax=ax, label="Transformer", markeredgecolor='none')

    if mode == "depth":
        plt.xlim(min(x_lstms2s), 14)
        plt.xticks(list(range(min(x_lstms2s), 14 + 1, 1)))
    elif mode == "number of functions":
        plt.xlim(min(x_lstms2s), 15)
        plt.xticks(list(range(min(x_lstms2s), 15 + 1, 1)))
    else:
        plt.xticks(list(range(5, 50 + 1, 5)))
        plt.xlim(min(x_lstms2s), 50)
        print(max(x_lstms2s))
    plt.ylim(-0.01, 1.01)

    # Share axes for subplots displayed next to each other in the paper, but keep grid
    ax.grid(True)
    ax.set_xlabel(mode, fontsize=20)
    ax.tick_params(labelsize=20)
    if keep_ylabels:
        plt.yticks(list([x / 10 for x in range(0, 12, 2)]))
        ax.set_ylabel("accuracy", fontsize=20)
        plt.legend(fontsize=15)
    else:
        plt.yticks(list([x / 10 for x in range(0, 12, 2)]))
        ax.yaxis.set_ticklabels([])
        ax.get_legend().set_visible(False)

    ax.tick_params(labelsize=20)
    plt.savefig(output_filename, bbox_inches='tight')
    plt.clf()
//  [python]
def generate_stats_graph():

    df = pd.read_csv(RESULT_FILE)
    
        
    fig, axes = plt.subplots(1, 2, figsize=(12, 5), sharey=False)
    
    #generate response time distribution
    kwargs = dict(element='step',shrink=.8, alpha=0.6, fill=True, legend=True) 
    ax = sns.histplot(ax=axes[0],data=df,**kwargs)
    #ax.set(xlim=(0.00,1.00)) #set the ylim boundary if auto option is not what you need
    ax.set_title('Response Time Distribution')
    ax.set_xlabel('Response Time (s)')
    ax.set_ylabel('Request Count')
    
    
    #generate percentile distribution       
    summary = np.round(df.describe(percentiles=[0.0, 0.1, 0.2,
                                                     0.3, 0.4, 0.5,
                                                     0.6, 0.7, 0.8,  
                                                     0.9, 0.95, 0.99, 1]),2) # add 1 in the percentile
    dropping = ['count', 'mean', 'std', 'min','max'] #remove metrics not needed for percentile graph
    
    for drop in dropping:
        summary = summary.drop(drop)
    ax = sns.pointplot(ax=axes[1],data=summary,dashes=False, legend=True)
    ax.legend(fontsize='medium')
    #ax.set(ylim=(0.0,1.0)) #set the ylim boundary if auto option is not what you need
    ax.set_title('Percentile Distribution')
    ax.set_xlabel('Percentile')
    ax.set_ylabel('Response Time (s)')
    
    fig.tight_layout(pad=1)
//  [python]
def generate_stats_graph():

    df = pd.read_csv(RESULT_FILE)
    
        
    fig, axes = plt.subplots(1, 2, figsize=(12, 5), sharey=False)
    
    #generate response time distribution
    kwargs = dict(element='step',shrink=.8, alpha=0.6, fill=True, legend=True) 
    ax = sns.histplot(ax=axes[0],data=df,**kwargs)
    #ax.set(xlim=(0.00,1.00)) #set the ylim boundary if auto option is not what you need
    ax.set_title('Response Time Distribution')
    ax.set_xlabel('Response Time (s)')
    ax.set_ylabel('Request Count')
    
    
    #generate percentile distribution       
    summary = np.round(df.describe(percentiles=[0.0, 0.1, 0.2,
                                                     0.3, 0.4, 0.5,
                                                     0.6, 0.7, 0.8,  
                                                     0.9, 0.95, 0.99, 1]),2) # add 1 in the percentile
    dropping = ['count', 'mean', 'std', 'min','max'] #remove metrics not needed for percentile graph
    
    for drop in dropping:
        summary = summary.drop(drop)
    ax = sns.lineplot(ax=axes[1],data=summary,dashes=False, legend=True)
    ax.legend(fontsize='medium')
    #ax.set(ylim=(0.0,1.0)) #set the ylim boundary if auto option is not what you need
    ax.set_title('Percentile Distribution')
    ax.set_xlabel('Percentile')
    ax.set_ylabel('Response Time (s)')
    
    fig.tight_layout(pad=1)
//  [python]
def get_line_chart(result: QueryResult) -> Optional[str]:
    """
    Return a line chart in SVG format if the result table adheres to the expected format.

    A line chart is rendered if
    * there is at least on row of in the result table
    * there is at least one numeric column (the first column (with index 0) does not count)

    The first column is used as x-axis labels.
    All other numeric columns represent a line on the chart.
    The name of the column is used as the name of the line in the legend.
    Not numeric columns (except the first on) are ignored.
    """
    if len(result.data) < 1:
        return None
    numeric_columns = [
        c for c in range(1, len(result.data[0]))
        if all([isinstance(col[c], (int, float)) or col[c] is None for col in result.data])
    ]
    if len(numeric_columns) < 1:
        return None
    labels = [row[0] for row in result.data]
    fig, ax = plt.subplots(figsize=(10, 3.8))
    for col_num in numeric_columns:
        plt.plot(labels, [row[col_num] for row in result.data], label=result.headers[col_num])
    ax.set_xlabel(result.headers[0])
    # Rotate x-axis labels by 20 degrees to reduce overlap
    for label in ax.get_xticklabels():
        label.set_rotation(20)
        label.set_ha("right")
    return get_svg(fig)
//  [python]
def get_line_chart(result: QueryResult) -> Optional[str]:
    """
    Return a line chart in SVG format if the result table adheres to the expected format.

    A line chart is rendered if
    * there is at least on row of in the result table
    * there is at least one numeric column (the first column (with index 0) does not count)

    The first column is used as x-axis labels.
    All other numeric columns represent a line on the chart.
    The name of the column is used as the name of the line in the legend.
    Not numeric columns (except the first on) are ignored.
    """
    if len(result.data) < 1:
        return None
    numeric_columns = [
        c for c in range(1, len(result.data[0]))
        if all([isinstance(col[c], (int, float)) or col[c] is None for col in result.data])
    ]
    if len(numeric_columns) < 1:
        return None
    labels = [row[0] for row in result.data]
    fig, ax = plt.subplots(figsize=(10, 3.8))
    for col_num in numeric_columns:
        sns.lineplot(ax=ax,
                     x=labels,
                     y=[row[col_num] for row in result.data],
                     label=result.headers[col_num])
    ax.set_xlabel(result.headers[0])
    # Rotate x-axis labels by 20 degrees to reduce overlap
    for label in ax.get_xticklabels():
        label.set_rotation(20)
        label.set_ha("right")
    return get_svg(fig)
//  [python]
def plot_mbias(mtables, out_dir, PE=True):
    # load and arange tables
    assert len(mtables) == 2
    # make sure the first table is OB, and the second is OT
    if mtables[0].endswith('.OT.txt'):
        mtables.reverse()
    tables = [load_and_arange(m, l, PE) for l in ('meth', 'N') for m in mtables]

    # plot 4 figures
    fig, axes = plt.subplots(2, 2, figsize=(10,10))
    ((ax1, ax2), (ax3, ax4)) = axes
    hue = 'read' if PE else None
    for dd, ax in zip(tables, axes.flatten()):
        s.lineplot(data=dd, x='pos', y='value', hue=hue, ax=ax)

    # set titles
    ax1.set_title('OT / CTOT' if PE else 'OB')
    ax2.set_title('OB / CTOB' if PE else 'OT')
    name = op.basename(mtables[0])[:-13]
    fig.suptitle(f'{name}.bam: Methylation Bias')

    # set axes labels
    ax1.set_ylabel('Average methylation')
    ax3.set_ylabel('Number of observations')
    ax2.set_ylabel('')
    ax1.set_xlabel('')
    ax2.set_xlabel('')
    ax4.set_ylabel('')

    # set shared axes 
    ax3.sharey(ax4)
    ax1.sharey(ax2)
    ax3.sharex(ax1)
    ax4.sharex(ax2)

    # set axes limits
    for ax in axes.flatten():
        ax.set_xlim(0, None)
    for ax in axes[0]:
        ax.set_ylim(0, 1)
    outpath = op.join(out_dir, name) + '.pdf'
    eprint(f'[wt bam2pat] [mbias] dumped figure to {outpath}')
    plt.savefig(outpath)
//  [python]
def plot_mbias(mtables, out_dir, PE=True):
    # load and arange tables
    assert len(mtables) == 2
    # make sure the first table is OB, and the second is OT
    if mtables[0].endswith('.OT.txt'):
        mtables.reverse()
    tables = [load_and_arange(m, l, PE) for l in ('meth', 'N') for m in mtables]

    # plot 4 figures
    fig, axes = plt.subplots(2, 2, figsize=(10,10))
    ((ax1, ax2), (ax3, ax4)) = axes
    hue = 'read' if PE else None
    for dd, ax in zip(tables, axes.flatten()):
        sns.lineplot(data=dd, x='pos', y='value', hue=hue, ax=ax)

    # set titles
    ax1.set_title('OT / CTOT' if PE else 'OB')
    ax2.set_title('OB / CTOB' if PE else 'OT')
    name = op.basename(mtables[0])[:-13]
    fig.suptitle(f'{name}.bam: Methylation Bias')

    # set axes labels
    ax1.set_ylabel('Average methylation')
    ax3.set_ylabel('Number of observations')
    ax2.set_ylabel('')
    ax1.set_xlabel('')
    ax2.set_xlabel('')
    ax4.set_ylabel('')

    # set shared axes 
    ax3.sharey(ax4)
    ax1.sharey(ax2)
    ax3.sharex(ax1)
    ax4.sharex(ax2)

    # set axes limits
    for ax in axes.flatten():
        ax.set_xlim(0, None)
    for ax in axes[0]:
        ax.set_ylim(0, 1)
    outpath = op.join(out_dir, name) + '.pdf'
    eprint(f'[wt bam2pat] [mbias] dumped figure to {outpath}')
    plt.savefig(outpath)
//  [python]
def plot_strategies(args, extra_args):
    program_datas = get_strategy_data(args.input_dir)
    for program_name, program_data in program_datas.items():
        pruned_data = []
        name_map = {
            "depth_first": "DFS",
            "random_backtrack": "Random",
            "greedy_statement_search": "Coverage-Optimized",
        }
        for strategy, candidate_data in program_data.items():
            candidate_data = candidate_data.drop("Seed", axis=1)
            candidate_data["Strategy"] = name_map[strategy]
            candidate_data.Time = pd.to_numeric(candidate_data.Time)
            candidate_data = candidate_data.sort_values(by=["Time"])
            bins = np.arange(
                0,
                candidate_data.Time.max() + candidate_data.Time.max() / 1000,
                candidate_data.Time.max() / 1000,
            )
            candidate_data["Minutes"] = pd.cut(
                candidate_data.Time, bins.astype(np.int64), include_lowest=True
            ).map(attrgetter("right"))
            candidate_data.Minutes = pd.to_timedelta(candidate_data.Minutes, unit="nanoseconds")
            candidate_data.Minutes = candidate_data.Minutes / pd.Timedelta(minutes=1)
            candidate_data = candidate_data[candidate_data.Minutes <= 60]
            pruned_data.append(candidate_data)
        concat_data = pd.concat(pruned_data)
        ax = sns.tsplot(
            time="Minutes", value="Coverage", unit="Seed", condition="Strategy", data=concat_data
        )
        sns.move_legend(ax, "lower center", bbox_to_anchor=(0.5, 0.98), ncol=3, title=None)
        outdir = Path(args.out_dir).joinpath(f"{program_name}_strategy_coverage")
        plt.savefig(outdir.with_suffix(".png"), bbox_inches="tight")
        plt.savefig(outdir.with_suffix(".pdf"), bbox_inches="tight")
        plt.gcf().clear()
//  [python]
def plot_strategies(args, extra_args):
    program_datas = get_strategy_data(args.input_dir)
    for program_name, program_data in program_datas.items():
        pruned_data = []
        name_map = {
            "depth_first": "DFS",
            "random_backtrack": "Random",
            "greedy_statement_search": "Coverage-Optimized",
        }
        for strategy, candidate_data in program_data.items():
            candidate_data = candidate_data.drop("Seed", axis=1)
            candidate_data["Strategy"] = name_map[strategy]
            candidate_data.Time = pd.to_numeric(candidate_data.Time)
            candidate_data = candidate_data.sort_values(by=["Time"])
            bins = np.arange(
                0,
                candidate_data.Time.max() + candidate_data.Time.max() / 1000,
                candidate_data.Time.max() / 1000,
            )
            candidate_data["Minutes"] = pd.cut(
                candidate_data.Time, bins.astype(np.int64), include_lowest=True
            ).map(attrgetter("right"))
            candidate_data.Minutes = pd.to_timedelta(candidate_data.Minutes, unit="nanoseconds")
            candidate_data.Minutes = candidate_data.Minutes / pd.Timedelta(minutes=1)
            candidate_data = candidate_data[candidate_data.Minutes <= 60]
            pruned_data.append(candidate_data)
        concat_data = pd.concat(pruned_data)
        ax = sns.lineplot(
            x="Minutes", y="Coverage", hue="Strategy", data=concat_data, errorbar=None
        )
        sns.move_legend(ax, "lower center", bbox_to_anchor=(0.5, 0.98), ncol=3, title=None)
        outdir = Path(args.out_dir).joinpath(f"{program_name}_strategy_coverage")
        plt.savefig(outdir.with_suffix(".png"), bbox_inches="tight")
        plt.savefig(outdir.with_suffix(".pdf"), bbox_inches="tight")
        plt.gcf().clear()
//  [python]
def annotate(ax, xlabel=None, ylabel=None, title=None, xlim=None, ylim=None, legend='upper left') :
    if xlabel is not None : ax.set_xlabel(xlabel, fontsize=20)
    if ylabel is not None : ax.set_ylabel(ylabel, fontsize=20)
    ax.tick_params(labelsize=20)
    if title is not None : ax.set_title(title)
    if xlim is not None : ax.set_xlim(*xlim)
    if ylim is not None : ax.set_ylim(*ylim)

    set_square_aspect(ax)
    sns.despine(ax=ax)
    if legend is None and ax.get_legend() is not None : ax.get_legend().remove()
//  [python]
def annotate(ax, xlabel=None, ylabel=None, title=None, xlim=None, ylim=None, legend='upper left') :
    if xlabel is not None : ax.set_xlabel(xlabel, fontsize=20)
    if ylabel is not None : ax.set_ylabel(ylabel, fontsize=20)
    ax.tick_params(labelsize=20)
    if title is not None : ax.set_title(title)
    if xlim is not None : ax.set_xlim(*xlim)
    if ylim is not None : ax.set_ylim(*ylim)

    set_square_aspect(ax)
    sns.utils.despine(ax=ax)
    if legend is None and ax.get_legend() is not None : ax.get_legend().remove()
//  [python]
def plot_df(df, name='basement'):
    fig = plt.figure(figsize=(6,3.5))
    ax = sns.pointplot(x="threads", y="Speedup", hue="normals", palette='deep', data=df, legend=False)
    ax2 = ax.twinx()
    sns.pointplot(x="threads", y="Execution Time (ms)", ax=ax2, hue='normals',palette='muted', data=df, legend=False)
    for line in ax2.lines:
        line.set_linestyle('--')

    current_palette = sns.color_palette()
    from matplotlib.lines import Line2D
    custom_lines = [Line2D([0], [0], color=current_palette[i], lw=1) for i in range(4)]
    custom_lines_2 = [Line2D([0], [0], color='k', lw=1),
                    Line2D([0], [0], color='k', lw=1, dashes=[2,6])]

    ax.legend(custom_lines, ['1 DP', '2 DP', '3 DP', '4 DP'], loc='upper left', bbox_to_anchor=(0.1, 1,))
    ax2.legend(custom_lines_2, ['Speedup', 'Execution Time'], loc='upper left', bbox_to_anchor=(0.35, 1,))
    # ax.axis('equal')
    # ax.legend(custom_lines, ['1 DP', '2 DP', '3 DP', '4 DP'], loc='upper left', bbox_to_anchor=(0.4, 0.4,))
    # ax2.legend(custom_lines_2, ['Speedup', 'Execution Time'], loc='upper left', bbox_to_anchor=(0.6, 0.4,))
    fig.savefig(f'assets/scratch/{name}_speedup.pdf', bbox_inches='tight')
    plt.tight_layout()
    plt.show()
//  [python]
def plot_df(df, name='basement'):
    fig = plt.figure(figsize=(6,3.5))
    ax = sns.lineplot(x="threads", y="Speedup", hue="normals", palette='deep', data=df, legend=False)
    ax2 = ax.twinx()
    sns.lineplot(x="threads", y="Execution Time (ms)", ax=ax2, hue='normals',palette='muted', data=df, legend=False)
    for line in ax2.lines:
        line.set_linestyle('--')

    current_palette = sns.color_palette()
    from matplotlib.lines import Line2D
    custom_lines = [Line2D([0], [0], color=current_palette[i], lw=1) for i in range(4)]
    custom_lines_2 = [Line2D([0], [0], color='k', lw=1),
                    Line2D([0], [0], color='k', lw=1, dashes=[2,6])]

    ax.legend(custom_lines, ['1 DP', '2 DP', '3 DP', '4 DP'], loc='upper left', bbox_to_anchor=(0.1, 1,))
    ax2.legend(custom_lines_2, ['Speedup', 'Execution Time'], loc='upper left', bbox_to_anchor=(0.35, 1,))
    # ax.axis('equal')
    # ax.legend(custom_lines, ['1 DP', '2 DP', '3 DP', '4 DP'], loc='upper left', bbox_to_anchor=(0.4, 0.4,))
    # ax2.legend(custom_lines_2, ['Speedup', 'Execution Time'], loc='upper left', bbox_to_anchor=(0.6, 0.4,))
    fig.savefig(f'assets/scratch/{name}_speedup.pdf', bbox_inches='tight')
    plt.tight_layout()
    plt.show()
//  [python]
def visualize_log(files, keys, grouper=10):
    df_learning = pd.DataFrame()
    
    
    for file in files:
        with open(file, 'r') as f:
            data = json.load(f)
        if 'episode' not in data:
            raise ValueError('Log file "{}" does not contain the "episode" key.'.format(file))
        
        
        df = pd.DataFrame(data)
        df["mean_reward"] = df["episode_reward"] / df["nb_episode_steps"]
        df = df.groupby(df.index // grouper).mean()
        
        df["RL Algorithm"] = algo_names(file)
        df_learning = df_learning.append(df)
        
    
    df_learning = df_learning[df_learning["episode"] < 120]

    f, axs = plt.subplots(1, len(keys))
    for idx, key in enumerate(keys):
        g = sns.lineplot(x="episode", y=key, 
                     style="RL Algorithm", hue="RL Algorithm",
                     dashes=True, markers=True, ci=0,
                     data=df_learning, ax=axs[idx])
        
        ylabel=labels(key)
        g.set(xlabel='Episode', ylabel=ylabel)    
        
        #plt.xticks(np.arange(0, df_learning["episode"].max() + 1, 30));  
        
    plt.tight_layout()
    plt.tight_layout()
    sns.despine(offset=10)