"无法将浮动Nan转换为int"但没有南?

时间:2015-12-07 14:45:17

标签: python pandas int nan

我有一个数据框并尝试进行以下操作:

data['SD_rates']=np.array([int((data['actual value'][i]-data['means'][i])/data['std'][i]) for i in range (len(data['means']))])  

它打破了以下消息: "无法将浮动Nan转换为int"

这是我理解的错误,但是使用data.isnull()测试了df,并且没有涉及的列包含NaN(我通过发送data.to_csv手动控制它)。

我甚至用fillna(-1,inplace = True)填充数据[' std']但是,它仍然会中断。我不明白为什么,因为没有除以0(我也控制了这个列中没有零,所以没有原始0和Null / Nan填充-1),实际值和手段是fillna (0)对于缺失值,无论如何减法都不能产生一个nan(数据范围在[0-10]中)。

可能有什么不对? (正如我所说,触发操作之前的数据是正确的......)。感谢

这是一段代码:
我的一个假设是,在某种程度上,groupby可能会产生NaN,在计算我的手段时我无法摆脱(但我相信它被大熊猫自动忽略了......)并且没有填充0或-1(我故意为标准差选择-1以避免除以0)。

def stats_setting(data):

    print('Stats settings')
    print(data.columns)
    print(data.dtypes) 
    #sys.exit()

    data['marks']=np.log1p(data['marks'].astype(float))
    data['students']=np.log1p(data['students'].astype(float))#Rossman9 think this has to be tested
    #were filled with fillna before)

#First Part: by studentType and Assortment
    types_DoM_select=['Type','Type2','Category']

#First Block:types_DoM students grouped by categories
#wonder if can do a groupby of groupb
    print("types_DoM_marks_means")
    types_DoM_marks_means = data.groupby(types_DoM_select)['marks'].mean()
    types_DoM_marks_means.name = 'types_DoM_marks_means'
    types_DoM_marks_means = types_DoM_marks_means.reset_index()
    data = pd.merge(data, types_DoM_marks_means, on = types_DoM_select, how='left')

    print("types_DoM_students_means")
    types_DoM_students_means = data.groupby(types_DoM_select)['students'].mean() #.students won't work. Why?
    types_DoM_students_means.name = 'types_DoM_students_means'
    types_DoM_students_means=types_DoM_students_means.reset_index()    
    data = pd.merge(data, types_DoM_students_means, on = types_DoM_select, how='left')

    print("types_DoM_marks_medians")
    types_DoM_marks_medians = data.groupby(types_DoM_select)['marks'].median()
    types_DoM_marks_medians.name = 'types_DoM_marks_medians'
    types_DoM_marks_medians = types_DoM_marks_medians.reset_index()
    data = pd.merge(data, types_DoM_marks_medians, on = types_DoM_select, how='left')

    print("types_DoM_students_medians")
    types_DoM_students_medians = data.groupby(types_DoM_select)['students'].median() #.students won't work. Why?
    types_DoM_students_medians.name = 'types_DoM_students_medians'
    types_DoM_students_medians=types_DoM_students_medians.reset_index()    
    data = pd.merge(data, types_DoM_students_medians, on = types_DoM_select, how='left')
    print("types_DoM_marks_std")
    types_DoM_marks_std = data.groupby(types_DoM_select)['marks'].std()
    types_DoM_marks_std.name = 'types_DoM_marks_std'
    types_DoM_marks_std = types_DoM_marks_std.reset_index()
    data = pd.merge(data, types_DoM_marks_std, on = types_DoM_select, how='left')


    print("types_DoM_students_std")
    types_DoM_students_std = data.groupby(types_DoM_select)['students'].std()
    types_DoM_students_std.name = 'types_DoM_students_std'
    types_DoM_students_std = types_DoM_students_std.reset_index()
    data = pd.merge(data, types_DoM_students_std, on = types_DoM_select, how='left')

    data['types_DoM_marks_means'].fillna(-1, inplace=True)
    data['types_DoM_students_means'].fillna(-1, inplace=True)
    data['types_DoM_marks_medians'].fillna(-1, inplace=True)
    data['types_DoM_students_medians'].fillna(-1, inplace=True)
    data['types_DoM_marks_std'].fillna(-1, inplace=True)
    data['types_DoM_students_std'].fillna(-1, inplace=True)

#Second Part: by specific student
    student_DoM_select=['Type','Type2','Category']

