a
    RG5d^8                     @   s   d dl mZ d dlmZmZ d dlmZ d dlmZ d dl	m
Z
 d dlmZ d dlmZ d dlmZ d d	lmZmZ d d
lmZmZmZmZmZmZ d dlmZ dd ZG dd deZdd Zdd Z dd Z!G dd deZ"dS )    )Counter)Mulsympify)Add)ExprBuilder)default_sort_key)log)
ShapeError)
MatrixExpr)
ZeroMatrix	OneMatrix)unpackflatten	conditionexhaustrm_idsort)sympy_deprecation_warningc                  G   sF   | st dt|   t| dkr(| d S dd | D } t|   S dS )au  
    Return the elementwise (aka Hadamard) product of matrices.

    Examples
    ========

    >>> from sympy import hadamard_product, MatrixSymbol
    >>> A = MatrixSymbol('A', 2, 3)
    >>> B = MatrixSymbol('B', 2, 3)
    >>> hadamard_product(A)
    A
    >>> hadamard_product(A, B)
    HadamardProduct(A, B)
    >>> hadamard_product(A, B)[0, 1]
    A[0, 1]*B[0, 1]
    z#Empty Hadamard product is undefined   r   c                 S   s   g | ]}|j s|qS  )is_Identity.0ir   r   _/var/www/html/django/DPS/env/lib/python3.9/site-packages/sympy/matrices/expressions/hadamard.py
<listcomp>(       z$hadamard_product.<locals>.<listcomp>N)	TypeErrorvalidatelenHadamardProductdoit)matricesr   r   r   hadamard_product   s    r#   c                       s`   e Zd ZdZdZddd fdd
Zedd	 Zd
d Zdd Z	dd Z
dd Zdd Z  ZS )r    a(  
    Elementwise product of matrix expressions

    Examples
    ========

    Hadamard product for matrix symbols:

    >>> from sympy import hadamard_product, HadamardProduct, MatrixSymbol
    >>> A = MatrixSymbol('A', 5, 5)
    >>> B = MatrixSymbol('B', 5, 5)
    >>> isinstance(hadamard_product(A, B), HadamardProduct)
    True

    Notes
    =====

    This is a symbolic object that simply stores its argument without
    evaluating it. To actually compute the product, use the function
    ``hadamard_product()`` or ``HadamardProduct.doit``
    TFN)evaluatecheckc                   sl   t tt|}|d ur$tdddd |dv r6t|  ntdddd t j| g|R  }|rh|jdd}|S )	NzjPassing check to HadamardProduct is deprecated and the check argument will be removed in a future version.z1.11z,remove-check-argument-from-matrix-operations)deprecated_since_versionactive_deprecations_target)TNzpPassing check=False to HadamardProduct is deprecated and the check argument will be removed in a future version.F)deep)listmapr   r   r   super__new__r!   )clsr$   r%   argsobj	__class__r   r   r,   D   s$    
