U
     xbD                     @   s   d dl Z d dlZd dlZd dlZd dlZd dlmZ dd Z	dd Z
dd Zd	d
 Zdd Zdd Zdd Zd0ddZdd Zdd Zdd Zdd Zdd Zdd Zdd  Zd1d!d"Zd2d#d$Zd%d& Zd'd( Zd3d,d-Zd.d/ ZdS )4    N)progressBarc                 C   sR   t | tr| d n| } t| }|dd}|dd}|dd}|dd	}|S )
zGet the "compact-looking" isoformat of the input datetime string.
    Parameters: date_str   - str, an example date string
    Returns:    iso_format - str, date string in "compact" iso format
    r   yY%Y%m%d%Y-%m-%dz%H%M%Sz%H:%M:%Sz%H%Mz%H:%M)
isinstancelistget_date_str_formatreplace)date_strZ
iso_format r   I/home/exouser/operations/rsmas_insar/sources/MintPy/mintpy/utils/ptime.pyget_compact_isoformat   s    r   c                 C   s6  t | tr| d n| } z| d} W n   Y nX d}ttd| dkrPd}nttd| dkrjd}nttd| dkrd	}nttd
| dkrd}nttd| dkrd}nzttd| dkrd}n`ttd| dkrd}nFttd| dkrd}n*ttd| dkr$d}ntd| |S )a~  Get the datetime string format as defined in:
    https://docs.python.org/3.7/library/datetime.html#strftime-and-strptime-behavior

    Parameters: date_str - str, date in one of the following formats:
                            YYYYMMDDTHHMM
                            YYYYMMDD
                            YYMMDD
    Returns:    date_str_format - str, datetime string format
    r   utf8Nz#\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}z%Y-%m-%dT%H:%M:%Sz\d{4}-\d{2}-\d{2}T\d{2}:\d{2}z%Y-%m-%dT%H:%Mz\d{4}-\d{2}-\d{2}T\d{2}z%Y-%m-%dT%Hz\d{4}-\d{2}-\d{2}r   z\d{8}T\d{6}z%Y%m%dT%H%M%Sz\d{8}T\d{4}z%Y%m%dT%H%Mz\d{6}T\d{4}z%y%m%dT%H%Mz\d{8}r   z\d{6}z%y%m%dz*un-recognized date string format for "{}"!)r   r   decodelenrefindall
ValueErrorformat)r   date_str_formatr   r   r   r	   !   s4    
r	   c                 C   s   dddg}d}|  tjddd }|D ]>}|D ],}tt||dkr0t||d } q^q0|r( qhq(|s|td|  d|S )	zGet date12 str from a given file path.

    Parameters: file_path  - str, path to a file that contains date1/2 info
    Returns:    date12_str - str, date12 in (YY)YYMMDD(THHMM)[-_](YY)YYMMDD(THHMM) format
    z\d{8}T\d{4}[-_]\d{8}T\d{4}z\d{8}[-_]\d{8}z\d{6}[-_]\d{6}Nr   zNO date12 str found in path: !)splitossepr   r   r   r   )	file_pathZdate12_fmtsZ
date12_strpartspartZ
date12_fmtr   r   r   get_date12_from_pathT   s     	r   c                 C   s*   | }|j dkr|tjdd7 }|jddS )zRound datetime object to the nearest second.
    Link: https://stackoverflow.com/questions/47792242/rounding-time-off-to-the-nearest-second-python
    g    A   )secondsr   )microsecond)r"   dt	timedeltar
   )Zdatetime_objZdatetime_obj_outr   r   r   round_secondsu   s    
r%   c                 C   sZ   t | } tj| d j}d}|dk s0|dkr6d}n |dk rDd}n|dk rRd	}nd
}|S )zDetermine the season of input date in YYYYMMDD format

    Parameters: date_str - str, date in YYYYMMDD format
    Returns:    season   - str, season in ['WINTER', 'SPRING', 'SUMMER', 'FALL']
    r   N<   iJ  ZWINTER   ZSPRING   ZSUMMERZFALL)yyyymmddr#   datetimestrptime	timetupletm_yday)r   ydayZseasonr   r   r   yyyymmdd2season   s    r/   c                 C   s,   t jt| t j| d d t jdd S )zConvert Matlab datenum into Python datetime.
    Parameters: datenum : Date in datenum format, i.e. 731763.5
    Returns:    datetime: Date in datetime.datetime format, datetime.datetime(2003, 7, 1, 12, 0)
    r    )daysn  )r#   r*   fromordinalintr$   )Zdatenumr   r   r   datenum2datetime   s
    
r4   c                 C   sf   dd }t | ttjtjtfr(|| }n:t | trPg }| D ]}||| q:ntd	t
| |S )zread date in 2002.40657084 to datetime format
    Parameters: years    : (list of) float or str for years
    Returns:    years_dt : (list of) datetime.datetime objects
    c                 S   sn   t | } t| t}t| | d td }d||}ztj|d}W n   t	d| Y nX |S )N     v@r    z	{:d}-{:d}z%Y-%jzwrong format: )
floatnpfloorastyper3   r   r#   r*   r+   r   )xyearr.   x2Zxtr   r   r   decimal_year2datetime1   s    z5decimal_year2datetime.<locals>.decimal_year2datetime1zAunrecognized input format: {}. Only float/str/list are supported.)r   r6   r7   float32float64strr   appendr   r   type)yearsr=   Zyears_dtr;   r   r   r   decimal_year2datetime   s    

rD   c                 C   s   t | tr| g}nt| }t|d }g }|D ]n}tj||}|j| j	d d  |j
d  |jd  |jd  }|rd|kr|t|d 7 }|| q.t | tr|d }|S )a  Convert date(s) string into float number in the unit of year
    Parameters: dates   - (list of) str, date in YYYYMMDD format
                seconds - float or str, time of the day info in seconds
    Returns:    years   - (list of) float, years including the date and time info
    r   r    r5        @     A    ~~AT)r   r@   r   r	   r#   r*   r+   r;   r,   r-   hourminutesecondr6   rA   )datesr!   	date_listdate_formatrC   r   dr   r   r   r   yyyymmdd2years   s(    

rP   c                 C   s"   | d dkrd|  } nd|  } | S )z/Convert date str from YYMMDD to YYYYMMDD formatr   91920r   )dater   r   r   yymmdd2yyyymmdd   s    
rU   c                 C   s"   | d dkrd|  } nd|  } | S )z'Convert year str from YY to YYYY formatr   rQ   rR   rS   r   )r;   r   r   r   yy2yyyy   s    
rV   c                 C   sz   t | tr0t| dd dkr*t| }qv| }nFt | trrg }| D ],}t|dd dkrdt|}|| qBndS |S )zAConvert date str from (YY)YYMMDD(THHMM) to YYYYMMDD(THHMM) formatrH   r      N)r   r@   r   r   rU   r   rA   rL   ZdatesOutrT   r   r   r   r)      s    


r)   c                 C   sn   t | tr*t| dkr$| dd }qj| }n@t | trfg }| D ]&}t|dkrX|dd }|| q<ndS |S )z/Convert date str in (YY)YYMMDD to YYMMDD format      N)r   r@   r   r   rA   rX   r   r   r   yymmdd  s    

r[   c                 C   sh   t | tr| g}nt| }tdd |D }tdd |D }dd t||D }t | trd|d }|S )zConvert date12 into YYYYMMDD_YYYYMMDD format
    Parameters: date12_list_in  - (list of) str
    Returns:    date12_list_out - (list of) str in YYYYMMDD_YYYYMMDD format
    c                 S   s"   g | ]}| d ddd qS -_r   r
   r   .0ir   r   r   
<listcomp>(  s     z#yyyymmdd_date12.<locals>.<listcomp>c                 S   s"   g | ]}| d ddd qS r]   r^   r    r_   r`   r   r   r   rc   )  s     c                 S   s   g | ]\}}d  ||qS )z{}_{}r   ra   msr   r   r   rc   *  s     r   )r   r@   r   r)   zipZdate12_list_indate12_listZm_datesZs_datesZdate12_list_outr   r   r   yyyymmdd_date12  s    

