2012-09-10 197 views
4

我有一個熊貓數據幀「DT = MYFUNC()」,並從IDLE輸出的屏幕拷貝如下:爲什麼熊貓在一種情況下會導致「ZeroDivisionError」,但在另一種情況下卻不會呢?

>>> from __future__ import division 
>>> dt = __get_stk_data__(['*'], frq='CQQ', from_db=False) # my function 
>>> dt = dt[dt['ebt']==0][['tax','ebt']] 
>>> type(dt) 
<class 'pandas.core.frame.DataFrame'> 
>>> dt 
       tax ebt 
STK_ID RPT_Date   
000719 20100331 0 0 
     20100630 0 0 
     20100930 0 0 
     20110331 0 0 
002164 20080331 0 0 
300155 20120331 0 0 
600094 20090331 0 0 
     20090630 0 0 
     20090930 0 0 
600180 20090331 0 0 
600757 20110331 0 0 
>>> dt['tax_rate'] = dt.tax/dt.ebt 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
    File "D:\Python\Lib\site-packages\pandas\core\series.py", line 72, in wrapper 
    return Series(na_op(self.values, other.values), 
    File "D:\Python\Lib\site-packages\pandas\core\series.py", line 53, in na_op 
    result = op(x, y) 
ZeroDivisionError: float division 
>>> 

它花費了我很多時間去弄明白爲什麼熊貓引發「ZeroDivisionError:浮法事業部',而熊貓都非常好,下面的示例代碼:

tuples = [('000719','20100331'),('000719','20100930'),('002164','20080331')] 
index = MultiIndex.from_tuples(tuples, names=['STK_ID', 'RPT_Date']) 
dt =DataFrame({'tax':[0,0,0],'ebt':[0,0,0]},index=index) 
dt['tax_rate'] = dt.tax/dt.ebt 

>>> dt 
       ebt tax tax_rate 
STK_ID RPT_Date      
000719 20100331 0 0  NaN 
     20100930 0 0  NaN 
002164 20080331 0 0  NaN 
>>> 

我希望大熊貓提供‘男’這兩種情況下,爲什麼‘ZeroDivisionError’發生在第一種情況?如何解決它?


下面碼&屏幕輸出被連接以提供進一步的信息,以調試

def __by_Q__(df): 
    ''' this function transforms the input financial report data (which 
     is accumulative) to qurterly data 
    ''' 
    df_q1=df[df.index.map(lambda x: x[1].endswith("0331"))] 

    print 'before diff:\n' 
    print df.dtypes 
    df_delta = df.diff() 
    print '\nafter diff: \n' 
    print df_delta.dtypes 


    q1_mask = df_delta.index.map(lambda x: x[1].endswith("0331")); 
    df_q234 = df_delta[~q1_mask] 

    rst = concat([df_q1,df_q234]) 

    rst=rst.sort_index() 
    return rst 

畫面輸出:

before diff: 

sales      float64 
discount     object 
net_sales     float64 
cogs      float64 
ebt      float64 
tax      float64 

after diff: 

sales      object 
discount     object 
net_sales     object 
cogs      object 
ebt      object 
tax      object 
+0

你可以檢查第一個例子的dt.dtypes嗎?我也無法重現這種行爲。 –

+0

'dt.dtypes'顯示'稅'和'ebt'是'對象'(我不知道爲什麼)。我能收到你的電子郵件嗎?我可以將您的整個源代碼和SQLite數據文件發送給您,然後您可以重現該場景。通常,程序從SQLite後端獲取財務報告數據,並嘗試計算財務比率... – bigbug

回答

2

@bigbug,你是如何獲取數據了SQLite的後端?如果你看看pandas.io.sqlread_frame方法有一個coerce_float參數,如果可能的話,應該將數字數據轉換爲浮點數。

你的第二個例子工作,因爲DataFrame的構造函數試圖聰明的類型。如果您將dtype設置爲對象,那麼它將失敗:

In [16]: dt = DataFrame({'tax':[0,0,0], 'ebt':[0,0,0]},index=index,dtype=object) 

In [17]: dt.tax/dt.ebt 
--------------------------------------------------------------------------- 
ZeroDivisionError       Traceback (most recent call last) 

請再次檢查您的數據導入代碼,並讓我知道您找到了什麼?

+0

'df = psql.frame_query(sqlstr,con = cx,coerce_float = True)'是獲取數據的代碼來自SQLite。我認爲'psql.frame_query'效果很好,它爲具有數據的SQLite列創建'float64',將'object'列分配給SQLite列爲空(NULL)。 (大熊貓也可以默認分配'float64'嗎?)。我一步步跟蹤內部邏輯流程,發現'DataFrame.diff()'是原因,它將數據類型從'float64'更改爲'object'! – bigbug

+0

我附上問題區域中的相關代碼和輸出。請看看。 'diff()'在碰到邊界時會改變數據類型嗎? – bigbug

+0

啊,這是一個混合dtype DataFrame的錯誤。我在這裏提交了一個錯誤報告。作爲解決方案,如果您將折扣列轉換爲浮動,那麼它應該可以工作(請參閱https://github.com/pydata/pandas/issues/1896) –

0

我沒有安倍重現該行爲(I嘗試創建DataFrames從整數,浮動和numpy陣列),購買我認爲這是一個更好的主意,以NaNtax_rate列和然後覆蓋的值時,ebt是非零:

dt['tax_rate'] = numpy.nan 
dt['tax_rate'][dt.ebt != 0] = dt.tax[dt.ebt != 0]/dt.ebt[dt.ebt != 0] 
相關問題