zHadamardProduct.__new__c                 C   s   | j d jS Nr   )r.   shapeselfr   r   r   r3   Y   s    zHadamardProduct.shapec                    s   t  fdd| jD  S )Nc                    s    g | ]}|j  fi qS r   )_entryr   argr   jkwargsr   r   r   ^   r   z*HadamardProduct._entry.<locals>.<listcomp>)r   r.   )r5   r   r:   r;   r   r9   r   r6   ]   s    zHadamardProduct._entryc                 C   s    ddl m} ttt|| j S Nr   )	transpose)$sympy.matrices.expressions.transposer=   r    r)   r*   r.   r5   r=   r   r   r   _eval_transpose`   s    zHadamardProduct._eval_transposec                    s   | j fdd| jD  }ddlm  ddlm}  fdd|jD rfdd|jD }|dd t D j| j }t	|g|  }t
|S )	Nc                    s   g | ]}|j f i  qS r   )r!   r   )hintsr   r   r   e   r   z(HadamardProduct.doit.<locals>.<listcomp>r   
MatrixBase)ImmutableMatrixc                    s   g | ]}t | r|qS r   )
isinstancer   rB   r   r   r   i   r   c                    s   g | ]}| vr|qS r   r   r   )explicitr   r   r   k   r   c                 S   s   g | ]}t |qS r   )r   fromiterr   r   r   r   r   l   s   )funcr.   sympy.matrices.matricesrC   sympy.matrices.immutablerD   zipreshaper3   r    canonicalize)r5   rA   exprrD   	remainderZexpl_matr   )rC   rF   rA   r   r!   d   s    zHadamardProduct.doitc                 C   sd   g }t | j}tt|D ]>}|d | || |g ||d d   }|t|  qt|S Nr   )	r)   r.   ranger   diffappendr#   r   rG   )r5   xtermsr.   r   factorsr   r   r   _eval_derivatives   s    
,z HadamardProduct._eval_derivativec                    s<  ddl m} ddl m} ddlm} fddt jD }g }|D ]} jd | } j|d d  }	 j| }
t|	|  }dd	g} fd
dt|D }|
D ]}|j	|j
 }|j	|j }t|t|t||g|t||ggg|}|jd jd j|_d|_|jd jd j|_d|_|g|_	|| qqD|S )Nr   ArrayDiagonalArrayTensorProduct_make_matrixc                    s   g | ]\}}|  r|qS r   )has)r   r   r8   rT   r   r   r      r   zAHadamardProduct._eval_derivative_matrix_lines.<locals>.<listcomp>r   )r            c                    s"   g | ]\}} j | d kr|qS r   )r3   r   r:   er4   r   r   r      r   r`   )0sympy.tensor.array.expressions.array_expressionsrY   r[   "sympy.matrices.expressions.matexprr]   	enumerater.   _eval_derivative_matrix_linesr#   _lines_first_line_index_second_line_indexr   _first_pointer_parent_first_pointer_index_second_pointer_parent_second_pointer_indexrS   )r5   rT   rY   r[   r]   
with_x_indlinesind	left_args
right_argsdZhadamdiagonalr   l1l2subexprr   )r5   rT   r   rj   {   sF    

	z-HadamardProduct._eval_derivative_matrix_lines)__name__
