前几天使用sklearn拟合数据,发现曲线特别离谱,找了很久的原因,最后发现是因为我在代码中对特征进行了特征之间的相乘操作,来增加特征的维度,但是两个正数相乘之后,变成了负数:
下图中 xi
为所有数据的第一个特征, xj
为第二个特征, xij
为两个特征相乘之后的结果
在经过下面的代码测试后,发现原因是数据太大,直接相乘不会出错,但是在pandas中进行相乘后结果就是负值。
if __name__ == '__main__':
a = 10000000000
b = 70000000000
print("a:{}, b:{}".format(a, b))
print("a与b直接相乘:\n", a*b)
pda = pd.DataFrame(np.array([a]))
pdb = pd.DataFrame(np.array([b]))
print("通过pandas相乘:")
print(pda * pdb)
a:10000000000, b:70000000000
a与b直接相乘:
700000000000000000000
通过pandas相乘:
0
0 -976274800962961408
造成结果为负数的原因是,原始的数据太大,相乘后的结果超过pandas所能表达的整数的范围,导致溢出,这一现象在numpy中也存在。
一般整数的组织类型为: int8、int16、int32、int64等,如果相乘的两个数是因为pandas的整数类型为int32导致的溢出,而相乘后结果可以用int64类型的表示范围内,则将pandas的数据类型从int32改为int64即可:
pda = pd.DataFrame(np.array([a]), dtype='int64')
pdb = pd.DataFrame(np.array([b]), dtype='int64')
res = pda * pdb
如果相乘的两个数字实在太大,相乘后的结果超过了int64所能表示的范围,我们可以采取归一化将数据归一化至 (-1, 1)
或 (0, 1)
,归一化后的数据在相乘或平方时的结果就会变得正常起来。