U
    f»{jÄB  ã                	   @   sò   d Z ddlZddlmZ ddlmZ ddlmZm	Z	m
Z
mZ ddlmZ ddlmZmZmZmZmZmZmZmZmZmZmZmZmZ ed#dd„ƒZd$dd„Zd%dd„Zed&dd„ƒZed'dd„ƒZ ed(dd„ƒZ!dd„ Z"dd„ Z#ed)d!d"„ƒZ$dS )*z+Some utility functions for rank estimation.é    Né   )Ú_handle_default)Ú_simplify_info)Ú_picks_by_typeÚ	pick_infoÚpick_channels_covÚ_picks_to_idx)Úmake_projector)ÚloggerÚ_compute_row_normsÚ_plÚ_validate_typeÚ_apply_scaling_covÚ_undo_scaling_covÚ_scaled_arrayÚwarnÚ_check_rankÚ_on_missingÚverboseÚ_check_on_missingÚfill_docÚautoFTÚabsolutec           
      C   sd   ddl m} |r6|  ¡ } t| ƒ}| |dd…tjf  } | | ¡}t|||ƒ}	|dkr\|	|fS |	S dS )a9  Estimate the rank of data.

    This function will normalize the rows of the data (typically
    channels or vertices) such that non-zero singular values
    should be close to one.

    Parameters
    ----------
    data : array
        Data to estimate the rank of (should be 2-dimensional).
    %(tol_rank)s
    return_singular : bool
        If True, also return the singular values that were used
        to determine the rank.
    norm : bool
        If True, data will be scaled by their estimated row-wise norm.
        Else data are assumed to be scaled. Defaults to True.
    %(tol_kind_rank)s

    Returns
    -------
    rank : int
        Estimated rank of the data.
    s : array
        If return_singular is True, the singular values that were
        thresholded to determine the rank are also returned.
    r   )ÚlinalgNT)Zscipyr   Úcopyr   ÚnpZnewaxisZsvdvalsÚ_estimate_rank_from_s)
ÚdataÚtolÚreturn_singularÚnormÚtol_kindr   r   ZnormsÚsÚrank© r$   úG/var/www/html/bwave/python/venv/lib/python3.8/site-packages/mne/rank.pyÚestimate_rank   s    
r&   c                 C   sÞ   t  | t¡} t j| dd�}t|tƒr˜|dkr:td|f ƒ‚|dkrRt  t j¡j	}nt  t j
¡j	}| jd | | }| jdkrÈt d||t| ƒ|f ¡ n0t|t jƒr°|jjdksÈt|ƒ}|d	krÈ|| }t j| |kdd�}|S )
a=  Estimate the rank of a matrix from its singular values.

    Parameters
    ----------
    s : ndarray, shape (..., ndim)
        The singular values of the matrix.
    tol : float | 'auto'
        Tolerance for singular values to consider non-zero in calculating the
        rank. Can be 'auto' to use the same thresholding as
        ``scipy.linalg.orth`` (assuming np.float64 datatype) adjusted
        by a factor of 2.
    tol_kind : str
        Can be "absolute" or "relative".

    Returns
    -------
    rank : ndarray, shape (...)
        The estimated rank.
    éÿÿÿÿ©Zaxis)r   Úfloat32z#tol must be "auto" or float, got %rr)   r   zJ    Using tolerance %0.2g (%0.2g eps * %d dim * %0.2g  max singular value)ÚfÚrelative)r   ÚarrayÚfloatZamaxÚ
isinstanceÚstrÚ
ValueErrorZfinfor)   ÚepsZfloat64ÚshapeÚndimr
   ÚinfoÚlenZndarrayZdtypeÚkindÚsum)r"   r   r!   Zmax_sr1   r#   r$   r$   r%   r   ?   s&    

ÿr   ç-Cëâ6?r    c                 C   s:   |dkrt | j||d�}t| | d t| j|ƒ||d|ƒS )z/Aid the transition away from raw.estimate_rank.N)Úwith_ref_megr   F)r   r4   Ú_estimate_rank_meeg_signalsr   )ÚrawÚpicksr   Úscalingsr9   r!   r$   r$   r%   Ú_estimate_rank_rawn   s    
 
   þr>   c           
   	   C   s�   t |ƒ}| jd | jd k r$tdƒ t| ||ƒ� t| |d||d�}W 5 Q R X t|tƒr`|d n|}d tt	|Ž ƒd ¡}	t
 d|	|f ¡ |S )aæ  Estimate rank for M/EEG data.

    Parameters
    ----------
    data : np.ndarray of float, shape(n_channels, n_samples)
        The M/EEG signals.
    %(info_not_none)s
    scalings : dict | 'norm' | np.ndarray | None
        The rescaling method to be applied. If dict, it will override the
        following default dict:

            dict(mag=1e15, grad=1e13, eeg=1e6)

        If 'norm' data will be scaled by channel-wise norms. If array,
        pre-specified norms will be used. If None, no scaling will be applied.
    tol : float | str
        Tolerance. See ``estimate_rank``.
    return_singular : bool
        If True, also return the singular values that were used
        to determine the rank.
    tol_kind : str
        Tolerance kind. See ``estimate_rank``.

    Returns
    -------
    rank : int
        Estimated rank of the data.
    s : array
        If return_singular is True, the singular values that were
        thresholded to determine the rank are also returned.
    r   r   úOYou've got fewer samples than channels, your rank estimate might be inaccurate.F)r   r    r   r!   ú + ú    Estimated rank (%s): %d)r   r2   r0   r   r&   r.   ÚtupleÚjoinÚlistÚzipr
   r4   )
r   r4   r=   r   r   r!   Ú
picks_listÚoutr#   Úch_typer$   r$   r%   r:   y   s    "þr:   c           
      C   sœ   t |g d�}td|ƒ}t| ||ƒ | jd | jd k r>tdƒ t| |d|d�}t|tƒr`|d n|}d t	t
