首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >检测Python中连续行上的错误数据

检测Python中连续行上的错误数据
EN

Stack Overflow用户
提问于 2016-01-08 01:31:04
回答 2查看 384关注 0票数 1

当我在Pandas DataFrame上操作季度收益数据的时候,我意识到我想做季度间(即Q2到Q3)的比较,我意识到我应该确定我的数据是正确的,也是完整的。

因此,1.总是‘正确’季度(Q1->Q2-> q3 ->Q4->Q1->Q2.) 2.不缺少任何季度(q1->q2->q4->q1->q2->q3) .

我已经有一个我加载的数据,并认为这是有意义的检查它在熊猫,而不是回去检查它的预装。

我想出了两种轻微的创可贴来解决一个问题,但我认为发布这个问题和我的解决方案可能会很有趣,看看是否有人能给出一些线索,或者觉得这很有趣。似乎很难找到潘达的信息,有时带我从初级到中级水平熟练。

我想这个问题有一个更优雅的解决方案,也可能是一个更广泛适用的概念,我可以在这里学习和应用,也可以应用于其他问题。别再唠叨了。还是胡闹?.

我有一套财务收益数据。看起来是这样的:

代码语言:javascript
复制
Index   Symbol  Time    Earning_Date    Year    Quarter Last_Quarter
0   AAPL    16:30:00    10/27/2015  2015    Q4  Q3
1   AAPL    16:30:00    7/21/2015   2015    Q3  Q2
2   AAPL    16:30:00    4/27/2015   2015    Q2  Q1
3   AAPL    16:30:00    1/27/2015   2015    Q1  Q4
4   AAPL    16:30:00    10/20/2014  2014    Q4  Q3
5   AAPL    16:30:00    7/22/2014   2014    Q3  Q2
6   AAPL    16:30:00    4/23/2014   2014    Q2  Q1
7   AAPL    16:30:00    1/27/2014   2014    Q1  Q4
8   AAPL    16:30:00    10/28/2013  2013    Q4  Q3
9   AAPL    16:30:00    7/23/2013   2013    Q3  Q2
10  AAPL    16:30:00    4/23/2013   2013    Q2  Q1
11  AAPL    16:30:00    1/23/2013   2013    Q1  Q4
12  AAPL    16:30:00    10/25/2012  2012    Q4  Q3
13  AAPL    16:30:00    7/24/2012   2012    Q3  Q2
14  AAPL    16:30:00    4/24/2012   2012    Q2  Q1
15  AAPL    16:30:00    1/24/2012   2012    Q1  Q4
16  AAPL    16:30:00    10/18/2011  2011    Q4  Q3
17  AAPL    16:30:00    7/19/2011   2011    Q3  Q2
18  AAPL    16:30:00    4/20/2011   2011    Q2  Q1
19  AAPL    16:30:00    1/18/2011   2011    Q1  NaN

首先,完全公开--我已经用“解决方案”填充了这个DF,解决了将Last_Quarter附加到每一行的问题--我只是使用.shift(-1)来填充它。我确信这一点可以做得更好--数据对DF的重要性,就像它帮助我以两种方式解决问题一样。但是,如果我们不使用Last_Quarter列来解决这个问题,那就没问题了。希望这是合理的。

更大的问题是清理可能丢失或错误的数据。如果一只股票跳过了一个盈利季度,或者我的数据被破坏了,那么顺序可能是索引2季度Q2,索引3季度Q4,从而跳过Q3,然后很多假设都可能是错误的。所以我只想确保所有的数据Q1遵循Q4,Q2遵循Q1,Q3遵循Q2,Q4遵循Q3。

如果数据是坏的,那么就排除一个例外吧。以下是我们提出的两个解决方案:

代码语言:javascript
复制
    accptbl_qtr_pr_tpls = [('Q3','Q4'),('Q4','Q1'),('Q1','Q2'),('Q2','Q3')]
    rows_that_pass = 0
    rows_total = len(self.df)
    print 'total rows', rows_total
    for accptbl_qtr_pr_tpl in accptbl_qtr_pr_tpls:
        foo = self.df.ix[(self.df['Last_Quarter'] == accptbl_qtr_pr_tpl[0]) & (self.df['Quarter'] == accptbl_qtr_pr_tpl[1])]
        rows_that_pass += len(foo)
    if rows_total != 1+rows_that_pass: # the + 1 is to account for NaN in earliest result last_quarter column
        print 'quarter issue!, exiting'

我们还想出了:

代码语言:javascript
复制
        if not (((self.df['Last_Quarter'] == 'Q1') & (self.df['Quarter'] == 'Q2')).any() and ((self.df['Last_Quarter'] == 'Q2') & (self.df['Quarter'] == 'Q3')).any() \
           and ((self.df['Last_Quarter'] == 'Q3') & (self.df['Quarter'] == 'Q4')).any() and ((self.df['Last_Quarter'] == 'Q4') & (self.df['Quarter'] == 'Q1')).any()):
            print "bad data"
        else:
            print 'good data'

我想我会把这个扔到这里看看我们有多聪明或者.我们浪费了很多时间解决一个已解决的问题。

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2016-01-08 04:10:46

我将编写一个函数,根据季度和Last_Quarter中值的有效组合返回True或False,然后通过应用函数行,创建一个具有有效状态结果的新列。

这将使您能够只使用好行或坏行来获取DataFrame的一部分。

该函数如下所示:

代码语言:javascript
复制
def check_quarters(row):
   # if either Quarter or Last_Quarter is NaN, return False
   if (row['Quarter'] != row['Quarter']) or (row['Last_Quarter'] != row['Last_Quarter']):
      return False
   # check for valid combination when Quarter is Q2 Q3 or Q4
   if int(row['Quarter'][1:2]) - 1 == int(row['Last_Quarter'][1:2]):
      return True
   # check for valid combination when Quarter is Q1
   elif int(row['Quarter'][1:2]) == 1 and int(row['Last_Quarter'][1:2]) == 4:
      return True
   else:
      return False

应用函数创建新列:

代码语言:javascript
复制
df['Valid_Quarters'] = df.apply(check_quarters, axis = 1)

现在,您可以对DataFrame进行切片,只获得有效的行:

代码语言:javascript
复制
df.loc[df['Valid_Quarters'],:]
票数 2
EN

Stack Overflow用户

发布于 2016-01-08 04:43:47

我认为你可以把收入转换成时间序列,然后再重新整理。下面的df是您的示例DataFrame。

代码语言:javascript
复制
#Drop a couple of row to test
df = df.drop([3,8,10]) 

#I'm creating a timestamp index, according to Year & Quarter columns. But if they are guaranteed to be conssitent with Earning_Date, you can use that date directly.
df.index = pd.PeriodIndex(df['Year'].astype(str)  + df['Quarter'], freq='Q').to_timestamp() #

#Some random data pretending to be earnings
df['Earnings'] = np.random.rand(len(df))

earnings = df['Earnings'].sort_index().resample('QS') #this will fill in NaN for missing quarters

print earnings

像这样的结果(数字是随机的)。注意NaNs):

代码语言:javascript
复制
2011-01-01    0.215123
2011-04-01    0.161175
2011-07-01    0.476889
2011-10-01    0.280691
2012-01-01    0.384339
2012-04-01    0.358041
2012-07-01    0.985589
2012-10-01    0.515073
2013-01-01    0.675246
2013-04-01         NaN
2013-07-01    0.379003
2013-10-01         NaN
2014-01-01    0.625809
2014-04-01    0.572225
2014-07-01    0.547720
2014-10-01    0.651770
2015-01-01         NaN
2015-04-01    0.318578
2015-07-01    0.713037
2015-10-01    0.799639
Freq: QS-JAN, Name: Earnings, dtype: float64

然后,您可以将季度/季度的收益变化作为

代码语言:javascript
复制
QoQ_Earnings_Chg = earnings.diff()
print QoQ_Earnings_Chg

丢失的硬币会给你带来NaN QoQ的零钱。

代码语言:javascript
复制
2011-01-01         NaN
2011-04-01   -0.053948
2011-07-01    0.315714
2011-10-01   -0.196198
2012-01-01    0.103648
2012-04-01   -0.026298
2012-07-01    0.627548
2012-10-01   -0.470516
2013-01-01    0.160172
2013-04-01         NaN
2013-07-01         NaN
2013-10-01         NaN
2014-01-01         NaN
2014-04-01   -0.053584
2014-07-01   -0.024505
2014-10-01    0.104050
2015-01-01         NaN
2015-04-01         NaN
2015-07-01    0.394458
2015-10-01    0.086602
Freq: QS-JAN, Name: Earnings, dtype: float64

由于重采样,这与原始的df有不同的长度,但是您可以加入到df

代码语言:javascript
复制
print df.join(QoQ_Earnings_Chg, rsuffix='_QoQChg')

           Symbol      Time Earning_Date  Year Quarter Last_Quarter  Earnings  \
2015-10-01   AAPL  16:30:00   10/27/2015  2015      Q4           Q3  0.799639   
2015-07-01   AAPL  16:30:00    7/21/2015  2015      Q3           Q2  0.713037   
2015-04-01   AAPL  16:30:00    4/27/2015  2015      Q2           Q1  0.318578   
2014-10-01   AAPL  16:30:00   10/20/2014  2014      Q4           Q3  0.651770   
2014-07-01   AAPL  16:30:00    7/22/2014  2014      Q3           Q2  0.547720   
2014-04-01   AAPL  16:30:00    4/23/2014  2014      Q2           Q1  0.572225   
2014-01-01   AAPL  16:30:00    1/27/2014  2014      Q1           Q4  0.625809   
2013-07-01   AAPL  16:30:00    7/23/2013  2013      Q3           Q2  0.379003   
2013-01-01   AAPL  16:30:00    1/23/2013  2013      Q1           Q4  0.675246   
2012-10-01   AAPL  16:30:00   10/25/2012  2012      Q4           Q3  0.515073   
2012-07-01   AAPL  16:30:00    7/24/2012  2012      Q3           Q2  0.985589   
2012-04-01   AAPL  16:30:00    4/24/2012  2012      Q2           Q1  0.358041   
2012-01-01   AAPL  16:30:00    1/24/2012  2012      Q1           Q4  0.384339   
2011-10-01   AAPL  16:30:00   10/18/2011  2011      Q4           Q3  0.280691   
2011-07-01   AAPL  16:30:00    7/19/2011  2011      Q3           Q2  0.476889   
2011-04-01   AAPL  16:30:00    4/20/2011  2011      Q2           Q1  0.161175   
2011-01-01   AAPL  16:30:00    1/18/2011  2011      Q1          NaN  0.215123   

            Earnings_QoQChg  
2015-10-01         0.086602  
2015-07-01         0.394458  
2015-04-01              NaN  
2014-10-01         0.104050  
2014-07-01        -0.024505  
2014-04-01        -0.053584  
2014-01-01              NaN  
2013-07-01              NaN  
2013-01-01         0.160172  
2012-10-01        -0.470516  
2012-07-01         0.627548  
2012-04-01        -0.026298  
2012-01-01         0.103648  
2011-10-01        -0.196198  
2011-07-01         0.315714  
2011-04-01        -0.053948  
2011-01-01              NaN  
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/34668109

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档