Сделайте Datetime Series из отдельных столбцов года, месяца и даты в Pandas - PullRequest
0 голосов
/ 21 ноября 2018

Как мы можем использовать столбцы 'Yr', 'Mo' и 'Dy', чтобы создать новый столбец с типом Datetime и установить его в качестве индекса PFDAS?

type

Ответы [ 2 ]

0 голосов
/ 21 ноября 2018

Как указал Брэд, вот как я это исправил

def adjustyear(x):
    if x >= 1800:
        x = 1900 + x
    else:
        x = 2000 + x
    return x

def parsefunc(x):
    yearmodified = adjustyear(x['Yr'])
    print(yearmodified)
    datetimestr = str(yearmodified)+str(x['Mo'])+str(x['Dy'])
    return pd.to_datetime(datetimestr, format='%Y%m%d', errors='ignore')

data['newindex'] = data.apply(parsefunc, axis=1)
data.index = data['newindex']
0 голосов
/ 21 ноября 2018

Во-первых, вы должны преобразовать Yr в четырехзначное целое число, то есть 1961 или 2061. Это однозначно, и, если вы используете подход, описанный ниже, необходим формат YYYY-MM-DD.Это потому, что Pandas использует format='%Y%m%d' в pandas / core / tools / datetimes.py:

# From pandas/core/tools/datetimes.py, if you pass a DataFrame or dict
values = to_datetime(values, format='%Y%m%d', errors=errors)

Итак, чтобы взять пример:

from itertools import product

import numpy as np
import pandas as pd
np.random.seed(444)

datecols = ['Yr', 'Mo', 'Dy']
mapper = dict(zip(datecols, ('year', 'month', 'day')))
df = pd.DataFrame(list(product([61, 62], [1, 2], [1, 2, 3])),
                  columns=datecols)
df['data'] = np.random.randn(len(df))

Вот df:

In [11]: df                                                                                                                                                   
Out[11]: 
    Yr  Mo  Dy      data
0   61   1   1  0.357440
1   61   1   2  0.377538
2   61   1   3  1.382338
3   61   2   1  1.175549
4   61   2   2 -0.939276
5   61   2   3 -1.143150
6   62   1   1 -0.542440
7   62   1   2 -0.548708
8   62   1   3  0.208520
9   62   2   1  0.212690
10  62   2   2  1.268021
11  62   2   3 -0.807303

Для простоты предположим, что истинный диапазон составляет 1920 г., т. Е.

In [16]: yr = df['Yr']                                                                                                                                        

In [17]: df['Yr'] = np.where(yr <= 20, 2000 + yr, 1900 + yr)                                                                                                  

In [18]: df                                                                                                                                                   
Out[18]: 
      Yr  Mo  Dy      data
0   1961   1   1  0.357440
1   1961   1   2  0.377538
2   1961   1   3  1.382338
3   1961   2   1  1.175549
4   1961   2   2 -0.939276
5   1961   2   3 -1.143150
6   1962   1   1 -0.542440
7   1962   1   2 -0.548708
8   1962   1   3  0.208520
9   1962   2   1  0.212690
10  1962   2   2  1.268021
11  1962   2   3 -0.807303

Второе, что вам нужно сделать, - это переименовать столбцы;Pandas довольно строго относится к этому, если вы передаете отображение или DataFrame в pd.to_datetime().Вот этот шаг и результат:

In [21]: df.index = pd.to_datetime(df[datecols].rename(columns=mapper))                                                                                       

In [22]: df                                                                                                                                                   
Out[22]: 
              Yr  Mo  Dy      data
1961-01-01  1961   1   1  0.357440
1961-01-02  1961   1   2  0.377538
1961-01-03  1961   1   3  1.382338
1961-02-01  1961   2   1  1.175549
1961-02-02  1961   2   2 -0.939276
1961-02-03  1961   2   3 -1.143150
1962-01-01  1962   1   1 -0.542440
1962-01-02  1962   1   2 -0.548708
1962-01-03  1962   1   3  0.208520
1962-02-01  1962   2   1  0.212690
1962-02-02  1962   2   2  1.268021
1962-02-03  1962   2   3 -0.807303

И наконец, вот один из вариантов чередования столбцов в виде строк:

In [27]: as_str = df[datecols].astype(str)   
In [30]: pd.to_datetime( 
    ...:     as_str['Yr'] + '-' + as_str['Mo'] +'-' + as_str['Dy'], 
    ...:     format='%y-%m-%d' 
    ...:    )                                                                                                                                                 
Out[30]: 
0    2061-01-01
1    2061-01-02
2    2061-01-03
3    2061-02-01
4    2061-02-02
5    2061-02-03
6    2062-01-01
7    2062-01-02
8    2062-01-03
9    2062-02-01
10   2062-02-02
11   2062-02-03
dtype: datetime64[ns]

Обратите внимание, что для вас это будет столетие.Если вы хотите быть явным, вам нужно следовать тому же подходу, что и выше, для добавления правильного века перед определением as_str.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...