|Ž ƒd ¡}	t d	|	|f ¡ t| ||ƒ |S )
aÉ  Estimate rank of M/EEG covariance data, given the covariance.

    Parameters
    ----------
    data : np.ndarray of float, shape (n_channels, n_channels)
        The M/EEG covariance.
    %(info_not_none)s
    scalings : dict | 'norm' | np.ndarray | None
        The rescaling method to be applied. If dict, it will override the
        following default dict:

            dict(mag=1e12, grad=1e11, eeg=1e5)

        If 'norm' data will be scaled by channel-wise norms. If array,
        pre-specified norms will be used. If None, no scaling will be applied.
    tol : float | str
        Tolerance. See ``estimate_rank``.
    return_singular : bool
        If True, also return the singular values that were used
        to determine the rank.

    Returns
    -------
    rank : int
        Estimated rank of the data.
    s : array
        If return_singular is True, the singular values that were
        thresholded to determine the rank are also returned.
    ©ÚexcludeÚscalings_cov_rankr   r   r?   F)r   r    r   r@   rA   )r   r   r   r2   r0   r&   r.   rB   rC   rD   rE   r
   r4   r   )
r   r4   r=   r   r   r   rF   rG   r#   rH   r$   r$   r%   Ú_estimate_rank_meeg_cov©   s     
ÿrL   ú/You should use data-based rank estimate insteadc           	      C   sà   ddl m} t| |ƒr| n| j}~ | dg ¡}t|ƒdkrDt d¡ t|ƒdkspd|d kspd|d d d kr|td	| ƒ‚|d }|d }|d d }|d d
 d }|t|d d d|… ƒ|d d d|…  ¡  8 }|S )aa  Look up rank from SSS data.

    .. note::
        Throws an error if SSS has not been applied.

    Parameters
    ----------
    inst : instance of Raw, Epochs or Evoked, or Info
        Any MNE object with an .info attribute

    Returns
    -------
    rank : int
        The numerical rank as predicted by the number of SSS
        components.
    r   )ÚInfoZproc_historyz,Found multiple SSS records. Using the first.r   Úmax_infoZin_orderZsss_infoz@Could not find Maxfilter information in info["proc_history"]. %sé   Ú
componentsN)	Úio.meas_inforN   r.   r4   Úgetr5   r
   r0   r7   )	ÚinstÚmsgr   rN   r4   Z	proc_inforO   ZinsideZnfreer$   r$   r%   Ú_get_rank_sssØ   s(    
ÿÿÿrV   c                 C   s8   |dkr0|dkr0z
t | ƒW S  tk
r.   Y nX t|ƒS )N)ÚmegÚmagZgradÚfull)rV   r0   r5   )r4   rH   r<   r#   r$   r$   r%   Ú
_info_rank  s    
rZ   c                 O   s   t t| f|ž|Ž ¡ ƒS )z#Wrap compute_rank but yield an int.)r7   Úcompute_rankÚvalues)rT   ÚargsÚkwargsr$   r$   r%   Ú_compute_rank_int
  s    r_   Úignorec	                    sZ  ddl m}	 ddlm}
 ddlm} t|ƒ}td|ƒ}t|dƒ t	| |ƒr¾d}ˆ dkr^t
