def init_lhood(self,space):
     from modules.lhood_dict import get_lhood_dict
     from modules.lhood_module import LHood
     self.lhood_name= space.xenon_lhood_name
     if self.lhood_name is not None:
         xenon_dict=get_lhood_dict()[self.lhood_name]
         self.lhood = LHood(None,xenon_dict)
         self.xenon_ssi_sn = xenon_dict["vars"][1]
     print self.xenon_ssi_sn
class KOhack_class(object):
    def __init__(self,mcf):
        self.mcf            = mcf
        self.hack_applied   = False
        self.df             = 1 #dimention factor, to go to cm-2 df=10^-36
        # the rest only gets initiated upon calling init_hack 
        self.mneu1_index    = None
        self.lhood          = None
        self.lhood_name     = None
        self.ssi_axis       = None
        self.xenon_ssi_sn   = None
        self.xenon_ssi_index= None
        self.KOssi_cen50_index      = None 
        self.KOssi_unc50_14_index   = None 
        self.KOssi_unc50_7_index    = None 
        self.mneu1_index            = None 

    def init_hack(self,space=None):
        self.ssi_axis = 'Y' # FIXME:this is now hard coded!!!
        self.hack_applied=True
        #if not space == None:
        if space is not None:
            self.init_lhood(space)
            self.init_var_indices()
            self.df=get_dimension_factor(space)
            self.bin_centres=get_bin_centres(space)

    def init_lhood(self,space):
        from modules.lhood_dict import get_lhood_dict
        from modules.lhood_module import LHood
        self.lhood_name= space.xenon_lhood_name
        if self.lhood_name is not None:
            xenon_dict=get_lhood_dict()[self.lhood_name]
            self.lhood = LHood(None,xenon_dict)
            self.xenon_ssi_sn = xenon_dict["vars"][1]
        print self.xenon_ssi_sn

    def init_var_indices(self):
        vars = v.mc_variables()
        # one will need indices: first   of KO's (to find the other 21); m_neutralino; ssi with whith the normal X^2 was calculated
        self.KOssi_cen50_index      = vars["KOsigma_pp^SI_cen50"].get_index(self.mcf)
        self.KOssi_unc50_14_index   = vars["KOsigma_pp^SI_unc50_14"].get_index(self.mcf)
        self.KOssi_unc50_7_index    = vars["KOsigma_pp^SI_unc50_7"].get_index(self.mcf)
        self.mneu1_index            = vars["neu1"].get_index(self.mcf)
        if self.lhood_name is not None:
            self.xenon_ssi_index = vars[self.xenon_ssi_sn].get_index(self.mcf)
        print  self.mneu1_index, self.xenon_ssi_index
         

################## Genaral    - functions #########################
    def get_lh_chi2(self,mneu1,ssi):
        return self.lhood.test_chi2([mneu1,ssi])

    def set_axis(self, axis):
        self.ssi_axis= axis

    def get_hack_applied(self):
        return self.hack_applied

################## DataHistos - functions #########################

    def set_ssi_bin_centre(self,histo, i_bin):
        assert self.ssi_axis is not None
        nX,nY,nZ=r.Long(0),r.Long(0),r.Long(0)
        histo.GetBinXYZ(i_bin,nX,nY,nZ)
        centre_ssi=eval("histo.Get%saxis().GetBinCenter(n%s)" % (self.ssi_axis,self.ssi_axis) )
        self.bin_centre=centre_ssi

    def get_KO_chi2(self,chain,ssi_b_c_plot  ):
        # USE [pb] AS UNIT !!!
        ssi_b_c= (ssi_b_c_plot/self.df)
        mneu1       = chain.treeVars["predictions"][self.mneu1_index]
        old_tot_chi2= chain.treeVars["contributions"][0]
        KO_ssi_c    = chain.treeVars["predictions"][self.KOssi_cen50_index ] 
        KO_ssi_u_14 = chain.treeVars["predictions"][self.KOssi_unc50_14_index ] 
        KO_ssi_u_7  = chain.treeVars["predictions"][self.KOssi_unc50_7_index ] 
        if self.lhood_name is not None:
            xenon_ssi   = chain.treeVars["predictions"][self.xenon_ssi_index]

        if self.lhood_name is None:
            chi2= self.get_asym_gauss_chi2(KO_ssi_c,ssi_b_c,KO_ssi_u_14,KO_ssi_u_7) + old_tot_chi2
        else:
            chi2= self.get_asym_gauss_chi2(KO_ssi_c,ssi_b_c,KO_ssi_u_14,KO_ssi_u_7) + self.get_lh_chi2(mneu1,ssi_b_c) + (old_tot_chi2 - self.get_lh_chi2(mneu1,xenon_ssi)) 
        return chi2
    
    def get_asym_gauss_chi2(self,mu,val,unc_up,unc_down):
        assert unc_up is not 0
        assert unc_down is not 0
        if val >  mu : chi2=((mu-val)/unc_up)**2
        if val <= mu : chi2=((mu-val)/unc_down)**2
        return chi2

    def get_gauss_chi2(self,cent,meas,unc):
        assert unc is not 0
        return ((cent-meas)/unc)**2