rl   c                 C   sh   t | tr| g}nt| }tdd |D }tdd |D }dd t||D }t | trd|d }|S )zConvert date12 into YYMMDD-YYMMDD format
    Parameters: date12_list_in  - (list of) str
    Returns:    date12_list_out - (list of) str in YYMMDD-YYMMDD format
    c                 S   s"   g | ]}| d ddd qS r\   r_   r`   r   r   r   rc   ?  s     z!yymmdd_date12.<locals>.<listcomp>c                 S   s"   g | ]}| d ddd qS rd   r_   r`   r   r   r   rc   @  s     c                 S   s   g | ]\}}d  ||qS )z{}-{}re   rf   r   r   r   rc   A  s     r   )r   r@   r   r[   ri   rj   r   r   r   yymmdd_date123  s    

rm   c              	   C   sB   g }t j| r>t| d}|  }W 5 Q R X tt|}|S )zRead Date List from txt filer)r   pathisfileopenread
splitlinessortedr)   )Z	date_filerM   fr   r   r   read_date_txtK  s    rv   c                 C   s   | sg S t | tr| g} g }| D ]:}|drLtj|rZt|}||7 }q |g}||7 }q ttt	t
|}|rtt	t
||}|S )zRead Date List
    Parameters: date_list_in  : list of str / text file
                date_list_all : list of str in YYYYMMDD format
    Returns:    date_list_out : list of str in YYYYMMDD format
    )z.txtz.cfgz.dat)r   r@   endswithr   ro   rp   rv   rt   r)   r   setintersection)Zdate_list_indate_list_allZdate_list_outrO   dsr   r   r   read_date_listZ  s     



r|   c           
      C   s   t | }g }|r2|tt|| d7 }td|  |rtd|  t t|}t|| D ]0\}}||k rZ||krZtd|  || qZ|rtd|  t t|}	t|| D ]0\}}||	kr||krtd|  || qttt|}|S )a  Get exclude date list from input options (start/end/ex_date).

    Parameters: date_list    - list of str, all dates in YYYYMMDD(THHMM) format
                start_date   - str, starting date
                end_date     - str, ending date
                exclude_date - list of str, exclude date in YYYYMMDD or text file
    Returns:    ex_date_list - list of str, exclude date
    )rz   zexclude date: zstart   date: z  remove date: zend     date: )	rP   r|   r   printr)   ri   rA   rt   rx   )
rM   Z
start_dateZend_dateZexclude_dateZ	year_listZex_date_listZyear_minr;   r   Zyear_maxr   r   r   get_exclude_date_listy  s*    
r~   c           	         s   t | } tt|   fdd| D }g }|D ]*}||d  }|j|jd  }|| q.i }t| D ]\}}|| ||< qf||fS )ak  Get temporal Baseline in days with respect to the 1st date
    Parameters: date_list - list of string, date in YYYYMMDD or YYMMDD format
    Returns:    tbase     - list of int, temporal baseline in days
                dateDict  - dict with key   - string, date in YYYYMMDD format
                                      value - int, temporal baseline in days
    c                    s   g | ]}t j| qS r   r#   r*   r+   r`   rN   r   r   rc     s     z#date_list2tbase.<locals>.<listcomp>r   iQ )r)   r	   r@   r0   r!   rA   	enumerate)	rM   rL   tbaserT   Z
