ó
[™xTc           @   s´   d  d l  m Z d  d l Z d  d l m Z d e f d „  ƒ  YZ d e f d „  ƒ  YZ d e f d	 „  ƒ  YZ d
 e f d „  ƒ  YZ	 d e f d „  ƒ  YZ
 d e f d „  ƒ  YZ d S(   iÿÿÿÿ(   t   divisionN(   t   flext   journaled_non_linear_lsc           B   sG   e  Z d  Z d „  Z d „  Z e d „ Z d „  Z d „  Z d „  Z	 RS(   s   A decorator that keeps the history of the objective, gradient,
  step, etc of an underlying normal equations object. An instance of this
  class is a drop-in replacement of that underlying object, with the
  journaling just mentioned automatically happening behind the scene.
  c         C   sÐ   | |  _  | |  _ t j ƒ  |  j _ | r9 g  |  j _ n d |  j _ t j ƒ  |  j _ | rl g  |  j _ n d |  j _ t j ƒ  |  j _	 t j ƒ  |  j _
 t | d ƒ rÀ t j ƒ  |  j _ n d |  j _ d S(   sí    Decorate the given normal equations. The history will be accumulated
    in relevant attributes of journal. The flags track_xxx specify whether
    to journal the gradient and/or the step, a potentially memory-hungry
    operation.
    t   scale_factorN(   t   actualt   journalR   t   doublet   objective_historyt   gradient_historyt   Nonet   gradient_norm_historyt   step_historyt   step_norm_historyt   parameter_vector_norm_historyt   hasattrt   scale_factor_history(   t   selft   non_linear_lsR   t   track_gradientt
   track_step(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   __init__   s    		c         C   s   t  |  j | ƒ S(   N(   t   getattrR   (   R   t   name(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   __getattr__*   s    c         C   sÛ   |  j  j | ƒ | r d  S|  j j j |  j  j ƒ  ƒ |  j j j |  j  j ƒ  ƒ |  j j j |  j  j	 ƒ  j
 ƒ  ƒ |  j j d  k	 r¦ |  j j j |  j  j	 ƒ  ƒ n  |  j j d  k	 r× |  j j j |  j  j ƒ  ƒ n  d  S(   N(   R   t   build_upR   R   t   appendt   parameter_vector_normR   t	   objectiveR
   t   opposite_of_gradientt   norm_infR   R	   R   R   (   R   t   objective_only(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR   -   s      c         C   sj   |  j  j ƒ  |  j j j |  j  j ƒ  j ƒ  ƒ |  j j d  k	 rf |  j j j |  j  j ƒ  j	 ƒ  ƒ n  d  S(   N(
   R   t   solveR   R   R   t   stept   normR   R	   t	   deep_copy(   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR   :   s    "c         C   s   |  j  j ƒ  d  S(   N(   R   t   step_forward(   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR#   @   s    c         C   s   |  j  ƒ  |  j ƒ  d  S(   N(   R   R#   (   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   solve_and_step_forwardC   s    
(
   t   __name__t
   __module__t   __doc__R   R   t   FalseR   R   R#   R$   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR   
   s   				t
   iterationsc           B   sz   e  Z d  Z e Z e Z e 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 RS(   sì   Iterations to solve a non-linear L.S. minimisation problem.

  It is assumed that the objective function is properly scaled to be
  between 0 and 1 (or approximately so), so that this class can
  meaningfully thresholds the norm of the gradients to watch for
  convergence.

  The interface expected from the normal equations object passed to __init__
  is that of lstbx.non_linear_normal_equations_mixin

  Use classic stopping criteria: c.f. e.g.
  Methods for non-linear least-squares problems,
  K. Madsen, H.B. Nielsen, O. Tingleff,
  http://www2.imm.dtu.dk/pubdb/views/edoc_download.php/3215/pdf/imm3215.pdf

  The do_damping and do_scale_shifts function implements the shelxl damping as
  described here:
  http://shelx.uni-ac.gwdg.de/SHELX/shelx.pdf
  do_scale_shifts aslo compares the maximum shift/esd with
  convergence_as_shift_over_esd and returns boolean to indicate if
  the refinement converged according to this criterion
  These functions do nothing unless called by a derived class
  id   gÇº¸�ðF?i   gñhãˆµøä>c         K   sX   t  j |  | ƒ |  j r, t |  _ |  _ n  t | |  |  j |  j ƒ |  _ |  j ƒ  d S(   s   
    N(	   t   libtbxt   adopt_optional_init_argst	   track_allt   TrueR   R   R   R   t   do(   R   R   t   kwds(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR   k   s    	 	c         C   s,   |  j  } |  j d } | d  k	 o+ | | k S(   Niÿÿÿÿ(   t   gradient_thresholdR
   R	   (   R   t   eps_1t   g(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   has_gradient_converged_to_zerou   s    	c         C   sE   |  j  } | d  k r t S|  j d } |  j d } | | | | k S(   Niÿÿÿÿ(   t   step_thresholdR	   R(   R   R   (   R   t   eps_2t   xt   h(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   had_too_small_a_stepz   s    	 c         C   s*   |  j  j ƒ  } | j | | j ƒ  ƒ d  S(   N(   R   t   normal_matrix_packed_ut%   matrix_packed_u_diagonal_add_in_placet   matrix_packed_u_diagonal(   R   t   valuet   a(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt
   do_damping�   s    c         C   s‰   |  j  j ƒ  } |  j  j ƒ  j ƒ  } t j | t j | ƒ ƒ } t j | ƒ } | |  j k  rb t	 S| | k r… | | } | | 9} n  t
 S(   N(   R   R    t   covariance_matrixR;   R   t   abst   sqrtt   maxt   convergence_as_shift_over_esdR-   R(   (   R   t   max_shift_over_esdR6   t   esdt
   x_over_esdt   max_valt   shift_scale(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   do_scale_shifts…   s    
c         C   s
   t  ‚ d  S(   N(   t   NotImplementedError(   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR.   ‘   s    N(   R%   R&   R'   R(   R   R   R,   t   n_max_iterationsR	   R0   R4   t   damping_valueRD   RC   R   R3   R8   R>   RI   R.   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR)   H   s    	
				t   naive_iterationsc           B   s   e  Z d  „  Z d „  Z RS(   c         C   s|   d |  _  xl |  j  |  j k  rw |  j j ƒ  |  j ƒ  r; Pn  |  j j ƒ  |  j ƒ  rX Pn  |  j j ƒ  |  j  d 7_  q Wd  S(   Ni    i   (   t   n_iterationsRK   R   R   R3   R   R8   R#   (   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR.   —   s    	  c         C   s   d S(   Ns   pure Gauss-Newton(    (   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   __str__¡   s    (   R%   R&   R.   RO   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRM   •   s   	
t   naive_iterations_with_dampingc           B   s   e  Z d  „  Z d „  Z RS(   c         C   s£   d |  _  t } x� |  j  |  j k  rž |  j j ƒ  |  j ƒ  rF t } n  |  j |  j ƒ |  j j	 ƒ  |  j
 ƒ  } |  j j ƒ  |  j  d 7_  | s— | r Pq q Wd  S(   Ni    i   (   RN   R(   RK   R   R   R3   R-   R>   RL   R   R8   R#   (   R   t   do_lastt   step_too_small(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR.   §   s    		 c         C   s   d S(   Ns   pure Gauss-Newton with damping(    (   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRO   µ   s    (   R%   R&   R.   RO   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRP   ¥   s   	t-   naive_iterations_with_damping_and_shift_limitc           B   s   e  Z d  „  Z d „  Z RS(   c         C   s¾   d |  _  t } x¨ |  j  |  j k  r¹ |  j j ƒ  |  j ƒ  rF t } n  |  j |  j ƒ |  j j	 ƒ  |  j
 ƒ  } | sŠ |  j |  j ƒ } n  |  j j ƒ  |  j  d 7_  | s² | r Pq q Wd  S(   Ni    i   (   RN   R(   RK   R   R   R3   R-   R>   RL   R   R8   RI   RD   R#   (   R   RQ   RR   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR.   »   s    		 c         C   s   d S(   Ns0   pure Gauss-Newton with damping and shift scaling(    (   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRO   Ë   s    (   R%   R&   R.   RO   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRS   ¹   s   	t   levenberg_marquardt_iterationsc           B   s9   e  Z d  Z d e j f d „  ƒ  YZ d „  Z d „  Z RS(   gü©ñÒMbP?t   muc           B   s   e  Z d  „  Z d „  Z RS(   c         C   s   |  j  S(   N(   t   _mu(   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   fgetÔ   s    c         C   s   |  j  j | ƒ | |  _ d  S(   N(   t
   mu_historyR   RV   (   R   R<   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   fsetÖ   s    (   R%   R&   RW   RY   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRU   Ó   s   	c   
      C   sÑ  t  j ƒ  |  _ d |  _ d } |  j j ƒ  |  j ƒ  r; d  S|  j j ƒ  } |  j t  j	 | j
 ƒ  ƒ |  _ xa|  j |  j k  rÌ| j |  j ƒ |  j j ƒ  } |  j j ƒ  } |  j j ƒ  |  j ƒ  rÊ Pn  |  j d 7_ |  j j ƒ  } d | j |  j | | ƒ } |  j j ƒ  |  j j d t ƒ |  j j ƒ  } | | } | | }	 |	 d k r–|  j ƒ  rePn  |  j t	 d d d |	 d d ƒ 9_ d } n& |  j j ƒ  |  j | 9_ | d 9} |  j j ƒ  ql Wd  S(   Ni    i   i   g      à?R   i   gUUUUUUÕ?(   R   R   RX   RN   R   R   R3   R9   t   tauRB   R;   RU   RK   R:   R   R   R   R8   R    t   dotR#   R-   t   step_backward(
   R   t   nuR=   R   R2   R7   t   expected_decreaset   objective_newt   actual_decreaset   rho(    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyR.   Ú   s@    	  

 (	
c         C   s   d S(   Ns   Levenberg-Marquardt(    (   R   (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRO   ú   s    (   R%   R&   RZ   R*   t   propertyRU   R.   RO   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyRT   Ï   s   	 (   t
   __future__R    R*   t   scitbx.array_familyR   t   objectR   R)   RM   RP   RS   RT   (    (    (    sN   /public2/ftp/pub/ccp4/6.5/ccp4-6.5/lib/py2/scitbx/lstbx/normal_eqns_solving.pyt   <module>   s   >M