³ò
A¶GJc           @   si   d  Z  d d k Z d d k Z d e f d „  ƒ  YZ d „  Z d „  Z d „  Z d e f d	 „  ƒ  YZ d S(
   sf  
aver.py

Classes: 'Mean' represents an average of a set of numbers or a random number
'LinearFit' represents a result of a straight line fit.

Functions: 'average', 'combine', 'stdcorrection'

To get an array of mean values from an 'array' of 'Mean' objects you can try
'[x.mean for x in array]' or 'numpy.array([x.mean for x in array])'.

Lev, 17 Dec 2008
iÿÿÿÿNt   Meanc           B   s>  e  Z d  Z e i e i e i e i d d „ Z d „  Z d „  Z d „  Z	 e
 d „  ƒ Z d „  Z d „  Z d	 „  Z d
 „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z d „  Z e Z d „  Z e Z e Z d „  Z d „  Z e Z d „  Z  d „  Z! d „  Z" d e$ d „ Z% d d d „ Z& RS(   sú  
    Represent a result of averaging numbers together or a random number:
    
    mean - (the best estimate of) the mean

    std - standard deviation. Note that for correct combination of uncertainties,
        this is should be calculated using
        std = \sqrt{rac{\sum x^2 - (\sum x)^2}/(N-1)},
        with N-1 in the denominator, rather N (and 1 for N < 2).
        This accounts for the fact that the average, from which individual
        points deviate is not known precisely.

    min, max - extrema of the data

    N - amount of data. 0 means unknown/undefined, such as in case of combining
        random quantities.
    
    derived properties (calculated on creation):
    
    error = std/sqrt(N) - error of the mean (equal to 'std' for N < 2)
    
    median = (max + min)/2
    halfspan = (max - min)/2 - to be used for errorbars that encompass all data points
    
    rmsdev - root of mean square of deviation of individual values from the best estimate of the mean
    rmsdev = \sqrt{rac{N-1}{N}}std for N > 1, 0 for N = 1 and just std for N < 1.
    
    stderror - error of the standard deviation (equal to 0 for N < 2)
    
    Arithmetic operations +,-,*,/,** are supported between Mean objects as well
    as between Mean objects and numbers. The arguments are considered uncorrelated.
    
    When combining uncertainties all information about number of points is lost
    (because it can be different for the two arguments). Standard deviation,
    rather than error of the mean is retained, such that the result represents
    scatter of the hypothetic combination of the numbers averaged together.
    Use 'be()' before combining uncertainties to get best estimates of the
    means with its errors.
    
    DISCLAIMER: When dividing by or deriving a power of a 'Mean' object the
    standard deviation of the result is only valid under the assumption that
    for the argument it is much smaller than the mean.
    
    Only a real number can be used as a right hand side argument for **.

    A number is equal ('==' returns True) to the Mean object if it is within one
    'std' from the mean. Two Mean objects are equal if their difference is equal
    to 0 in the above sense.

    'fromtuple()'/'totuple()' methods are primarily for spreadsheet I/O.
    i    c         C   s¬   | |  _  t | ƒ |  _ t i | | g ƒ |  _ t i | | g ƒ |  _ t i |  i ƒ o t i |  _ n t i |  i ƒ o t i |  _ n t | ƒ |  _	 |  i
 ƒ  d S(   s2  
        Construct a Mean from its statistical properties.
        'mean' is (the best estimate of) the mean
        'std' is standard deviation
        'min' and 'max' are value limits
        'N' is number of points that contributed to the estimate of the mean/std
        or '0' if unavailable.
        N(   t   meant   abst   stdt   numpyt   mint   maxt   isnant   Inft   intt   Nt	   calculate(   t   selfR   R   R   R   R
   (    (    s   c:\py\lib\aver.pyt   __init__W   s    		  c         C   sÃ   |  i  d j  o
 |  i n |  i |  i  d |  _ d |  i |  i |  _ d |  i |  i |  _ |  i  d j o |  i t |  i  ƒ n d |  _ |  i  d j  o d n |  i t	 i
 d ƒ |  _ d S(   s   Calculate derived quantitiesi   g      à?i   i    N(   R
   R   t   errorR   R   t   mediant   halfspant   stdcorrectiont   rmsdevR   t   sqrtt   stderror(   R   (    (    s   c:\py\lib\aver.pyR   i   s
    10c         C   s"   t  |  i |  i |  i |  i d ƒ S(   sa  
        Return the best estimate of the mean, an object with both 'std' and 'error' set to the 'error' of the processed Mean
        and zero as number of points. This is useful when combining uncertainties, because then the number of points
        is lost and the standard deviation, the scatter of points, is kept as both 'std' and 'error'.
        i    (   R    R   R   R   R   (   R   (    (    s   c:\py\lib\aver.pyt   beq   s    c         C   s"   |  i  |  i |  i |  i |  i f S(   s-   Convert into a tuple (mean, std, min, max, N)(   R   R   R   R   R
   (   R   (    (    s   c:\py\lib\aver.pyt   totupley   s    c         C   s
   t  |  Œ  S(   sF   Convert a tuple/list/array (mean, std, min, max, N) into a Mean object(   R    (   t   array(    (    s   c:\py\lib\aver.pyt	   fromtuplez   s    c         C   s   t  i |  i ƒ  ƒ S(   N(   R    R   R   (   R   (    (    s   c:\py\lib\aver.pyt   copy}   s    c         C   sA   d |  i  |  i |  i |  i |  i d j o d |  i n d f S(   Ns   x = %g +- %g (%g <= x <= %g)%si    s   , %d samplest    (   R   R   R   R   R
   (   R   (    (    s   c:\py\lib\aver.pyt   __repr__   s   c         C   s   |  i  S(   N(   R   (   R   (    (    s   c:\py\lib\aver.pyt   __min__   s    c         C   s   |  i  S(   N(   R   (   R   (    (    s   c:\py\lib\aver.pyt   __max__‚   s    c         C   s(   t  |  i |  i |  i |  i |  i ƒ S(   N(   R    R   R   R   R   R
   (   R   (    (    s   c:\py\lib\aver.pyt   __neg__ƒ   s    c         C   s   t  |  i ƒ S(   N(   R   R   (   R   (    (    s   c:\py\lib\aver.pyt   __abs__„   s    c         C   s   t  |  i ƒ S(   N(   t   complexR   (   R   (    (    s   c:\py\lib\aver.pyt   __complex__…   s    c         C   s   t  |  i ƒ S(   N(   R	   R   (   R   (    (    s   c:\py\lib\aver.pyt   __int__†   s    c         C   s   t  |  i ƒ S(   N(   t   floatR   (   R   (    (    s   c:\py\lib\aver.pyt	   __float__‡   s    c         C   s­   t  | t ƒ oN t |  i | i |  i d | i d d |  i | i |  i | i d ƒ SnF t i | ƒ o5 t |  i | |  i |  i | |  i | |  i ƒ Sn t	 ‚ d  S(   Ni   g      à?i    (
   t
   isinstanceR    R   R   R   R   R   t   isscalarR
   t   NotImplemented(   R   t   other(    (    s   c:\py\lib\aver.pyt   __add__‰   s    )%"c         C   s	   |  | S(   N(    (   R   R(   (    (    s   c:\py\lib\aver.pyt   __sub__’   s    c         C   s-  t  | t ƒ o¬ |  i | i |  i | i |  i | i |  i | i g } t |  i | i |  i d | i d | i d |  i d |  i d | i d d t | ƒ t | ƒ d ƒ Snh t i | ƒ oW |  i | |  i | g } t |  i | t |  i | ƒ t | ƒ t | ƒ |  i	 ƒ Sn t
 ‚ d  S(   Ni   g      à?i    (   R%   R    R   R   R   R   R   R&   R   R
   R'   (   R   R(   t   extrema(    (    s   c:\py\lib\aver.pyt   __mul__”   s    :+ c         C   s   |  | d S(   Niÿÿÿÿ(    (   R   R(   (    (    s   c:\py\lib\aver.pyt   __truediv__¡   s    c         C   s  t  i | ƒ p
 t ‚ n |  i |  i d j  oT | d j  oG t |  i | t | |  i | d |  i ƒ t  i	 t  i	 |  i
 ƒ Sn |  i | |  i | g } |  i |  i d j  o | i d ƒ n t |  i | t | |  i | d |  i ƒ t | ƒ t | ƒ |  i
 ƒ S(   Ni    i   (   R   R&   R'   R   R   R    R   R   R   R   R
   t   append(   R   R(   R+   (    (    s   c:\py\lib\aver.pyt   __pow__¤   s    
$G,c         C   s	   |  | S(   N(    (   R   R(   (    (    s   c:\py\lib\aver.pyt   __rsub__·   s    c         C   s   | |  d S(   Niÿÿÿÿ(    (   R   R(   (    (    s   c:\py\lib\aver.pyt   __rtruediv__¸   s    c         C   s„   t  | t ƒ o4 t |  i | i ƒ d |  i d | i d j Sn7 t i | ƒ o& t |  i | ƒ d |  i d j Sn t ‚ d  S(   Ni   (   R%   R    R   R   R   R   R&   R'   (   R   R(   (    (    s   c:\py\lib\aver.pyt   __eq__»   s
    4&c         C   s„   t  | t ƒ ot t i |  i | i ƒ o[ t i |  i | i ƒ oB t i |  i | i ƒ o) t i |  i | i ƒ o |  i | i j S(   sÀ   
        Compares two Mean objects to be identical. Return True only if all
        5 fields, the mean, standard deviation, value boundaries and number of points
        are the same.
        (	   R%   R    t   flibt   floatcmpR   R   R   R   R
   (   R   R(   (    (    s   c:\py\lib\aver.pyt   sameÂ   s    )2c         C   s   t  t i |  i ƒ  ƒ ƒ S(   sG   Return True if a Mean object has all properties finite, otherwise False(   t   allR   t   isfiniteR   (   R   (    (    s   c:\py\lib\aver.pyR7   Ì   s    c         C   s§   | d j or |  i d j o t i t i |  i ƒ ƒ } n d } | d j  o d | } q | d j o
 d } q d } n | |  i | o d n d | |  i S(   s1   Return a string representation without boundariesi    s   %%.%dfs   %gs   %ds   \pm s   +-N(   t   NoneR   R   t   floort   log10R   (   R   t   fmtt   text	   std_order(    (    s   c:\py\lib\aver.pyt   briefÐ   s    

t   xs   %gc         C   s‚   t  i |  i ƒ o | |  i d n d } t  i |  i ƒ o d | |  i n d } d i d | ƒ | |  i |  i | | | f S(   s   Return a neat TeX represenations    \les	   -\infty <s   \le s   < \inftys   %s = %g \pm %g\,(%s %s %s)s   %g(   R   R7   R   R   t   replaceR   R   (   R   t   varnameR;   R   R   (    (    s   c:\py\lib\aver.pyt   totexà   s    ++N('   t   __name__t
   __module__t   __doc__R   t   NaNR   R   R   R   R   t   staticmethodR   R   R   R   R   R   R   R!   R"   R$   R)   R*   R,   R-   t   __div__R/   t   __radd__t   __rmul__R0   R1   t   __rdiv__R2   R5   R7   R8   t   FalseR>   RB   (    (    (    s   c:\py\lib\aver.pyR    "   s>   3%																						
	c         C   s$   |  d j o |  |  d d n d S(   s   
    Return sqrt(N/(N-1)) for N > 1, else 1
    This factor can be included in standard deviation calculation to account
    for uncertainty of the mean
    i   g      ð?g      à?(    (   R
   (    (    s   c:\py\lib\aver.pyR   æ   s    c          O   s  t  |  ƒ d j o" t i |  d ƒ o |  d }  n t i |  ƒ } d | j o" | d o | t i | ƒ } n t  | ƒ d j  o' t t i t i t i t i d ƒ SnQ t  | ƒ } t t i | ƒ t i	 | ƒ t
 | ƒ t i | ƒ t i | ƒ | ƒ Sd S(   s$  
    Construct a Mean object from an array of numbers.
    If a single argument is supplied and it is iterable, it is used as
    an array of values, otherwise each argument is one of the values.
    
    Mean.fromarray([1,2,3]) is equivalent to Mean.fromarray(1,2,3)
    
    If a keyword argument 'finites' is specified and is 'True', then all Not-a-Number's
    are discarded from averaging. Other keyword arguments are discarded and not
    taken as numbers to average. A NaN-Mean object is returned if no finite arguments are encountered.
    i   i    t   finitesN(   t   lenR   t   iterablet   asarrayR7   R    RF   R   R   R   R   R   R   (   t   argst   vargst   valueR
   (    (    s   c:\py\lib\aver.pyt   averageî   s    ' 'c          O   sã  t  |  ƒ d j o" t i |  d ƒ o |  d }  n d | j o! | d o t d „  |  ƒ }  n d | j o | d } t  |  ƒ d j  o t ƒ  Sn t i t  |  ƒ g ƒ } t i t  |  ƒ g ƒ } t i t  |  ƒ g ƒ } t i t  |  ƒ g ƒ } t i t  |  ƒ g ƒ } t i t  |  ƒ g ƒ } x¬ t t  |  ƒ ƒ D]˜ }	 t |  |	 t ƒ p t d |	 d ƒ ‚ n |  |	 i	 | |	 <|  |	 i
 | |	 <|  |	 i | |	 <|  |	 i | |	 <|  |	 i | |	 <|  |	 i | |	 <q;W| oT | d }
 t t |
 | ƒ t |
 ƒ t |
 ƒ d t i | ƒ t i | ƒ d ƒ Sn t i | ƒ d j  o d | (d } n t | ƒ } t | | ƒ t | ƒ } t | | d	 | d	 ƒ t | ƒ | d	 } t | | d
 t | ƒ t i | ƒ t i | ƒ | ƒ S(   s,  
    Combine a set of Mean objects representing similar measurements into a single one.
    If all arguments have non-zero number of points '.N', these are used for weighting.
    Otherwise all objects are considered to consist of equal numbers of points.
    
    The function can be invoked in two ways: with a single argument containing
    a list of objects to combine, or one object per argument.

    If a keyword argument 'finites' is specified and is 'True', then all Not-a-Number's
    are discarded from averaging. Other keyword arguments are discarded and not
    taken as numbers to average. A NaN-Mean is returned if no finite arguments are encountered.
    
    If a keyword argument 'weightonstd' is specified and is 'True', then 1/std^2 is used
    as a weight, rather than number of points.
    i   i    RM   c         S   s
   |  i  ƒ  S(    (   R7   (   R?   (    (    s   c:\py\lib\aver.pyt   <lambda>  s    t   weightonstds"   Argument %d of an unsupported typeiþÿÿÿg      à¿i   g      à?(   RN   R   RO   t   filterR    t   zerost   rangeR%   t
   ValueErrorR
   R   R   R   R   R   t   sumR   (   RQ   RR   RV   t   Nst   meanst   rmsdevst   stdst   minst   maxest   it   wt   NtotalR   t   rmsdev2(    (    s   c:\py\lib\aver.pyt   combine  sB    '    
J
.t	   LinearFitc           B   sƒ   e  Z d  Z d „  Z e d d „ ƒ Z d „  Z d „  Z d „  Z	 d „  Z
 d „  Z d „  Z d	 „  Z d
 „  Z e d d d „ Z RS(   s¥   
    Straight line fit y(x) = A*x + B with errorbars
    Keeps the information necessary to reconstruct uncertainties of
    the intercepts of the fit with x=X.
    c         C   sC   | |  _  | |  _ | |  _ | |  _ | |  _ | |  _ | |  _ d S(   s¯   
        Construct a linear fit object. The model is:
        
        y(x) = A*(x-x_mean) + B.
        
        A - slope of the fit
        B - intercept of the fit
        N(   t   At   Bt   A_errt   B_errt   x_meant   x_std2t   chi2(   R   Rh   Ri   Rj   Rk   Rl   Rm   Rn   (    (    s   c:\py\lib\aver.pyR   H  s    							c         C   s   t  i |  ƒ }  t | d t ƒ o{ | d j	 o t d ƒ ‚ n t  i g  } | D] } | | i qQ ~ ƒ } t  i g  } | D] } | | i q~ ~ ƒ } n t  i | ƒ } t |  ƒ d j  o t d ƒ ‚ n t |  ƒ t | ƒ j o t d ƒ ‚ n | d j	 op t  i	 | ƒ o | t  i
 |  i ƒ } n t  i | ƒ } t | ƒ t | ƒ j o t d ƒ ‚ n | d } n t  i
 |  i ƒ } t  i | ƒ } t  i | |  ƒ | } |  | }  t  i | | ƒ | }	 t  i | |  d ƒ | }
 t  i | |  | ƒ | } | |
 } |	 } | d j o| t  i
 |  i ƒ t | |  | | d | ƒ t |  ƒ d d } | d } t  i | ƒ } | d j o
 d	 } qÌd
 } n/ t | |  | | d | ƒ t |  ƒ d } | |
 d } | d } t | | | | | |
 | ƒ S(   s   
        Evaluate a straight line fit to a model y(x) = A*x + B.
        x are considered precise and y uncertain.
        
        A fit is unweighted unless y are 'Mean' objects or 'y_err' are supplied.
        
        Return a LinearFit object
        i    sG   'y_err' should not be specified when 'y' have uncertainties themselves.i   s1   it takes at least 2 points to fit a straight lines   'x' and 'y' are different sizes"   'y' and 'y_err' are different sizeiþÿÿÿg      à?g      ð?g        g      à¿N(   R   RP   R%   R    R8   RZ   R   R   RN   R&   t   onest   shapeR[   Rg   (   R?   t   yt   y_errt   _[1]Rb   t   _[2]Rc   t   sum_wt   mean_xt   mean_yt   mean_x2t   mean_xyRh   Ri   Rn   Rj   Rk   (    (    s   c:\py\lib\aver.pyt   fitY  sL     -1   

B


.
c         C   s   t  |  i |  i ƒ S(   s,   slope of the linear fit with its uncertainty(   R    Rh   Rj   (   R   (    (    s   c:\py\lib\aver.pyt   slope—  s    c         C   sq   t  i | ƒ o# t |  i | ƒ |  i | ƒ ƒ Sn; g  } | D]( } | t |  i | ƒ |  i | ƒ ƒ q> ~ Sd S(   s$   intercept of the linear fit with x=XN(   R   R&   R    t   y_meanRr   (   R   t   XRs   R?   (    (    s   c:\py\lib\aver.pyRq   ™  s    #c         C   sx   t  i | ƒ o< |  i | |  i |  i } t | |  i | ƒ |  i ƒ Sn) g  } | D] } | |  i | ƒ qW ~ Sd S(   s$   intercept of the linear fit with y=YN(   R   R&   Rl   Ri   Rh   R    Rr   R?   (   R   t   Yt   x0Rs   Rq   (    (    s   c:\py\lib\aver.pyR?      s    !c         C   s   |  i  | |  i |  i S(   N(   Rh   Rl   Ri   (   R   R?   (    (    s   c:\py\lib\aver.pyR|   ¨  s    c         C   s%   |  i  d | |  i d |  i d S(   Ni   i   g      à?(   Rk   Rl   Rm   (   R   R?   (    (    s   c:\py\lib\aver.pyRr   «  s    c         O   s+   d d  k  } | i | |  i | ƒ | | Ž S(   Niÿÿÿÿ(   t   pylabt   plotR|   (   R   R?   RQ   RR   R€   (    (    s   c:\py\lib\aver.pyt	   plot_line®  s    c         O   sQ   d d  k  } | i | |  i | ƒ |  i | ƒ |  i | ƒ |  i | ƒ | | Ž S(   Niÿÿÿÿ(   R€   t   fill_betweenR|   Rr   (   R   R?   RQ   RR   R€   (    (    s   c:\py\lib\aver.pyt   plot_envelope²  s    c         C   s   |  i  d t d d d d ƒ S(   NR<   R?   Rq   (   t   strRL   (   R   (    (    s   c:\py\lib\aver.pyR   ¶  s    R?   Rq   c      	   C   sŠ   |  i  ƒ  } |  i d ƒ } | i d j  o | i d 9_ d } n d } d | | i d | ƒ | o d n d | | | i d | ƒ f S(	   Ni    iÿÿÿÿt   -t   +s   %s = (%s)%s%s %s %sR<   s   \times t    (   R{   Rq   R   R>   (   R   R<   R?   Rq   R{   t	   interceptt   isign(    (    s   c:\py\lib\aver.pyR…   ¸  s    
N(   RC   RD   RE   R   RG   R8   Rz   R{   Rq   R?   R|   Rr   R‚   R„   R   RL   R…   (    (    (    s   c:\py\lib\aver.pyRg   A  s   	=								(	   RE   R   R3   t   objectR    R   RT   Rf   Rg   (    (    (    s   c:\py\lib\aver.pys   <module>   s   Ä			: