def __init__(self, tree, alignment, model, underflowfreq=<NUM_LIT:3>,<EOL>dparamscurrent=True, dtcurrent=False, branchScale=None):
assert isinstance(underflowfreq, int) and underflowfreq >= <NUM_LIT:1><EOL>self.underflowfreq = underflowfreq<EOL>assert isinstance(dparamscurrent, bool)<EOL>self._dparamscurrent = dparamscurrent<EOL>assert isinstance(dtcurrent, bool)<EOL>self._dtcurrent = dtcurrent<EOL>assert not (self.dparamscurrent and self.dtcurrent), (<EOL>"<STR_LIT>")<EOL>if isinstance(model, phydmslib.models.DistributionModel):<EOL><INDENT>self._distributionmodel = True<EOL><DEDENT>elif isinstance(model, phydmslib.models.Model):<EOL><INDENT>self._distributionmodel = False<EOL><DEDENT>else:<EOL><INDENT>raise ValueError("<STR_LIT>")<EOL><DEDENT>self.model = copy.deepcopy(model)<EOL>self.nsites = self.model.nsites<EOL>assert isinstance(alignment, list) and all([isinstance(tup, tuple)<EOL>and len(tup) == <NUM_LIT:2> for tup in alignment]), ("<STR_LIT>"<EOL>"<STR_LIT>")<EOL>assert all([len(seq) == <NUM_LIT:3> * self.nsites for (head, seq) in alignment])<EOL>assert set([head for (head, seq) in alignment]) == set([clade.name for<EOL>clade in tree.get_terminals()])<EOL>self.alignment = copy.deepcopy(alignment)<EOL>self.nseqs = len(alignment)<EOL>alignment_d = dict(self.alignment)<EOL>assert isinstance(tree, Bio.Phylo.BaseTree.Tree), "<STR_LIT>"<EOL>self._tree = copy.deepcopy(tree)<EOL>assert self._tree.count_terminals() == self.nseqs<EOL>if branchScale == None:<EOL><INDENT>branchScale = self.model.branchScale<EOL><DEDENT>else:<EOL><INDENT>assert isinstance(branchScale, float) and branchScale > <NUM_LIT:0><EOL><DEDENT>for node in self._tree.find_clades():<EOL><INDENT>if node != self._tree.root:<EOL><INDENT>node.branch_length /= branchScale<EOL><DEDENT><DEDENT>self.name_to_nodeindex = {}<EOL>self.ninternal = len(self._tree.get_nonterminals())<EOL>self.ntips = self._tree.count_terminals()<EOL>self.nnodes = self.ntips + self.ninternal<EOL>self.rdescend = [-<NUM_LIT:1>] * self.ninternal<EOL>self.ldescend = [-<NUM_LIT:1>] * self.ninternal<EOL>self.underflowlogscale = scipy.zeros(self.nsites, dtype='<STR_LIT:float>')<EOL>if self._distributionmodel:<EOL><INDENT>self._Lshape = (self.model.ncats, self.nsites, N_CODON)<EOL><DEDENT>else:<EOL><INDENT>self._Lshape = (self.nsites, N_CODON)<EOL><DEDENT>self.dL_dt = dict([(n, {}) for n in range(self.nnodes - <NUM_LIT:1>)])<EOL>self.L = {}<EOL>self.dL = {}<EOL>self._dLshape = {}<EOL>for param in self._paramlist_PartialLikelihoods:<EOL><INDENT>self.dL[param] = {}<EOL>if self._distributionmodel and param == self.model.distributedparam:<EOL><INDENT>self._dLshape[param] = self._Lshape<EOL><DEDENT>else:<EOL><INDENT>paramvalue = getattr(self.model, param)<EOL>if isinstance(paramvalue, float):<EOL><INDENT>self._dLshape[param] = self._Lshape<EOL><DEDENT>elif isinstance(paramvalue, scipy.ndarray) and (paramvalue.ndim<EOL>== <NUM_LIT:1>):<EOL><INDENT>if self._distributionmodel:<EOL><INDENT>self._dLshape[param] = (self.model.ncats,<EOL>len(paramvalue), self.nsites, N_CODON)<EOL><DEDENT>else:<EOL><INDENT>self._dLshape[param] = (len(paramvalue),<EOL>self.nsites, N_CODON)<EOL><DEDENT><DEDENT>else:<EOL><INDENT>raise ValueError("<STR_LIT>".format(<EOL>param, paramvalue))<EOL><DEDENT><DEDENT><DEDENT>tipnodes = []<EOL>internalnodes = []<EOL>self.tips = scipy.zeros((self.ntips, self.nsites), dtype='<STR_LIT:int>')<EOL>self.gaps = []<EOL>self.descendants = []<EOL>self._t = scipy.full((self.nnodes - <NUM_LIT:1>,), -<NUM_LIT:1>, dtype='<STR_LIT:float>')<EOL>for node in self._tree.find_clades(order='<STR_LIT>'):<EOL><INDENT>if node.is_terminal():<EOL><INDENT>tipnodes.append(node)<EOL><DEDENT>else:<EOL><INDENT>internalnodes.append(node)<EOL><DEDENT><DEDENT>for (n, node) in enumerate(tipnodes + internalnodes):<EOL><INDENT>if node != self._tree.root:<EOL><INDENT>assert n < self.nnodes - <NUM_LIT:1><EOL>self._t[n] = node.branch_length<EOL><DEDENT>if node.is_terminal():<EOL><INDENT>assert n < self.ntips<EOL>self.descendants.append([])<EOL>seq = alignment_d[node.name]<EOL>nodegaps = []<EOL>for r in range(self.nsites):<EOL><INDENT>codon = seq[<NUM_LIT:3> * r : <NUM_LIT:3> * r + <NUM_LIT:3>]<EOL>if codon == '<STR_LIT>':<EOL><INDENT>nodegaps.append(r)<EOL><DEDENT>elif codon in CODON_TO_INDEX:<EOL><INDENT>self.tips[n][r] = CODON_TO_INDEX[codon]<EOL><DEDENT>else:<EOL><INDENT>raise ValueError("<STR_LIT>".format(codon,<EOL>node.name))<EOL><DEDENT><DEDENT>self.gaps.append(scipy.array(nodegaps, dtype='<STR_LIT:int>'))<EOL><DEDENT>else:<EOL><INDENT>assert n >= self.ntips, "<STR_LIT>".format(<EOL>n, self.ntips)<EOL>assert len(node.clades) == <NUM_LIT:2>, ("<STR_LIT>"<EOL>"<STR_LIT>"<EOL>"<STR_LIT>"<EOL>"<STR_LIT>").format(<EOL>node.name, len(node.clades), node == self._tree.root)<EOL>ni = n - self.ntips<EOL>self.rdescend[ni] = self.name_to_nodeindex[node.clades[<NUM_LIT:0>]]<EOL>self.ldescend[ni] = self.name_to_nodeindex[node.clades[<NUM_LIT:1>]]<EOL>self.descendants.append([self.name_to_nodeindex[nx] for nx<EOL>in node.find_clades() if nx != node])<EOL><DEDENT>self.name_to_nodeindex[node] = n<EOL><DEDENT>self.gaps = scipy.array(self.gaps)<EOL>assert len(self.gaps) == self.ntips<EOL>self._paramsarray = None <EOL>self._index_to_param = {} <EOL>i = <NUM_LIT:0><EOL>for param in self.model.freeparams:<EOL><INDENT>paramvalue = getattr(self.model, param)<EOL>if isinstance(paramvalue, float):<EOL><INDENT>self._index_to_param[i] = param<EOL>i += <NUM_LIT:1><EOL><DEDENT>else:<EOL><INDENT>for (pindex, pvalue) in enumerate(paramvalue):<EOL><INDENT>self._index_to_param[i] = (param, pindex)<EOL>i += <NUM_LIT:1><EOL><DEDENT><DEDENT><DEDENT>self._param_to_index = dict([(y, x) for (x, y) in<EOL>self._index_to_param.items()])<EOL>assert i == len(self._index_to_param)<EOL>self._updateInternals()<EOL>
Initialize a `TreeLikelihood` object.

        Args:
            `tree`, `alignment`, `model`, `underflowfreq`
                Attributes of same name described in class doc string.
                Note that we make copies of `tree`, `model`, and
                `alignment`' so the calling objects are not modified
                during optimization.
            `dparamscurrent`, `dtcurrent`
                Current values of these flags indicating which
                derivatives to compute.
            `branchScale` (`None` or float > 0)
                The branch lengths in the input tree are assumed
                to be in units of substitutions per site with
                the scaling defined by `model.branchScale`. If
                the scaling should instead be defined by some
                other value of `branchScale`, indicate by
                setting to that value rather than `None`. This
                is useful if tree was inferred on models across
                many sites but you are now just analyzing an
                individual one. Note that this option applies
                only to the input tree, not the output one.