d	ƒ‚ˆ  ¡ ‰ g ˆ d
< t| t| d ƒtˆ d ƒ@ g d�} ˆ d | d krÈtˆ ‡ fdd„| d D ƒƒ‰ n
| j‰ d}t d||f ¡ t|ttdfdƒ t	|tƒ�rd}|}tƒ }nd}|dk�rtƒ }tˆ ƒ}tˆ ddd
d�}|D �]\}}d}||k�rÆ|| t|ƒk�rŠt
dt|ƒ› d|| › dt|ƒ› d�ƒ‚d}|dk�r8|dk�r8|dk�r8t	| |ƒ�r8| d �rÆ�q8‡ fdd„|D ƒ}t|ƒ}|�rütˆ d  |ƒ\}}}nd!\}}|dk�rptˆ |||ƒ}|d"k�rV||8 }t d#| ¡ ||t|ƒ|t|ƒf ¡ nt d$| ¡ |f ¡ �nÐ|dk�s~t‚t	| |	|
fƒ�rþt	| |	ƒ�rª| j|d%d&�}n(|  ¡ dd…|dd…f }tj|dd'�}|�rät  ||¡}t!|t||ƒ||d|ƒ}nôt	| |ƒ�st‚| d �r2| d | d(k "¡ | }nÀ| d | dd…|f }|�rft  t  ||¡|j#¡}t$|t||ƒ||d|d)�\}}||k�rò||d  ||| d   }|d*k�r8d+t|ƒ› d|| › d,|› d-t %|¡d.›d/�	}t&||dƒ �q8tˆ ||dƒ}t d0| ¡ ||t|ƒ|t|ƒf ¡ ||k�r@t'd1||f ƒ ||k�r8|||< �q8|S )2ak  Compute the rank of data or noise covariance.

    This function will normalize the rows of the data (typically
    channels or vertices) such that non-zero singular values
    should be close to one.

    Parameters
    ----------
    inst : instance of Raw, Epochs, or Covariance
        Raw measurements to compute the rank from or the covariance.
    %(rank_none)s
    scalings : dict | None (default None)
        Defaults to ``dict(mag=1e15, grad=1e13, eeg=1e6)``.
        These defaults will scale different channel types
        to comparable values.
    %(info)s Only necessary if ``inst`` is a :class:`mne.Covariance`
        object (since this does not provide ``inst.info``).
    %(tol_rank)s
    proj : bool
        If True, all projs in ``inst`` and ``info`` will be applied or
        considered when ``rank=None`` or ``rank='info'``.
    %(tol_kind_rank)s
    %(on_rank_mismatch)s
    %(verbose)s

    Returns
    -------
    rank : dict
        Estimated rank of the data for each channel type.
        To get the total rank, you can use ``sum(rank.values())``.

    Notes
    -----
    .. versionadded:: 0.18
    r   )ÚBaseRaw)Ú
BaseEpochs)Ú
CovariancerK   Úon_rank_mismatchZ
covarianceNz,info cannot be None if inst is a Covariance.ZbadsÚnamesÚch_namesrI   c                    s   g | ]}ˆ d    |¡‘qS ©rf   )Úindex)Ú.0Úname©r4   r$   r%   Ú
<listcomp>K  s   ÿz compute_rank.<locals>.<listcomp>r   z#Computing rank from %s with rank=%rr#   r4   Z	estimatedTF)Zmeg_combinedZref_megrJ   zrank[z]=z! exceeds the number of channels (ú)r`   rW   Zdiagc                    s   g | ]}ˆ d  | ‘qS rg   r$   )ri   Úpickrk   r$   r%   rl   p  s     Zprojs)Nr   rY   z<    %s: rank %d after %d projector%s applied to %d channel%sz    %s: rank %d from infoZomit)Zreject_by_annotationr(   r   )r   r   éd   zThe passed rank[z5 exceeds the estimated rank of the noise covariance (zK) leading to a potential increase in noise during whitening by a factor of z0.1gzZ. Ensure that the rank correctly corresponds to that of the given noise covariance matrix.zC    %s: rank %d computed from %d data channel%s with %d projector%szÇSomething went wrong in the data-driven estimation of the data rank as it exceeds the theoretical rank from the info (%d > %d). Consider setting rank to "auto" or setting it explicitly as an integer.)(Zio.basera   Zepochsrb   Ú rc   r   r   r   r.   r0   r   r   Úsetr   r4   r
   r   r/   Údictr   r   r5   Úreprr	   rZ   Úupperr   ÚAssertionErrorÚget_datar   ZconcatenateÚdotr:   r7   ÚTrL   Úsqrtr   r   )rT   r#   r=   r4   r   Zprojr!   rd   r   ra   rb   rc   Z	inst_typeZ	rank_typeZ	info_typeZsimple_inforF   rH   r<   Zest_verboserf   Zn_chanZproj_opZn_projÚ_Z	this_rankr   ZsingÚratiorU   Zthis_info_rankr$   rk   r%   r[     sþ    '


  ÿÿ

ÿ
"ÿ
ÿþýü

   ÿþ
ÿ
    þ
    þ


,ÿ	ÿ ÿþ
ü
r[   )r   FTr   N)r   r   )Nr8   r    Fr   )r   Fr   )r   FN)rM   N)NNNr   Tr   r`   N)%Ú__doc__Únumpyr   Údefaultsr   rR   r   Zio.pickr   r   r   r   Zio.projr	   Úutilsr
   r   r   r   r   r   r   r   r   r   r   r   r   r&   r   r>   r:   rL   rV   rZ   r_   r[   r$   r$   r$   r%   Ú<module>   sN   <    ÿ*
/    ÿ
    ÿ/    ÿ.  ÿ(	       þ