2017-03-22 43 views
2

就拿这个简单的数据框:熊猫:数据帧排序按日期字符串无需转换

df = pd.DataFrame({ 
    'date':['1/15/2017', '2/15/2017','10/15/2016', '3/15/2017'], 
    'int':[2,3,1,4] 
}) 

我想按照日期排序,然后将其保存到CSV,而无需:

  1. 使用pd.to_datetime(df['date'])
  2. 排序使用.sort_values('date')
  3. 转换数据框转换日期可以追溯到.strftime('%-m/%-d/%Y')

,而是做这样的事情(当然,不工作):

df.apply(pd.to_dataframe(df['date']).sort_values(by = 'date', inplace = True) 

输出:

  date kw 
2 10/15/2016 1 
0 1/15/2017 2 
1 2/15/2017 3 
3 3/15/2017 4 

这是可能的,或者我应该只是坚持使用3一步过程?

回答

2

numpyargsort返回必要进行排序的阵列排列。我们可以利用iloc。因此,通过使用pd.to_datetime转换日期,然后获取值并调用argsort,我们已经完成了我们所需的所有工作,以便对原始数据框进行排序而不更改任何列。

df.iloc[pd.to_datetime(df.date).values.argsort()] 

     date int 
2 10/15/2016 1 
0 1/15/2017 2 
1 2/15/2017 3 
3 3/15/2017 4 
+0

总是欢迎解释。 –

+0

@ pshep123'argsort'是一个'np.array'方法,它返回一个可以对数组进行排序的索引数组。这被传递给'iloc',它根据* integer position *进行索引,在这种情况下,基于'argsort'返回的索引。这是一个非常整洁的解决方案! –

+0

@piRSquared - 感谢解决方案和解释。 – pshep123

3

可以使用.assign()方法:

In [22]: df.assign(x=pd.to_datetime(df['date'])).sort_values('x').drop('x', 1) 
Out[22]: 
     date int 
2 10/15/2016 1 
0 1/15/2017 2 
1 2/15/2017 3 
3 3/15/2017 4 
+0

谢谢MaxU - 由于简洁以及它不创建另一列的事实,我将使用piRSquared,但这很棒。 – pshep123

+0

@ pshep123,当然,我喜欢他的回答比我的更多 – MaxU

+0

我对这个解决方案很好奇,因为我认为它提供了更多的灵活性,以便包含日期以及日期(我知道我最初没有问过) 。但我对速度也很好奇 - 当我以15分钟的间隔运行20年(如此大概70万条线)时,您的解决方案速度一直高出2倍以上。谢谢! – pshep123