date_deltaZtbase_iZdateDictrb   r   r   r   r   date_list2tbase  s    r   c                    s|   t | } tt|   fdd| D }g }|D ]D}|j| jd d  |jd  |jd  |jd  }|	| q.||fS )aK  Get time in datetime format: datetime.datetime(2006, 5, 26, 0, 0)
    Parameters: date_list  - list of string, date in YYYYMMDD or YYMMDD format
    Returns:    dates      - list of datetime.datetime objects, i.e. datetime.datetime(2010, 10, 20, 0, 0)
                datevector - list of float, years, i.e. 2010.8020547945205
    c                    s   g | ]}t j| qS r   r   r`   r   r   r   rc     s     z$date_list2vector.<locals>.<listcomp>r    r5   rE   rF   rG   )
r)   r	   r@   r;   r,   r-   rI   rJ   rK   rA   )rM   rL   Z
datevectorrO   Zdate_vecr   r   r   date_list2vector  s    r   r    Dr   c                    sv   t | }ttj| | }ttj|| }t||}tj||| |dd	d}	 fdd|	D }
|
S )a  Make a list of dates with one-day (or given days) interval for [dmin, dmax]
    Parameters: dmin    - str in format supported by get_date_str_format()
                dmax    - str in format supported by get_date_str_format()
                dstep   - int, interval in number of dunit
                dunit   - str, unit of interval, e.g. Y, M, W, D, h, m, s
                out_fmt - str, output datetime string format
    Returns:    dt_list - list of str in YYYYMMDD format
    
datetime64)dtypeOc                    s   g | ]}|  qS r   )strftime)ra   objout_fmtr   r   rc     s     z"get_date_range.<locals>.<listcomp>)
r	   r7   r   r#   r*   r+   	isoformattimedelta64aranger9   )ZdminZdmaxZdstepZdunitr   r   t1t2ZtstepZdt_objsZdt_listr   r   r   get_date_range  s    
r   c                 C   s  ddl m}m}m} | jd dkrD| jd dkrD| jd dkrDd}nd}d| | |  jd	 t| jd
 d   }ddd||  d||  d|d|   d|d|    }|d|  }| jd | j	 | j
d  | }	tj|  tdtj|	d }
|
S )a  Convert UTC time to solar local time.
    Solar time: https://en.wikipedia.org/wiki/Solar_time
    Link: https://stackoverflow.com/questions/13314626

    Parameters: utc_time   - datetime.datetime object for the UTC time
                longitude  - float, longitude of the observer in degrees
    Returns:    solar_time - datetime.datetime object for the local solar time
    Example:    utc_time = dt.datetime(2015, 2, 9, 3, 18, 48)
                solar_time = ptime.utc2solar_time(utc_time, 130.7)
    r   )picossin   d   i  r1   im  rZ   r          g(\¥l@ga2U0*?gY+^?gmWel?g?x?g-&(?r&   )minutes)mathr   r   r   r;   r,   r-   r6   rI   rJ   rK   r#   r*   combinerT   timer$   )Zutc_time	longituder   r   r   Zyear_lengammaZeqtimeZtime_offsetZtstZ
solar_timer   r   r   utc2solar_time  s    *,$r   )r   )N)NNN)r    r   r   )r   r   r   r*   r#   numpyr7   Zmintpy.objects.progressr   r   r	   r   r%   r/   r4   rD   rP   rU   rV   r)   r[   rl   rm   rv   r|   r~   r   r   r   r   r   r   r   r   <module>	   s4   3!


%		

+
