U
    L?h                     @   sh   d dl mZmZ d dlZG dd deZG dd deZG dd deZG d	d
 d
eZe Ze Z	dS )    )BasicIntegerNc                   @   sP   e Zd ZdZdd Zedd Zedd Zdd	 Zd
d Z	dd Z
dd ZdS )
OmegaPowerz
    Represents ordinal exponential and multiplication terms one of the
    building blocks of the :class:`Ordinal` class.
    In ``OmegaPower(a, b)``, ``a`` represents exponent and ``b`` represents multiplicity.
    c                 C   sN   t |trt|}t |tr$|dkr,tdt |ts@t|}t| ||S )Nr   z'multiplicity must be a positive integer)
isinstanceintr   	TypeErrorOrdinalconvertr   __new__)clsab r   E/var/www/html/venv/lib/python3.8/site-packages/sympy/sets/ordinals.pyr
      s    


zOmegaPower.__new__c                 C   s
   | j d S Nr   argsselfr   r   r   exp   s    zOmegaPower.expc                 C   s
   | j d S N   r   r   r   r   r   mult   s    zOmegaPower.multc                 C   s,   | j |j kr|| j|jS || j |j S d S N)r   r   )r   otheropr   r   r   _compare_term   s    zOmegaPower._compare_termc                 C   s>   t |ts2ztd|}W n tk
r0   t Y S X | j|jkS r   )r   r   r   NotImplementedr   r   r   r   r   r   __eq__$   s    

zOmegaPower.__eq__c                 C   s
   t | S r   )r   __hash__r   r   r   r   r    ,   s    zOmegaPower.__hash__c                 C   s@   t |ts2ztd|}W n tk
r0   t Y S X | |tjS r   )r   r   r   r   r   operatorltr   r   r   r   __lt__/   s    

zOmegaPower.__lt__N)__name__
__module____qualname____doc__r
   propertyr   r   r   r   r    r#   r   r   r   r   r      s   

r   c                       s   e Zd ZdZ fddZedd Zedd Zedd	 Ze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dd Zdd Zdd ZeZd d! Zd"d# Zd$d% Zd&d' Zd(d) Z  ZS )*r   a  
    Represents ordinals in Cantor normal form.

    Internally, this class is just a list of instances of OmegaPower.

    Examples
    ========
    >>> from sympy import Ordinal, OmegaPower
    >>> from sympy.sets.ordinals import omega
    >>> w = omega
    >>> w.is_limit_ordinal
    True
    >>> Ordinal(OmegaPower(w + 1, 1), OmegaPower(3, 2))
    w**(w + 1) + w**3*2
    >>> 3 + w
    w
    >>> (w + 1) * w
    w**2

    References
    ==========

    .. [1] https://en.wikipedia.org/wiki/Ordinal_arithmetic
    c                    sP   t  j| f| }dd |jD  t fddtt d D sLtd|S )Nc                 S   s   g | ]
}|j qS r   )r   .0ir   r   r   
<listcomp>S   s     z#Ordinal.__new__.<locals>.<listcomp>c                 3   s"   | ]} |  |d   kV  qdS )r   Nr   r)   Zpowersr   r   	<genexpr>T   s     z"Ordinal.__new__.<locals>.<genexpr>r   z"powers must be in decreasing order)superr
   r   allrangelen
ValueError)r   termsobj	__class__r-   r   r
   Q   s
    "zOrdinal.__new__c                 C   s   | j S r   r   r   r   r   r   r4   X   s    zOrdinal.termsc                 C   s   | t krtd| jd S )Nz ordinal zero has no leading termr   ord0r3   r4   r   r   r   r   leading_term\   s    zOrdinal.leading_termc                 C   s   | t krtd| jd S )Nz!ordinal zero has no trailing termr8   r   r   r   r   trailing_termb   s    zOrdinal.trailing_termc                 C   s*   z| j jtkW S  tk
r$   Y dS X d S NFr<   r   r9   r3   r   r   r   r   is_successor_ordinalh   s    zOrdinal.is_successor_ordinalc                 C   s,   z| j jtk W S  tk
r&   Y dS X d S r=   r>   r   r   r   r   is_limit_ordinalo   s    zOrdinal.is_limit_ordinalc                 C   s   | j jS r   )r:   r   r   r   r   r   degreev   s    zOrdinal.degreec                 C   s   |dkrt S ttd|S r   )r9   r   r   )r   Zinteger_valuer   r   r   r	   z   s    zOrdinal.convertc                 C   s>   t |ts2zt|}W n tk
r0   t Y S X | j|jkS r   )r   r   r	   r   r   r4   r   r   r   r   r      s    

