Project: s41467-025-59099-1 | Function: calculate_RGR_metabolic_pool (python)

system: You are an expert Python programmer implementing algorithms from scientific papers.
Complete the masked function based on the algorithm description.
Follow Python best practices and maintain consistent code style.
Return **only** the complete Python function code.

user: Complete this Python function:

**DESCRIPTION:** Calculates relative growth rate (RGR) for metabolic pool analysis in CRISPR homing screen. Computes fitness differences between time points, normalizes by control genes, and applies variance propagation for statistical analysis of gene knockout effects.

**KEY TERMS:** {
  "rel_fitness": "conversion rate effects",
  "control_genes": "liver-specific control genes",
  "normalized_fit": "normalized conversion rate",
  "gaussianMeanAndVariance": "statistical normalization method"
}

**CONTEXT CODE:** import os
import sys
import pickle
import pandas as pd
import numpy as np
import matplotlib.backends.backend_pdf
import matplotlib.pyplot as plt
code=os.getcwd()
upLevel=code.replace('codes','') ####### we are going to upper level of code directory
sys.path.insert(0,upLevel+'data')
sys.path.insert(1, upLevel+'Figures')
# import statsmodels.stats.multitest as mtest  # Optional dependency, commented out for testing

# print(sys.path)
from special_fun_fertility  import preprocessing,filter_input_dropout,getNewIdfromPrevID,getCombined_mean_variance,gaussianMeanAndVariance
# input files which will be needed for analysis of cliare screen data

data_folder=sys.path[0]

## output folder where we will write figures and output files
out_folder=sys.path[1]

# ID conversion: we used plasmoDB to convert ID for P. Berghai
# Data loading moved to conditional block to avoid import errors during testing
try:
    prev_to_new=pickle.load(open(data_folder+'/prevTonew_PBANKA.pickle','rb'))
    db_df=pd.read_csv(data_folder+'/GenesByGeneModelChars_Summary.txt', sep='\t')
    db_df=db_df.fillna('NA')
    new_to_prev= dict((v,k) for k,v in prev_to_new.items())
except (FileNotFoundError, IOError):
    # Handle missing data files during testing
    prev_to_new = {}
    db_df = pd.DataFrame()
    new_to_prev = {}
## end of databse information






def calculate_RGR_metabolic_pool(m_df_d0,var_df_d0,m_df_d13,var_df_d13,control_genes):
    """
    Calculates relative growth rate (RGR) for metabolic pool analysis in CRISPR homing screen.

    This function implements the core statistical analysis for processing CRISPR homing screen data
    as described in the paper. It computes fitness differences between time points, normalizes by
    control genes, and applies variance propagation for statistical analysis of gene knockout effects
    in malaria transmission studies.

    Args:
        m_df_d0: Mean abundance dataframe at day 0 (log scale)
        var_df_d0: Variance dataframe at day 0
        m_df_d13: Mean abundance dataframe at day 13 (log scale)
        var_df_d13: Variance dataframe at day 13
        control_genes: List of control genes for normalization

    Returns:
        tuple: (normalized_fit, normalized_var)
            - normalized_fit: Normalized fitness scores relative to controls
            - normalized_var: Propagated variance after normalization

    Paper reference: "To find new gene functions in the oocyst, we looked for cases where the presence of gRNAs in the KO vector affected the conversion rate of asexual blood stages into oocysts. The oocyst conversion rate was first normalised to genes with liver-specific functions known to be dispensable at both blood and oocyst stage."

    Formula: RGR = (log2(day13) - log2(day0)) - control_mean, with variance propagation
    Implementation: Fitness calculation, control gene normalization, and statistical variance propagation
    """
    # MASKED: Relative growth rate calculation for CRISPR homing screen analysis
    raise NotImplementedError("This function is masked for testing purposes. The function calculates relative growth rate (RGR) for metabolic pool analysis in CRISPR homing screen, computing fitness differences between time points, normalizing by control genes, and applying variance propagation for statistical analysis of gene knockout effects.")



def plot_prop_rel_abun_nutrient(mean_df_d0,var_df_d0,mean_df_d13,var_df_d13,geneConv,plot_info):
    ''' We will plot genes sex-specific wise '''

    #### input ####
    # sex_list: sex_list[0]=mean and sex_list[1]=SD
    # geneConv: when we want to give name of gene
    # out_pdf: will generated pdf file
    ########
    out_pdf=plot_info['rel_file']
    # mf=plot_info['mf']
    day=plot_info['d']
    sex=plot_info['N']

    pdf = matplotlib.backends.backend_pdf.PdfPages(out_pdf)
    n=2
    genes=mean_df_d0.index;

    labels=[]
    for gene in genes:
        if gene in geneConv.keys():
            labels.append(geneConv[gene])
        else:
            labels.append(gene)

    ### get number of subplots

    num_subplots=2*len(genes) ### number of subplots

    l=len(genes)
    loops=int(l/(n*n))
    rem=l % (n*n)
    k=0

    per_page=num_subplots/16

    for loop in range(loops):
        fig = plt.figure(figsize=(15,15))
        for i in range(1,(n*n)+1):

            plt.subplot(n, n, i)
            x=[1,2]
            ### mf1 female
            y=[mean_df_d0.loc[genes[k],sex[0]+'_'+day[0]+'_NA'],mean_df_d13.loc[genes[k],sex[0]+'_'+day[1]+'_NA']]
            yerr=[var_df_d0.loc[genes[k],sex[0]+'_'+day[0]+'_NA'],var_df_d13.loc[genes[k],sex[0]+'_'+day[1]+'_NA']]
            plt.errorbar(x,y, yerr=yerr, fmt='r--')


            # ### mf1 male
            y=[mean_df_d0.loc[genes[k],sex[1]+'_'+day[0]+'_NA'],mean_df_d13.loc[genes[k],sex[1]+'_'+day[1]+'_NA']]
            yerr=[var_df_d0.loc[genes[k],sex[1]+'_'+day[0]+'_NA'],var_df_d13.loc[genes[k],sex[1]+'_'+day[1]+'_NA']]
            plt.errorbar(x,y, yerr=yerr, fmt='b--')


            plt.ylabel('log2 relative fitness')
            plt.title(labels[k])
            plt.legend((sex[0], sex[1]))
            plt.xticks([1, 1.5, 2],['day0', '', 'day14'],fontsize=15)

            plt.ylim(-18, 1)
            plt.grid(False)
            k=k+1
        pdf.savefig(fig)

    ## for the remaing one



    fig = plt.figure(figsize=(15,15))
    for i in range(1,rem+1):


Complete the function implementation replacing "raise NotImplementedError".