__module____qualname____doc__Zis_HadamardProductr,   propertyr3   r6   r@   r!   rW   rj   __classcell__r   r   r0   r   r    ,   s   
r    c                  G   sT   t dd | D std| d }| dd  D ] }|j|jkr.td||f q.d S )Nc                 s   s   | ]}|j V  qd S N)	is_Matrixr7   r   r   r   	<genexpr>   r   zvalidate.<locals>.<genexpr>z Mix of Matrix and Scalar symbolsr   r   z"Matrices %s and %s are not aligned)allr   r3   r	   )r.   ABr   r   r   r      s    r   c                 C   s   t dd t}t|}|| } t dd tdd }|| } dd }t dd |}|| } t| trt| j}g }| D ],\}}|dkr|	| qz|	t
|| qzt| } t d	d tt}|| } t| } | S )
a  Canonicalize the Hadamard product ``x`` with mathematical properties.

    Examples
    ========

    >>> from sympy import MatrixSymbol, HadamardProduct
    >>> from sympy import OneMatrix, ZeroMatrix
    >>> from sympy.matrices.expressions.hadamard import canonicalize
    >>> from sympy import init_printing
    >>> init_printing(use_unicode=False)

    >>> A = MatrixSymbol('A', 2, 2)
    >>> B = MatrixSymbol('B', 2, 2)
    >>> C = MatrixSymbol('C', 2, 2)

    Hadamard product associativity:

    >>> X = HadamardProduct(A, HadamardProduct(B, C))
    >>> X
    A.*(B.*C)
    >>> canonicalize(X)
    A.*B.*C

    Hadamard product commutativity:

    >>> X = HadamardProduct(A, B)
    >>> Y = HadamardProduct(B, A)
    >>> X
    A.*B
    >>> Y
    B.*A
    >>> canonicalize(X)
    A.*B
    >>> canonicalize(Y)
    A.*B

    Hadamard product identity:

    >>> X = HadamardProduct(A, OneMatrix(2, 2))
    >>> X
    A.*1
    >>> canonicalize(X)
    A

    Absorbing element of Hadamard product:

    >>> X = HadamardProduct(A, ZeroMatrix(2, 2))
    >>> X
    A.*0
    >>> canonicalize(X)
    0

    Rewriting to Hadamard Power

    >>> X = HadamardProduct(A, A, A)
    >>> X
    A.*A.*A
    >>> canonicalize(X)
     .3
    A

    Notes
    =====

    As the Hadamard product is associative, nested products can be flattened.

    The Hadamard product is commutative so that factors can be sorted for
    canonical form.

    A matrix of only ones is an identity for Hadamard product,
    so every matrices of only ones can be removed.

    Any zero matrix will make the whole product a zero matrix.

    Duplicate elements can be collected and rewritten as HadamardPower

    References
    ==========

    .. [1] https://en.wikipedia.org/wiki/Hadamard_product_(matrices)
    c                 S   s
   t | tS r   rE   r    r_   r   r   r   <lambda>  r   zcanonicalize.<locals>.<lambda>c                 S   s
   t | tS r   r   r_   r   r   r   r     r   c                 S   s
   t | tS r   )rE   r   r_   r   r   r   r     r   c                 S   s&   t dd | jD rt| j S | S d S )Nc                 s   s   | ]}t |tV  qd S r   )rE   r   )r   cr   r   r   r     r   z/canonicalize.<locals>.absorb.<locals>.<genexpr>)anyr.   r   r3   r_   r   r   r   absorb  s    
zcanonicalize.<locals>.absorbc                 S   s
   t | tS r   r   r_   r   r   r   r     r   r   c                 S   s
   t | tS r   r   r_   r   r   r   r   ,  r   )r   r   r   r   rE   r    r   r.   itemsrS   HadamardPowerr   r   r   )rT   rulefunr   ZtallyZnew_argbaseexpr   r   r   rM      s@    S