zOrdinal.__eq__c                 C   s
   t | jS r   )hashr   r   r   r   r   r       s    zOrdinal.__hash__c                 C   sr   t |ts2zt|}W n tk
r0   t Y S X t| j|jD ]\}}||kr@||k   S q@t| jt|jk S r   )r   r   r	   r   r   zipr4   r2   )r   r   Z	term_selfZ
term_otherr   r   r   r#      s    

zOrdinal.__lt__c                 C   s   | |kp| |k S r   r   r   r   r   r   __le__   s    zOrdinal.__le__c                 C   s
   | |k S r   r   r   r   r   r   __gt__   s    zOrdinal.__gt__c                 C   s
   | |k  S r   r   r   r   r   r   __ge__   s    zOrdinal.__ge__c                 C   s   d}d}| t krdS | jD ]}|r*|d7 }|jt krD|t|j7 }nJ|jdkrX|d7 }n6t|jjdksp|jjr|d|j 7 }n|d|j 7 }|jdks|jt ks|d	|j 7 }|d7 }q|S )
N r   r9   z + r   wzw**(%s)zw**%sz*%s)r9   r4   r   strr   r2   r@   )r   Znet_strZ
plus_countr+   r   r   r   __str__   s$    




zOrdinal.__str__c                 C   s   t |ts2zt|}W n tk
r0   t Y S X |tkr>| S t| j}t|j}t|d }|j	}|dkr|| j
|k r|d8 }qd|dk r|}nZ|| j
|krt||| j|jj }|d | |g |dd   }n|d |d  | }t| S )Nr   r   )r   r   r	   r   r   r9   listr4   r2   rA   r   r   r   r:   )r   r   Za_termsZb_termsrZb_expr4   Zsum_termr   r   r   __add__   s(    




 zOrdinal.__add__c                 C   s:   t |ts2zt|}W n tk
r0   t Y S X ||  S r   r   r   r	   r   r   r   r   r   r   __radd__   s    

zOrdinal.__radd__c                 C   s   t |ts2zt|}W n tk
r0   t Y S X t| |fkrBtS | j}| jj}g }|j	r|j
D ]}|t||j |j q`n^|j
d d D ]}|t||j |j q|jj}|t|||  |t| j
dd  7 }t| S )Nr;   r   )r   r   r	   r   r   r9   rA   r:   r   r@   r4   appendr   r   r<   rK   )r   r   Za_expZa_multZ	summationargZb_multr   r   r   __mul__   s&    


zOrdinal.__mul__c                 C   s:   t |ts2zt|}W n tk
r0   t Y S X ||  S r   rN   r   r   r   r   __rmul__   s    

zOrdinal.__rmul__c                 C   s   | t kstS tt|dS r   )omegar   r   r   r   r   r   r   __pow__   s    zOrdinal.__pow__)r$   r%   r&   r'   r
   r(   r4   r:   r<   r?   r@   rA   classmethodr	   r   r    r#   rD   rE   rF   rJ   __repr__rM   rO   rR   rS   rU   __classcell__r   r   r6   r   r   8   s:   






r   c                   @   s   e Zd ZdZdS )OrdinalZerozDThe ordinal zero.

    OrdinalZero can be imported as ``ord0``.
    N)r$   r%   r&   r'   r   r   r   r   rY      s   rY   c                   @   s$   e Zd ZdZdd Zedd ZdS )OrdinalOmegazThe ordinal omega which forms the base of all ordinals in cantor normal form.

    OrdinalOmega can be imported as ``omega``.

    Examples
    ========

    >>> from sympy.sets.ordinals import omega
    >>> omega + omega
    w*2
    c                 C   s
   t | S r   )r   r
   )r   r   r   r   r
     s    zOrdinalOmega.__new__c                 C   s   t ddfS r   )r   r   r   r   r   r4     s    zOrdinalOmega.termsN)r$   r%   r&   r'   r
   r(   r4   r   r   r   r   rZ     s   rZ   )
Z
sympy.corer   r   r!   r   r   rY   rZ   r9   rT   r   r   r   r   <module>   s   3 F