Exemple #1
0
    def survivalIntegral(self):
        """
        Calculate the survival integral.

        :return: float, float, StatusMessage -- survival integral, var(survival integral), status.
        """
        if self.isReplicateGroup():
            # here we average over the underlying replicates
            si=numpy.zeros([len(self.activeChildWellIndices())])

            allstatuses=StatusMessage()
            statuses=StatusMessage()
            i=0
            for clstc in self.activeChildWells():
                si[i], sivar, status = clstc.survivalIntegral()
                if status is not None:
                    allstatuses.addStatus(status)
                if status is not None and days is not None:
                    statuses.addStatus(status)
                i+=1

            idcs=numpy.isnan(si)
            if numpy.all(idcs):
                allstatuses.addStatus(self.initDiffStatus)
                return None, None, allstatuses

            simean, sivar = maskedArrayToMeanVar(si, ddof=1)

            statuses.addStatus(self.initDiffStatus)
            return simean, sivar, statuses

        days, viability, viabilityvar, initDiffStatus=self.viability()
        si=None
        if viability is not None and days is not None:
            si=numpy.trapz(viability,x=days)
        return si,None,None
Exemple #2
0
def derivativesToMatplotlibAxes(replicate,ax,
                                showMaxLinearSlope=False,
                                showMaxGrowthrate=True, showMaxGrowthrateFromLogOdDerivative=True,
                                showDerivativeLinear=True, showSmoothedDerivativeLinear=True,
                                showLogOdDerivative=True,showLogOdDerivativeFromNonLog=True,showLogOdDerivativeFromNonLogSmoothed=True,
                                showExpFitsOd0Mu=True,showExpFitsMu=False,
                                xmin=None,xmax=None,
                                statuslist=None,colors=None,
                                derlegendkwargs=None,
                                derax_tick_params=None,
                                derax2_tick_params=None):
    """
    Show features associated with derivative (dOD/dt, maximal growth, ...) on a matplotlib figure.

    :param ax: The matplotlib Axes object used for plotting.
    :type ax: matplotlib.axis.Axis

    :param show*: Whether to show a certain feature of this Replicate.
    :type show*: bool

    :param colors: override default colors
    :type colors: dict
    :param legendkwargs: kwargs passed to legend; when None, defaults to {'loc': 0, 'prop': {'size': 8}}
    :type legendkwargs: dict
    :param derax_tick_params: kwargs passed to tick_params for first axis
    :type derax_tick_params: dict
    :param derax2_tick_params: kwargs passed to tick_params for second axis; when None, defaults to derax_tick_params
    :type derax2_tick_params: dict

    FIXME enhance documentation of parameters.

    :return: StatusMessage -- Statuses of this dataset.
    """
    if derlegendkwargs is None:
        derlegendkwargs={
            'loc': 0,
            'prop': {'size': 8},
            'numpoints': 1, 
            }
    # make sure that error bars are not too close to symbol in legend
    matplotlib.legend.Legend.update_default_handler_map({
            matplotlib.container.ErrorbarContainer: matplotlib.legend_handler.HandlerErrorbar(xerr_size=0.8,yerr_size=0.8)
            })
    if derax_tick_params is None:
        derax_tick_params={}
    if derax2_tick_params is None:
        derax2_tick_params=derax_tick_params
    colors_=plotcolors(colors)

    if statuslist is None:
        statuslist=StatusMessage()
    expfitExpmaxStatus=None
    nonlogExpmaxStatus=None

    (ax1xmin,ax1xmax,ax1ymin,ax1ymax)=(None,None,None,None)
    (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=(None,None,None,None)

    if replicate.timeunit == "s":
        ax.ticklabel_format(style='sci', axis='x', scilimits=(0,0))
    ax.ticklabel_format(style='sci', axis='y', scilimits=(0,0))
    if showDerivativeLinear and replicate.derivative() is not None:
        ax.plot(replicate.time[:-1],replicate.derivative(),label="bckgrnd & HD corr.",color=colors_['od'])
    if showSmoothedDerivativeLinear and replicate.smoothedOdDerivative() is not None:
        ax.plot(replicate.time[:-1],replicate.smoothedOdDerivative(),label="smoothed",color=colors_['odsmoothed'])
        if showMaxLinearSlope:
            slopemax, slopemaxVar, interceptmax, interceptmaxVar, timemax, timemaxVar, timemaxIndices, plainSlopeStatus=replicate.odSlopemaxIntercept()
            if slopemax is not None:
                ax.plot([timemax],[slopemax],marker='o',color=colors_['linearmaxslope'])

    ax.set_xlabel("time/"+replicate.timeunit)
    ax.set_ylabel("dOD(t)/dt")
    ax.axhline(0,ls='--',color='black')

    ax2=None
    if (showLogOdDerivative or showExpFitsOd0Mu or showExpFitsMu
        or showLogOdDerivativeFromNonLog
        or showLogOdDerivativeFromNonLogSmoothed
        or showMaxGrowthrate
        or showMaxGrowthrateFromLogOdDerivative):
        ax2 = ax.twinx()
    if replicate.logOdCutoff() is not None and replicate.logOd() is not None:
        tmb=int(math.floor(replicate.slidingWindowSize()/2.))
        tmt=int(math.ceil(replicate.slidingWindowSize()/2.))
        logltidcsMinWin=notNanAndLess(replicate.logOd()[tmb:-tmt],replicate.logOdCutoff())
        logltidcsMin1=notNanAndLess(replicate.logOd()[:-1],replicate.logOdCutoff())
    else:
        logltidcsMinWin=numpy.array([False for i in range(0,len(replicate.time)-replicate.slidingWindowSize())],dtype=bool)
        logltidcsMin1=numpy.array([False for i in range(0,len(replicate.time)-1)],dtype=bool)

    if showLogOdDerivative:
        logodderivative=numpy.copy(replicate.logOdDerivative())
        logodderivative[logltidcsMin1] = numpy.nan
        if numpy.any(~numpy.isnan(logodderivative)):
            ax2.plot(replicate.time[:-1],logodderivative,label="local der.",color=colors_['logodderivative'])

    tslidwin = replicate.time[int(math.floor(replicate.slidingWindowSize()/2.)):int(-math.ceil(replicate.slidingWindowSize()/2.))]
    if showExpFitsOd0Mu:
        mu_withOd0, muvar_withOd0, od0, od0var = replicate.expFitsOd0Mu()
        if mu_withOd0 is not None and len(mu_withOd0):
            muCopy_withOd0=numpy.copy(mu_withOd0)
            muCopy_withOd0[logltidcsMinWin] = numpy.nan
            if numpy.any(~numpy.isnan(muCopy_withOd0)):
                ax2.plot(tslidwin,muCopy_withOd0,label='$\mu$ (exp. fits)',color=colors_['expfitsod0mu'])

    if showExpFitsMu:
        mu_onlyMu, muvar_onlyMu = replicate.expFitsMu()
        if mu_onlyMu is not None and len(mu_onlyMu):
            muCopy_onlyMu=numpy.copy(mu_onlyMu)
            muCopy_onlyMu[logltidcsMinWin] = numpy.nan
            if numpy.any(~numpy.isnan(muCopy_onlyMu)):
                ax2.plot(tslidwin,muCopy_onlyMu,label='$\mu$ (exp. fits, fixed OD(0))',color=colors_['expfitsmu'])

    if showLogOdDerivativeFromNonLogSmoothed:
        logodderivativefnlsm=replicate.logOdDerivativeFromNonLogSmoothed()
        if logodderivativefnlsm is not None and len(logodderivativefnlsm):
            logodderivativefnlsmCopy=numpy.copy(logodderivativefnlsm)
            logodderivativefnlsm[logltidcsMin1] = numpy.nan
            if numpy.any(~numpy.isnan(logodderivativefnlsm)):
                ax2.plot(replicate.time[:-1], logodderivativefnlsm,
                         label="1/OD(t)*dOD(t)/dt smoothed",color=colors_['logodsmoothed'])

    if ax2 is not None:
        (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=ax2.axis()

    if showExpFitsOd0Mu:
        # this shall not influence the y-limits, therefore it is not plotted before
        if mu_withOd0 is not None and len(mu_withOd0) and muvar_withOd0 is not None and len(muvar_withOd0):
            muerr_withOd0 = nonNanSqrt(muvar_withOd0)
            muerr_withOd0[logltidcsMinWin] = numpy.nan
            if numpy.any(~numpy.isnan(muerr_withOd0)):
                ax2.fill_between(tslidwin, 
                                 numpy.ma.masked_array(muCopy_withOd0-muerr_withOd0,numpy.isnan(muerr_withOd0)),
                                 numpy.ma.masked_array(muCopy_withOd0+muerr_withOd0,numpy.isnan(muerr_withOd0)),
                                 alpha=colors_['expfitsod0muerralpha'],edgecolor=colors_['expfitsod0muerr'],facecolor=colors_['expfitsod0muerr'])

    # we calculate these no matter whether they are shown or not, in order to set the ax2ymax limit (see below)
    mu_nl, muvar_nl, od0_nl, od0var_nl, maxt_nl, maxtvar_nl, lag_nl, lagvar_nl, method_nl, nonlogExpmaxStatus = replicate.maxGrowthrateFromLogOdDerivative()
    mu_ef, muvar_ef, od0_ef, od0var_ef, maxt_ef, maxtvar_ef, lag_ef, lagvar_ef, method_ef, expfitExpmaxStatus = replicate.maxGrowthrate()
    if showMaxGrowthrate and replicate.od() is not None and mu_ef is not None:
        ax2.errorbar([maxt_ef],[mu_ef],
                     xerr=[math.sqrt(maxtvar_ef)] if maxtvar_ef is not None else None,
                     yerr=[math.sqrt(muvar_ef)] if muvar_ef is not None else None,
                     marker='o',label='max. $\mu$',color=colors_['maxgrowthrate'])

    if showMaxGrowthrateFromLogOdDerivative and replicate.od() is not None and mu_nl is not None:
        ax2.errorbar([maxt_nl],[mu_nl],
                     xerr=[math.sqrt(maxtvar_nl)] if maxtvar_nl is not None else None,
                     yerr=[math.sqrt(muvar_nl)] if muvar_nl is not None else None,
                     marker='o',label='max. $\mu$ (1/OD(t)*dOD(t)/dt smoothed)',color=colors_['maxgrowthratefromlogod'])

    if showLogOdDerivativeFromNonLog:
        logodderivativefnl=replicate.logOdDerivativeFromNonLog()
        if logodderivativefnl is not None and len(logodderivativefnl):
            logodderivativefnlCopy=numpy.copy(logodderivativefnl)
            logodderivativefnlCopy[logltidcsMin1] = numpy.nan
            if numpy.any(~numpy.isnan(logodderivativefnlCopy)):
                ax2.plot(replicate.time[:-1], logodderivativefnlCopy,
                         label="1/OD(t)*dOD(t)/dt",color=colors_['logod'])

    if ax2 is not None:
        if ax2xmax is None:
            (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=ax2.axis()
        if ax2ymin < 0 and ax2ymax > 0:
            # fix insanely low ymin
            ax2ymin=-ax2ymax/10

        # of the two mu_max, see which one would lead to a higher ymax of ax2
        mupluserr=None
        if mu_nl is not None:
            mupluserr=mu_nl+math.sqrt(muvar_nl) if muvar_nl is not None else mu_nl
        if mu_ef is not None:
            mupluserr_ef=mu_ef+math.sqrt(muvar_ef) if muvar_ef is not None else mu_ef
            if mupluserr is None or mupluserr_ef > mupluserr:
                mupluserr=mupluserr_ef
        # if the mu + error does not lead to an "unhealthy" increase of ymax, use this as ymax
        if mupluserr is not None and ax2ymax is not None and ax2ymax < mupluserr:
            ax2ymax = min((ax2ymax-ax2ymin)*1.5+ax2ymin, 1.08*mupluserr)

        ax2.axis((ax2xmin,ax2xmax,ax2ymin,ax2ymax))

    if xmin is None:
        xmin=numpy.min(replicate.time)
    if xmax is None:
        xmax=numpy.max(replicate.time)
    ax.axis(xmin=xmin, xmax=xmax)
    if ax2 is not None:
        ax2.set_ylabel("growth rate")
        lines, labels = ax.get_legend_handles_labels()
        lines2, labels2 = ax2.get_legend_handles_labels()
        maxlen=0
        for lab in labels + labels2:
            if len(lab) > maxlen:
                maxlen=len(lab)
        dummy = matplotlib.legend.Rectangle((0, 0.5), .01, .01, fc="black", alpha=.0,)
        ax2.axis(xmin=xmin, xmax=xmax)
        ax2.legend(lines + [dummy] + lines2, labels + ['-' * maxlen] + labels2, **derlegendkwargs)
        ax2.xaxis.set_minor_locator(matplotlib.axes.mticker.AutoMinorLocator(10))

    else:
        ax.legend(**derlegendkwargs)

    if showMaxGrowthrateFromLogOdDerivative and nonlogExpmaxStatus is not None:
        statuslist.addStatus(nonlogExpmaxStatus)
    if showMaxGrowthrate and expfitExpmaxStatus is not None:
        statuslist.addStatus(expfitExpmaxStatus)

    ax.tick_params(**derax_tick_params)
    if ax2 is not None:
        ax2.tick_params(**derax2_tick_params)
    return statuslist
Exemple #3
0
def dataToMatplotlibAxes(replicate,ax,title=None,
                         showRaw=True,showBackground=True,showSingle=True,showSmoothed=True,
                         showOd=True,
                         showMaxLinearSlope=False,
                         showLogod=True,showLogodSmoothed=False,
                         showMaxGrowthrate=True, showMaxGrowthrateFromLogOdDerivative=True,
                         showExpFitsOd0Mu=True,showExpFitsMu=False,
                         showGrowthyield=True,
                         statuslist=None,colors=None,dontShowXlabel=False,
                         legendkwargs=None,
                         ax_tick_params=None,
                         ax2_tick_params=None):
    """
    Show features not associated with derivative (such as OD, log(OD), maximal growth, ...) on a matplotlib figure.

    :param ax: The matplotlib Axes object used for plotting.
    :type ax: matplotlib.axis.Axis

    :param show*: Whether to show a certain feature of this Replicate.
    :type show*: bool

    :param colors: override default colors
    :type colors: dict
    :param legendkwargs: kwargs passed to legend; when None, defaults to {'loc': 0, 'prop': {'size': 8}}
    :type legendkwargs: dict
    :param ax_tick_params: kwargs passed to tick_params for first axis
    :type ax_tick_params: dict
    :param ax2_tick_params: kwargs passed to tick_params for second axis; when None, defaults to ax_tick_params
    :type ax2_tick_params: dict

    FIXME enhance documentation of parameters.

    :return: StatusMessage -- Statuses of this dataset.
    """
    if legendkwargs is None:
        legendkwargs={
            'loc': 0,
            'prop': {'size': 8},
            'numpoints': 1,
            'scatterpoints': 1,
            #'markerscale': 0.8,
            #'handlelength': 3,
            }
    # make sure that error bars are not too close to symbol in legend
    matplotlib.legend.Legend.update_default_handler_map({
            matplotlib.container.ErrorbarContainer: matplotlib.legend_handler.HandlerErrorbar(xerr_size=0.8,yerr_size=0.8)
            })
    if ax_tick_params is None:
        ax_tick_params={}
    if ax2_tick_params is None:
        ax2_tick_params=ax_tick_params
    colors_=plotcolors(colors)

    if statuslist is None:
        statuslist=StatusMessage()

    if replicate.timeunit == "s":
        ax.ticklabel_format(style='sci', axis='x', scilimits=(0,0))
    if title is not None:
        ax.set_title(title)

    ax2=None

    if len(replicate.activeChildWellIndices()) == 0:
        statuslist.addStatus(StatusMessage(
                key='replicates:',shortmsg='noActiveChild',
                longmsg='none of the children is active',
                severity=Severity.failed))
        return statuslist, None, None
    if replicate.rawOd() is None:
        statuslist.addStatus(StatusMessage(
                key='replicates:',shortmsg='noRawOd',
                longmsg='raw optical density is not defined',
                severity=Severity.failed))
        return statuslist, None, None

    (ax1xmin,ax1xmax,ax1ymin,ax1ymax)=(replicate.time.min(),replicate.time.max(),None,None)
    (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=(ax1xmin,ax1xmax,None,None)

    if replicate.od() is not None and showOd:
        ax.plot(replicate.time,replicate.od(),label="bckgrnd & HD corr.",color=colors_['od'])
        if replicate.odVar() is not None:
            err=numpy.sqrt(replicate.odVar())
            if showSingle:
                # show each underlying replicate
                for stc in replicate.activeChildWells():
                    if stc.od() is not None:
                        ax.plot(stc.time,stc.od(),label="",color=colors_['singleod'])
            ax.fill_between(replicate.time, replicate.od()-err, replicate.od()+err,
                            alpha=colors_['oderralpha'],edgecolor=colors_['oderr'],facecolor=colors_['oderr'])

    if ((showLogod and replicate.logOd() is not None)
        or (showLogodSmoothed and replicate.logOdSmoothed() is not None)
        or (showMaxGrowthrate and replicate.od() is not None)
        or (showMaxGrowthrateFromLogOdDerivative and replicate.od() is not None)):
        ax2 = ax.twinx()
        ax2.set_ylabel("ln(OD)")

    if replicate.logOdCutoff() is not None and replicate.logOd() is not None:
        logltidcs=notNanAndLess(replicate.logOd(),replicate.logOdCutoff())
    else:
        logltidcs=numpy.array([False for i in range(0,len(replicate.time))],dtype=bool)

    if showLogod and replicate.logOd() is not None:
        logodcopy=numpy.copy(replicate.logOd())
        logodcopy[logltidcs] = numpy.nan
        if numpy.any(~numpy.isnan(logodcopy)):
            # plotting does not work if all values are nan; it is not enough to check logltidcs, because
            # logod can also be nan if od is less than zero (or rather: less then 1e-35 cutoff)
            ax2.plot(replicate.time,logodcopy,label="natural log",color=colors_['logod'])
        if numpy.any(~numpy.isnan(logodcopy)) and replicate.odVar() is not None:
            # create errors from odVar
            logoderr=nonNanNonZeroDivide(numpy.sqrt(replicate.odVar()),numpy.absolute(replicate.od()))
            logoderr[numpy.isnan(logodcopy)] = numpy.nan
            ax2.fill_between(replicate.time,
                             numpy.ma.masked_array(logodcopy-logoderr,numpy.isnan(logoderr)),
                             numpy.ma.masked_array(logodcopy+logoderr,numpy.isnan(logoderr)),
                             alpha=colors_['logoderralpha'],edgecolor=colors_['logoderr'],facecolor=colors_['logoderr'])
        (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=ax2.axis()

    if showRaw or replicate.od() is None:
        if replicate.rawOdVar() is not None:
            err=numpy.sqrt(replicate.rawOdVar())
            activeTcs=replicate.activeChildWells()
            if replicate.od() is None and len(activeTcs) > 1:
                # we only show the raw, so we can show all replicates on top of each other
                for stc in activeTcs:
                    ax.plot(stc.time,stc.rawOd(),label="",color=colors_['singlerawod'])
            ax.fill_between(replicate.time, replicate.rawOd()-err, replicate.rawOd()+err,
                            alpha=colors_['rawoderralpha'],edgecolor=colors_['rawoderr'],facecolor=colors_['rawoderr'])
        ax.plot(replicate.time,replicate.rawOd(),label="raw",color=colors_['rawod'])

    if showBackground and replicate.background is not None:
        ax.plot(replicate.time,replicate.background.rawOd(),label="background",color=colors_['background'])
        if replicate.background.rawOdVar() is not None:
            err=numpy.sqrt(replicate.background.rawOdVar())
            ax.fill_between(replicate.time, replicate.background.rawOd()-err, replicate.background.rawOd()+err,
                            alpha=colors_['backgrounderralpha'], edgecolor=colors_['backgrounderr'], facecolor=colors_['backgrounderr'])
    if showSmoothed and replicate.smoothedOd() is not None:
        ax.plot(replicate.time,replicate.smoothedOd(),color=colors_['smoothedod'],
                label="smoothed""\n(s="+str(replicate.smoothingS())+", k="+str(replicate.smoothingK())+")")
        if replicate.smoothedOdDerivative() is not None and showMaxLinearSlope:
            slopemax, slopemaxVar, interceptmax, interceptmaxVar, timemax, timemaxVar, timemaxIndices, plainSlopeStatus=replicate.odSlopemaxIntercept()
            if plainSlopeStatus is not None:
                statuslist.addStatus(plainSlopeStatus)
            if slopemax is not None:
                flin=lambda t: slopemax*t+interceptmax
                (dummyax1xmin,dummyax1xmax,ax1ymin,ax1ymax)=ax.axis()
                ax.plot(replicate.time, list(map(flin,replicate.time)),label="linear",color=colors_['linearmaxslope'])
                ax.plot([timemax],[flin(timemax)],marker='o',color=colors_['linearmaxslope'])

    if showGrowthyield and replicate.od() is not None:
        growthyield, growthyieldvar, tgrowthyield, tgrowthyieldvar, status=replicate.growthyield()
        if status is not None:
            statuslist.addStatus(status)
        if growthyield is not None:
            ax.scatter([tgrowthyield],[growthyield],s=40,alpha=1.,zorder=42,
                       marker='o',color=colors_['growthyield'],
                       edgecolor=colors_['growthyieldedge'],label='yield',
                       linewidths=.8,
                       )

    if showLogodSmoothed and replicate.logOdSmoothed() is not None:
        logodsmoothedcopy=numpy.copy(replicate.logOdSmoothed())
        logodsmoothedcopy[logltidcs] = numpy.nan
        if numpy.any(~numpy.isnan(logodsmoothedcopy)):
            ax2.plot(replicate.time,logodsmoothedcopy,color=colors_['logodsmoothed'],
                     label="smoothed""\n(s="+str(replicate.smoothingS())+", k="+str(replicate.smoothingK())+")")
            if ax2xmax is not None:
                ax2.axis((ax2xmin,ax2xmax,ax2ymin,ax2ymax))
            (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=ax2.axis()

    if showMaxGrowthrate and replicate.od() is not None:
        mu, muvar, od0, od0var, maxt, maxtvar, lag, lagvar, method, expfitExpmaxStatus = replicate.maxGrowthrate()
        if mu is not None and od0 > 0:
            lagAtLogOdEquals=replicate.lagAtLogOdEquals()
            flin=lambda t: mu*t+math.log(od0)
            ax2.plot(replicate.time, list(map(flin,replicate.time)),color=colors_['maxgrowthrate'])
            y2mumax=mu*maxt+math.log(od0)
            ax2.plot([maxt],[y2mumax],label='max. $\mu$',marker='o',color=colors_['maxgrowthrate'])
            if lag is not None:
                ax2.errorbar([lag],[lagAtLogOdEquals],
                             xerr=[math.sqrt(lagvar)] if lagvar is not None else None,
                             label='lag',
                             marker='x',markeredgewidth=2,color=colors_['maxgrowthrate'])
            if ax2xmin is not None:
                ax2.axis((ax2xmin,ax2xmax,ax2ymin,ax2ymax))
            (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=ax2.axis()
            if y2mumax-math.fabs(y2mumax)*.05 < ax2ymin:
                ax2ymin=y2mumax-math.fabs(y2mumax)*.05
            if lag is not None and ax2ymax >= lagAtLogOdEquals-math.fabs(lagAtLogOdEquals)*.05:
                ax2ymin=lagAtLogOdEquals-math.fabs(lagAtLogOdEquals)*.05
            ax2.axis((ax2xmin,ax2xmax,ax2ymin,ax2ymax))

    if showMaxGrowthrateFromLogOdDerivative and replicate.od() is not None:
        mu, muvar, od0, od0var, maxt, maxtvar, lag, lagvar, method, nonlogExpmaxStatus = replicate.maxGrowthrateFromLogOdDerivative()
        if mu is not None and od0 > 0:
            lagAtLogOdEquals=replicate.lagAtLogOdEquals()
            flin=lambda t: mu*t+math.log(od0)
            ax2.plot(replicate.time, list(map(flin,replicate.time)),color=colors_['maxgrowthratefromlogod'])
            y2mumax=mu*maxt+math.log(od0)
            ax2.plot([maxt],[y2mumax],label='max. $\mu$ (1/OD(t)*dOD(t)/dt smoothed)',marker='o',color=colors_['maxgrowthratefromlogod'])
            if lag is not None:
                ax2.errorbar([lag],[lagAtLogOdEquals],
                             xerr=[math.sqrt(lagvar)] if lagvar is not None else None,
                             label='lag (1/OD(t)*dOD(t)/dt smoothed)',
                             marker='x',markeredgewidth=2,color=colors_['maxgrowthratefromlogod'])
            if ax2xmin is not None:
                ax2.axis((ax2xmin,ax2xmax,ax2ymin,ax2ymax))
            (ax2xmin,ax2xmax,ax2ymin,ax2ymax)=ax2.axis()
            if y2mumax-math.fabs(y2mumax)*.05 < ax2ymin:
                ax2ymin=y2mumax-math.fabs(y2mumax)*.05
            if lag is not None and ax2ymax >= lagAtLogOdEquals-math.fabs(lagAtLogOdEquals)*.05:
                ax2ymin=lagAtLogOdEquals-math.fabs(lagAtLogOdEquals)*.05
            ax2.axis((ax2xmin,ax2xmax,ax2ymin,ax2ymax))

    if ax1xmin is not None:
        ax.axis((ax1xmin,ax1xmax,ax1ymin,ax1ymax))

    (sub1_ax1xmin,sub1_ax1xmax,sub1_ax1ymin,sub1_ax1ymax)=ax.axis()

    if ax2 is not None:
        # for legend see also http://stackoverflow.com/questions/5484922/secondary-axis-with-twinx-how-to-add-to-legend
        lines, labels = ax.get_legend_handles_labels()
        lines2, labels2 = ax2.get_legend_handles_labels()
        maxlen=0
        for lab in labels + labels2:
            if len(lab) > maxlen:
                maxlen=len(lab)
        dummy = matplotlib.legend.Rectangle((0, 0.5), .01, .01, fc="black", alpha=.0,)
        ax2.legend(lines + [dummy] + lines2, labels + ['-' * maxlen] + labels2, **legendkwargs)
    else:
        ax.legend(**legendkwargs)

    if not dontShowXlabel:
        ax.set_xlabel("time/"+replicate.timeunit)

    ax.set_ylabel("OD")
#    ax.xaxis.set_major_locator(matplotlib.axes.mticker.MaxNLocator(10))
    ax.xaxis.set_minor_locator(matplotlib.axes.mticker.AutoMinorLocator(10))
    ax.axhline(0,ls='--',color='black')

    ax.tick_params(**ax_tick_params)
    if ax2 is not None:
        ax2.tick_params(**ax2_tick_params)
    return statuslist, sub1_ax1xmin, sub1_ax1xmax
Exemple #4
0
    def viability(self):
        """
        Calculate the viability.

        :return: list(float), list(float), list(float), StatusMessage -- days, viability, var(viability), status.
        """
        if self.isReplicateGroup():
            # here we average over the underlying replicates
            viability=numpy.zeros([len(self.activeChildWellIndices()), self.days.shape[0]])

            allstatuses=StatusMessage()
            statuses=StatusMessage()
            i=0
            for clstc in self.activeChildWells():
                days, viability[i], viabilityvar, status = clstc.viability()
                if status is not None:
                    allstatuses.addStatus(status)
                if status is not None and days is not None:
                    statuses.addStatus(status)
                i+=1

            idcs=numpy.isnan(viability)
            if numpy.all(idcs):
                allstatuses.addStatus(self.initDiffStatus)
                return None, None, None, allstatuses

            viabilitymean, viabilityvar = maskedArrayToMeanVar(viability, idcs=idcs, ddof=1, axis=0)

            statuses.addStatus(self.initDiffStatus)
            return self.days, viabilitymean, viabilityvar, statuses

        viability=numpy.zeros([len(self._odReplicates)])
        viabilityvar=numpy.zeros([len(self._odReplicates)])
        mu_ef, mu_ef_var, od0_ef, od0_ef_var, maxt_ef, maxt_ef_var, lag_ef__0, lag_ef_var__0, method_ef, status = self._odReplicates[0].maxGrowthrate()
        if lag_ef__0 is None:
            return None, None, None, StatusMessage(
                key='viability:noInitialLag', severity=Severity.failed,
                longmsg='lag could not be extract for first timepoint')

        tcidx=-1
        for tc in self._odReplicates:
            tcidx+=1
            if tc is None:
                viability[tcidx]=None
                viabilityvar[tcidx]=None
                print('WARNING no Replicate defined for day '+str(self.days[tcidx])+' and sample/condition '+self._odReplicates[0].fullId())
                continue

            mu_ef, mu_ef_var, od0_ef, od0_ef_var, maxt_ef, maxt_ef_var, lag_ef, lag_ef_var, method_ef, status = tc.maxGrowthrate()
            doublingtime, doublingtimevar = Replicate.growthrateToDoublingTime(mu_ef,mu_ef_var)
            if lag_ef is not None and doublingtime is not None:
                deltaT=lag_ef-lag_ef__0
                # f(deltaT,doubling) = 2^(- deltaT/doubling )  [ == e^(-ln(2) deltaT/doubling) ]
                viability[tcidx]=math.pow(2,-deltaT/doublingtime)
            elif doublingtime is None:
                # if we could not extract a doubling time we assume that there was no growth at all
                viability[tcidx]=0.
                viabilityvar[tcidx]=0.
            else:
                viability[tcidx]=None
            if lag_ef_var__0 is not None and lag_ef_var is not None and doublingtimevar is not None:
                deltaTvar=lag_ef_var+lag_ef_var__0
                # df/ddeltaT  = - ln(2)/doubling  2^(- deltaT/doubling )
                # df/doubling = + ln(2) deltaT 1/doubling^2   2^(- deltaT/doubling )
                viabilityvar[tcidx]=( math.pow( math.log(2)/doublingtime * math.pow(2,-deltaT/doublingtime),2 ) * doublingtimevar
                                      + math.pow( math.log(2)*deltaT  * math.pow(doublingtime,-2) * math.pow(2,-deltaT/doublingtime),2 ) * deltaTvar)
            else:
                viabilityvar[tcidx]=None

        return self.days, viability, viabilityvar, self.initDiffStatus
Exemple #5
0
    def _loadGatFiles(self,files,days):
        """
        Reads data from GAT files and sets up 

        For internal use only.
        """
        self.days = days
        self.files = files

        self.plates=[]
        missingfiles=[]
        for f in self.files:
            if not os.path.exists(f):
                missingfiles.append(f)
        if len(missingfiles) > 0:
            raise Cls.PlateFileDoesNotExist(missingfiles)
        for f in self.files:
            self.plates.append(Plate(filename=f,fileformat='gat'))
            self.plates[-1].verbose=False

        self.clsWells=[]
        # we use the sampleid/conditions tuples from the first plate to initialise this cls analyser
        wellidx=0
        for tc0 in self.plates[0].wells:
            tc0fullId=tc0.fullId()
            listOfWells=[tc0]
            statuses=StatusMessage()
            for tcidx in range(1,len(self.plates)):
                listOfWells.append(self.plates[tcidx].wells[wellidx])
                if listOfWells[-1].fullId() != tc0fullId:
                    wellidstr=listOfWells[-1].activeChildWellIdStr()
                    raise Cls.Error('Plates do not match: could not find aquivalent to "'+tc0.fullId()+'" in "'
                                          +self.files[tcidx]+'" in well '+wellidstr+'.')
            self.clsWells.append(ClsReplicate(parent=self,listOfOdReplicates=listOfWells,days=self.days,
                                                                wellIndices=[wellidx],
                                                                wellids=tc0.wellids,sampleid=tc0.sampleid,condition=tc0.condition,
                                                                status=statuses))
            wellidx+=1

        self.clsReplicateGroups=[]
        # we use the sampleid/conditions tuples from the first plate to initialise this cls analyser
        for tc0 in self.plates[0].replicateGroups:
            listOfWells=[tc0]
            tc0fullId=tc0.fullId()
            statuses=StatusMessage()
            for tcidx in range(1,len(self.plates)):
                listOfWells.append(self.plates[tcidx].replicateGroupForSampleCondition(tc0.sampleid,tc0.condition))
                if listOfWells[-1] is None:
                    raise Cls.Error('Plates do not match: could not find aquivalent to "'+tc0.fullId()+'" in "'
                                          +self.files[tcidx]+'".')
                else:
                    diffstatus=Cls.differencesInChildActivations(tc0,listOfWells[-1],0,tcidx)
                    if diffstatus is not None:
                        statuses.addStatus(diffstatus)
            self.clsReplicateGroups.append(ClsReplicate(parent=self,listOfOdReplicates=listOfWells,days=self.days,
                                                                         status=statuses,
                                                                         wellIndices=tc0.childWellIndices(),isReplicateGroup=True,
                                                                         wellids=tc0.wellids,sampleid=tc0.sampleid,condition=tc0.condition))

        # NOTE we create a reference here in order to be able to use this class with ODplateModel
        self.replicateGroups=self.clsReplicateGroups