rM   c                 C   sB   t | } t |}|dkr| S | js*| | S |jr8tdt| |S )Nr   z#cannot raise expression to a matrix)r   r   
ValueErrorr   )r   r   r   r   r   hadamard_power6  s    r   c                       sd   e Zd ZdZ fddZedd Zedd Zedd	 Zd
d Z	dd Z
dd Zdd Z  ZS )r   a  
    Elementwise power of matrix expressions

    Parameters
    ==========

    base : scalar or matrix

    exp : scalar or matrix

    Notes
    =====

    There are four definitions for the hadamard power which can be used.
    Let's consider `A, B` as `(m, n)` matrices, and `a, b` as scalars.

    Matrix raised to a scalar exponent:

    .. math::
        A^{\circ b} = \begin{bmatrix}
        A_{0, 0}^b   & A_{0, 1}^b   & \cdots & A_{0, n-1}^b   \\
        A_{1, 0}^b   & A_{1, 1}^b   & \cdots & A_{1, n-1}^b   \\
        \vdots       & \vdots       & \ddots & \vdots         \\
        A_{m-1, 0}^b & A_{m-1, 1}^b & \cdots & A_{m-1, n-1}^b
        \end{bmatrix}

    Scalar raised to a matrix exponent:

    .. math::
        a^{\circ B} = \begin{bmatrix}
        a^{B_{0, 0}}   & a^{B_{0, 1}}   & \cdots & a^{B_{0, n-1}}   \\
        a^{B_{1, 0}}   & a^{B_{1, 1}}   & \cdots & a^{B_{1, n-1}}   \\
        \vdots         & \vdots         & \ddots & \vdots           \\
        a^{B_{m-1, 0}} & a^{B_{m-1, 1}} & \cdots & a^{B_{m-1, n-1}}
        \end{bmatrix}

    Matrix raised to a matrix exponent:

    .. math::
        A^{\circ B} = \begin{bmatrix}
        A_{0, 0}^{B_{0, 0}}     & A_{0, 1}^{B_{0, 1}}     &
        \cdots & A_{0, n-1}^{B_{0, n-1}}     \\
        A_{1, 0}^{B_{1, 0}}     & A_{1, 1}^{B_{1, 1}}     &
        \cdots & A_{1, n-1}^{B_{1, n-1}}     \\
        \vdots                  & \vdots                  &
        \ddots & \vdots                      \\
        A_{m-1, 0}^{B_{m-1, 0}} & A_{m-1, 1}^{B_{m-1, 1}} &
        \cdots & A_{m-1, n-1}^{B_{m-1, n-1}}
        \end{bmatrix}

    Scalar raised to a scalar exponent:

    .. math::
        a^{\circ b} = a^b
    c                    sd   t |}t |}|jr$|jr$|| S |jrP|jrP|j|jkrPtd|j|jt | ||}|S )NzGThe shape of the base {} and the shape of the exponent {} do not match.)r   	is_scalarr   r3   r   formatr+   r,   )r-   r   r   r/   r0   r   r   r,   {  s    zHadamardPower.__new__c                 C   s
   | j d S r2   _argsr4   r   r   r   r     s    zHadamardPower.basec                 C   s
   | j d S rP   r   r4   r   r   r   r     s    zHadamardPower.expc                 C   s   | j jr| j jS | jjS r   )r   r   r3   r   r4   r   r   r   r3     s    zHadamardPower.shapec                 K   s   | j }| j}|jr(|j||fi |}n|jr4|}ntd||jr^|j||fi |}n|jrj|}ntd||| S )Nz)The base {} must be a scalar or a matrix.z-The exponent {} must be a scalar or a matrix.)r   r   r   r6   r   r   r   )r5   r   r:   r;   r   r   abr   r   r   r6     s"    zHadamardPower._entryc                 C   s   ddl m} t|| j| jS r<   )r>   r=   r   r   r   r?   r   r   r   r@     s    zHadamardPower._eval_transposec                 C   s:   | j |}| jt}||}t|| | j |  | S r   )r   rR   r   	applyfuncr   r#   )r5   rT   dexpZlogbaseZdlbaser   r   r   rW     s    
zHadamardPower._eval_derivativec                    s  ddl m} ddl m} ddlm}  j|}|D ]}ddg} fddt|D }|j|j	 }|j|j
 }	t|t|t||g jt j jd	  t||	ggg||jd
}
|
jd jd j|_d|_d|_	|
jd jd j|_d|_d|_
|
g|_q4|S )Nr   rZ   rX   r\   )r   r`   ra   c                    s$   g | ]\}} j j| d kr|qS rd   )r   r3   re   r4   r   r   r     r   z?HadamardPower._eval_derivative_matrix_lines.<locals>.<listcomp>r   )	validatorr`   )rg   r[   rY   rh   r]   r   rj   ri   rk   rl   rm   r   r   r   	_validater.   rn   ro   rp   rq   )r5   rT   r[   rY   r]   lrr   rx   ry   rz   r{   r   r4   r   rj     s>    

	

z+HadamardPower._eval_derivative_matrix_lines)r|   r}   r~   r   r,   r   r   r   r3   r6   r@   rW   rj   r   r   r   r0   r   r   B  s   8


	r   N)#collectionsr   
sympy.corer   r   Zsympy.core.addr   sympy.core.exprr   sympy.core.sortingr   &sympy.functions.elementary.exponentialr   sympy.matrices.commonr	   rh   r
   Z"sympy.matrices.expressions.specialr   r   sympy.strategiesr   r   r   r   r   r   sympy.utilities.exceptionsr   r#   r    r   rM   r   r   r   r   r   r   <module>   s"    y 