#First Block:student_DoM
#wonder if can do a groupby of groupb
    print("student_DoM_marks_means")
    student_DoM_marks_means = data.groupby(student_DoM_select)['marks'].mean()
    student_DoM_marks_means.name = 'student_DoM_marks_means'
    student_DoM_marks_means = student_DoM_marks_means.reset_index()
    data = pd.merge(data, student_DoM_marks_means, on = student_DoM_select, how='left')

    print("student_DoM_students_means")
    student_DoM_students_means = data.groupby(student_DoM_select)['students'].mean() #.students won't work. Why?
    student_DoM_students_means.name = 'student_DoM_students_means'
    student_DoM_students_means=student_DoM_students_means.reset_index()    
    data = pd.merge(data, student_DoM_students_means, on = student_DoM_select, how='left')

    print("student_DoM_marks_medians")
    student_DoM_marks_medians = data.groupby(student_DoM_select)['marks'].median()
    student_DoM_marks_medians.name = 'student_DoM_marks_medians'
    student_DoM_marks_medians = student_DoM_marks_medians.reset_index()
    data = pd.merge(data, student_DoM_marks_medians, on = student_DoM_select, how='left')

    print("student_DoM_students_medians")
    student_DoM_students_medians = data.groupby(student_DoM_select)['students'].median() #.students won't work. Why?
    student_DoM_students_medians.name = 'student_DoM_students_medians'
    student_DoM_students_medians=student_DoM_students_medians.reset_index()    
    data = pd.merge(data, student_DoM_students_medians, on = student_DoM_select, how='left')

    # May I use data['marks','students','marksMean','studentsMean','marksMedian','studentsMedian']=data['marks','students','marksMean','studentsMean','marksMedian','studentsMedian'].astype(int) to spare memory?

    print("student_DoM_marks_std")
    student_DoM_marks_std = data.groupby(student_DoM_select)['marks'].std()
    student_DoM_marks_std.name = 'student_DoM_marks_std'
    student_DoM_marks_std = student_DoM_marks_std.reset_index()
    data = pd.merge(data, student_DoM_marks_std, on = student_DoM_select, how='left')

    print("student_DoM_students_std")
    student_DoM_students_std = data.groupby(student_DoM_select)['students'].std()
    student_DoM_students_std.name = 'student_DoM_students_std'
    student_DoM_students_std = student_DoM_students_std.reset_index()
    data = pd.merge(data, student_DoM_students_std, on = student_DoM_select, how='left')

    data['student_DoM_marks_means'].fillna(0, inplace=True)
    data['student_DoM_students_means'].fillna(0, inplace=True)
    data['student_DoM_marks_medians'].fillna(0, inplace=True)
    data['student_DoM_students_medians'].fillna(0, inplace=True)
    data['student_DoM_marks_std'].fillna(0, inplace=True)
    data['student_DoM_students_std'].fillna(0, inplace=True)

#Third Part: Exceptional students 

    #I think int is better here as it helps defining categories but can't use it.#    
    #print(data.isnull().sum())
    #print(data['types_DoM_marks_std'][data['types_DoM_marks_std']==0].sum())
    #data.to_csv('ex')
    #print(data.columns)

#Original version:#int raises the "can't convert Nan float to int. While there were no Nan as I verified in the data just before sending it to the    
    data['Except_student_IP2_DoM_marks_means']=np.array([int((data['student_IP2_DoM_marks_means'][i]-data['types_IP2_DoM_marks_means'][i])/data['types_IP2_DoM_students_std'][i]) for i in range (len(data['year']))])  
    data['Except_student_IP2_DoM_marks_medians']=np.array([int((data['student_IP2_DoM_marks_medians'][i]-data['types_IP2_DoM_marks_means'][i])/data['types_IP2_DoM_students_std'][i]) for i in range (len(data['year']))])  
#Second version: raises no error but final data (returned) is filled with these stupid NaN
    data['Except_student_P2M_DoM_marks_means']=np.array([np.round((data['student_DoM_marks_means'][i]-data['types_DoM_marks_means'][i])/data['types_DoM_marks_std'][i],0) for i in range (len(data['year']))])  
    data['Except_student_P2M_DoM_marks_medians']=np.array([np.round((data['student_DoM_marks_medians'][i]-data['types_DoM_marks_medians'][i])/data['types_DoM_marks_std'][i],0) for i in range (len(data['year']))])  

#End
    return data

1 个答案:

答案 0 :(得分:2)

您的数据框中没有Nans很可能是正确的,但是您在计算中创建它们。请参阅以下内容:

In [15]: import pandas as pd
In [16]: df = pd.DataFrame([[1, 2], [0, 0]], columns=['actual value', 'col2'])
         df['means'] = df.mean(axis=1)
         df['std'] = df.std(axis=1)

In [17]: df
Out[17]:
   actual value  col2  means  std
0             1     2    1.5  0.5
1             0     0    0.0  0.0

所以数据框没有任何Nans,但是计算呢?

In [21]: [(df['actual value'][i]-df['means'][i])/df['std'][i] for i in range (len(df['means']))]
Out[21]: [-1.0, nan]

现在当你打电话给int时,你会在结果列表中收到错误。 最后,我建议(如果可能的话)直接在底层数组中执行操作,而不是使用for循环,因为它会更快。

In [25]: (df['actual value']-df['means'])/df['std']
Out[25]:
0    -1
1   NaN
dtype: float64

这可能无法实现,具体取决于需要0分区的返回值。