
    Џkh%                     |    d dl mZ d dlZd dlmZmZ d dlmZm	Z	 ddl
mZmZ dgZ	 	 ddZ ed	d
dd      d        Zy)    )IterableN)_asarray_validated_apply_over_batch)
block_diagLinAlgError   )_compute_lworkget_lapack_funcscossinc           
         |s|r|dn
t        |      }|dn
t        |      }t        | d      } t        j                  | j                  dd  st        d| j                  dd        | j                  d   }||k\  s|dk  rt        d| d	| j                  d    d
      ||k\  s|dk  rt        d| d| j                  d    d
      | dd|d|f   | dd||df   | d|dd|f   | d|d|df   f\  }}	}
}nNt        | t              st        d      t        |       dk7  rt        dt        |              d | D        \  }}	}
}t        ||	|
|||||      S )u  
    Compute the cosine-sine (CS) decomposition of an orthogonal/unitary matrix.

    X is an ``(m, m)`` orthogonal/unitary matrix, partitioned as the following
    where upper left block has the shape of ``(p, q)``::

                                   ┌                   ┐
                                   │ I  0  0 │ 0  0  0 │
        ┌           ┐   ┌         ┐│ 0  C  0 │ 0 -S  0 │┌         ┐*
        │ X11 │ X12 │   │ U1 │    ││ 0  0  0 │ 0  0 -I ││ V1 │    │
        │ ────┼──── │ = │────┼────││─────────┼─────────││────┼────│
        │ X21 │ X22 │   │    │ U2 ││ 0  0  0 │ I  0  0 ││    │ V2 │
        └           ┘   └         ┘│ 0  S  0 │ 0  C  0 │└         ┘
                                   │ 0  0  I │ 0  0  0 │
                                   └                   ┘

    ``U1``, ``U2``, ``V1``, ``V2`` are square orthogonal/unitary matrices of
    dimensions ``(p,p)``, ``(m-p,m-p)``, ``(q,q)``, and ``(m-q,m-q)``
    respectively, and ``C`` and ``S`` are ``(r, r)`` nonnegative diagonal
    matrices satisfying ``C^2 + S^2 = I`` where ``r = min(p, m-p, q, m-q)``.

    Moreover, the rank of the identity matrices are ``min(p, q) - r``,
    ``min(p, m - q) - r``, ``min(m - p, q) - r``, and ``min(m - p, m - q) - r``
    respectively.

    X can be supplied either by itself and block specifications p, q or its
    subblocks in an iterable from which the shapes would be derived. See the
    examples below.

    Parameters
    ----------
    X : array_like, iterable
        complex unitary or real orthogonal matrix to be decomposed, or iterable
        of subblocks ``X11``, ``X12``, ``X21``, ``X22``, when ``p``, ``q`` are
        omitted.
    p : int, optional
        Number of rows of the upper left block ``X11``, used only when X is
        given as an array.
    q : int, optional
        Number of columns of the upper left block ``X11``, used only when X is
        given as an array.
    separate : bool, optional
        if ``True``, the low level components are returned instead of the
        matrix factors, i.e. ``(u1,u2)``, ``theta``, ``(v1h,v2h)`` instead of
        ``u``, ``cs``, ``vh``.
    swap_sign : bool, optional
        if ``True``, the ``-S``, ``-I`` block will be the bottom left,
        otherwise (by default) they will be in the upper right block.
    compute_u : bool, optional
        if ``False``, ``u`` won't be computed and an empty array is returned.
    compute_vh : bool, optional
        if ``False``, ``vh`` won't be computed and an empty array is returned.

    Returns
    -------
    u : ndarray
        When ``compute_u=True``, contains the block diagonal orthogonal/unitary
        matrix consisting of the blocks ``U1`` (``p`` x ``p``) and ``U2``
        (``m-p`` x ``m-p``) orthogonal/unitary matrices. If ``separate=True``,
        this contains the tuple of ``(U1, U2)``.
    cs : ndarray
        The cosine-sine factor with the structure described above.
         If ``separate=True``, this contains the ``theta`` array containing the
         angles in radians.
    vh : ndarray
        When ``compute_vh=True`, contains the block diagonal orthogonal/unitary
        matrix consisting of the blocks ``V1H`` (``q`` x ``q``) and ``V2H``
        (``m-q`` x ``m-q``) orthogonal/unitary matrices. If ``separate=True``,
        this contains the tuple of ``(V1H, V2H)``.

    Notes
    -----
    The documentation is written assuming array arguments are of specified
    "core" shapes. However, array argument(s) of this function may have additional
    "batch" dimensions prepended to the core shape. In this case, the array is treated
    as a batch of lower-dimensional slices; see :ref:`linalg_batch` for details.

    References
    ----------
    .. [1] Brian D. Sutton. Computing the complete CS decomposition. Numer.
           Algorithms, 50(1):33-65, 2009.

    Examples
    --------
    >>> import numpy as np
    >>> from scipy.linalg import cossin
    >>> from scipy.stats import unitary_group
    >>> x = unitary_group.rvs(4)
    >>> u, cs, vdh = cossin(x, p=2, q=2)
    >>> np.allclose(x, u @ cs @ vdh)
    True

    Same can be entered via subblocks without the need of ``p`` and ``q``. Also
    let's skip the computation of ``u``

    >>> ue, cs, vdh = cossin((x[:2, :2], x[:2, 2:], x[2:, :2], x[2:, 2:]),
    ...                      compute_u=False)
    >>> print(ue)
    []
    >>> np.allclose(x, u @ cs @ vdh)
    True

    Nr   T)check_finitez=Cosine Sine decomposition only supports square matrices, got r   z
invalid p=z, 0<p<z
 must holdz
invalid q=z, 0<q<.zJWhen p and q are None, X must be an Iterable containing the subblocks of X   z?When p and q are None, exactly four arrays should be in X, got c              3   F   K   | ]  }t        j                  |        y w)N)np
atleast_2d).0xs     W/var/www/teggl/fontify/venv/lib/python3.12/site-packages/scipy/linalg/_decomp_cossin.py	<genexpr>zcossin.<locals>.<genexpr>   s     :1bmmA.:s   !)separate	swap_sign	compute_u
compute_vh)
intr   r   equalshape
ValueError
isinstancer   len_cossin)Xpqr   r   r   r   mx11x12x21x22s               r   r   r      s   T 	AAAAAqt4xx& //0wwrs|n> ? ?GGBK6Q!Vz!F1772;-zJKK6Q!Vz!F1772;-zJKKRaR!naRaRnQR!naQRn>S#s8$ : ; 	; q6Q; 558VH> ? ?::S#s3S#I&:? ?    )r&      )r'   r+   )r(   r+   )r)   r+   c                 6   t        g d| |||g      D ]%  \  }}	|	j                  d   dk(  st        | d       | j                  \  }
}|j                  \  }}|j                  |
|fk7  rt        d|
|f d|j                         |j                  ||fk7  rt        d||f d|j                         |
|z   ||z   k7  rt        d|
|z    d	||z    d
      |
|z   }t        | |||fD cg c]  }t	        j
                  |       c}      }|rdnd}t        ||dz   g| |||g      \  }}t        |||
|      }|r|d   |d   dnd|i} |d| |||||||d|d
|^ }}}}}}}|j                  |z   }|dk  rt        d|  d|       |dkD  rt        | d|       |r	||f|||ffS t        ||      }t        ||      }t	        j                  t	        j                  |            } t	        j                  t	        j                  |            }!t        |
|||
z
  ||z
        }"t        |
|      |"z
  }#t        |
||z
        |"z
  }$t        ||
z
  |      |"z
  }%t        ||
z
  ||z
        |"z
  }&t	        j                  t	        j                   |#|$|%|&|"g      |j"                        }'t	        j$                  ||f|j"                        }(|'d |#d |#f   |(d |#d |#f<   |#|"z   })|#|"z   |$z   }*|#|%z   |&z   d|"z  z   }+|#|%z   |&z   d|"z  z   |$z   },|r|'d |$d |$f   n|'d |$d |$f    |(|)|*|+|,f<   |
|&z   |"z   })|
|&z   |"z   |%z   }*|#|"z   }+|#|"z   |%z   },|r|'d |%d |%f    n
|'d |%d |%f   |(|)|*|+|,f<   |'d |&d |&f   |(|
|
|&z   |||&z   f<   | |(|#|#|"z   |#|#|"z   f<   | |(|
|&z   |
|&z   |"z   |#|"z   |%z   |&z   d|"z  |#z   |%z   |&z   f<   |#})|#|"z   }*|#|%z   |&z   |"z   }+|#|%z   |&z   d|"z  z   },|r|!n|! |(|)|*|+|,f<   |r|! n|!|(|
|&z   |
|&z   |"z   |#|#|"z   f<   ||(|fS c c}w )N)r&   r'   r(   r)   r   r   z can't be emptyz Invalid x12 dimensions: desired z, got z Invalid x21 dimensions: desired zWThe subblocks have compatible sizes but don't form a square array (instead they form a r   z5 array). This might be due to missing p, q arguments.uncsdorcsd_lwork)r%   r#   r$   )lworklrworkr0   F)
r&   r'   r(   r)   
compute_u1
compute_u2compute_v1tcompute_v2ttranssignszillegal value in argument z of internal z did not converge: )dtyper+    )zipr   r   anyr   iscomplexobjr
   r	   typecoder   r   diagcossinmineyemaxr8   zeros)-r&   r'   r(   r)   r   r   r   r   nameblockr#   r$   mmpmmqr%   r   cplxdrivercsd	csd_lworkr0   
lwork_args_thetau1u2v1hv2hinfomethod_nameUVDHcsrn11n12n21n22IdCSxsxeysyes-                                                r   r!   r!      s    7c3/1 7e;;q>Qv_5667 99DAqyyHC
yyQH;QH: F  #		{, - 	- yyS!H;S!H: F  #		{, - 	- 	3w!c' #gYaCy 1;; < 	<
 	
CAS#sC,@Aq"ABDW'F%vv/@&A'*Cc&:<NC9Q!4E=AE!Ha9E" (+ ):#37@7@8B8B27y): /9):%Qr2sC ,,'Kax5teW =((3}6 7 	7ax[M)<TFCDDBxc
**2rA
S#
C 	uA
uAAq!a%QA
a)a-C
aQ-!
C
a!eQ-!
C
a!eQU
a
C	S#sA./u{{	CB	1a&	,Bdsd
^BttTcTzN	qB	q3B	sS1q5	 B	sS1q5	 3	&B*34C4#:"TcT4C4Z.Br2vr"u}	
S1B	
S1u	B	qB	q3B*34C4#:DSD$3$JBr"ube|!$3$*~BqSy!AG)#$Bs37{CaK KLBq3wq3w{C!GcMC/Ac0AC0GGGH	B	qB	sS1	B	sS1q5	 B%qA2Br"ube|1:A2Bq3wq3w{CaK'(b#:C Bs   *P)NNFFTT)collections.abcr   numpyr   scipy._lib._utilr   r   scipy.linalgr   r   lapackr	   r
   __all__r   r!   r9   r*   r   <module>rk      sL    $  B 0 4* (-7;C?L :z:zBZ CZr*   