在db

时间:2016-02-09 19:15:36

标签: python django python-3.x opencv numpy

我有一个numpy.float32元素列表,我从查询图像中提取:

[0.013991388, 0.0070270086, 0.0012525863, 0.013302466, . . . etc

它存储在对象中,也作为String存储在数据库中。然后将对象值与检索到的数据库值进行比较(当然从字符串转换后)。

然而,无论他们看起来多么相似,我似乎无法让他们再次平等。例如,我正在运行chi2距离算法来计算距离,并期望能够为同一图像返回0.0。

我的转化代码:

# converts string to numpy array (matrix). MUST CAST to float32 otherwise pythons float64 by default, this will not
# match with our query array even if they are the same image!!!
def toMatrix(text):
    text = text.replace('[', '').replace(']', '')
    floats = [np.float32(x) for x in text.split(',')]

    return floats

使用上面的字符串将字符串转换回浮点数列表后,我将它与存储在对象中的列表进行比较,方法是将一个接一个地粘贴到PyCharm文本文件中。检查本地历史记录表明没有发生任何变化,视觉上两个阵列是相同的。

所以这是我认为的一个类型问题。我打印出两个列表的类型第一个元素,例如type(listA[0]), type(listB[0]),两者都是numpy.float32。

所以我使用更一般的比较:

np.array_equal(listA, listB) # returns False
np.allclose(listA, listB)    # returns True

试图找出不相等的东西:

d = {}
count = 1
    for item in listA:
        if item not in listB:
            d[count] = type(item)
        count += 1

我得到了奇特的结果:{124: <class 'numpy.float32'>}

这是两个数组中的单项???

任何人都可以了解到究竟发生了什么,以及如何让阵列变得平等?

3 个答案:

答案 0 :(得分:1)

推测listA中的所有项目都是numpy.float32类型,所以这段代码:

d[type(item)] = item

将一遍又一遍地分配给相同的字典元素。

答案 1 :(得分:1)

我不会尝试解析容易出错且繁琐的字符串。我宁愿依赖json字符串之类的东西来保存数据,所以你可以在没有(或至少节省大部分时间)解析数据的情况下转换和加载数据。

你可以创建一个TextField并将数组保存/加载到它,或者可能有某些人已经创建的django-jsonfield

答案 2 :(得分:1)

您的数字的字符串表示形式有8位有效数字; dplyr的{​​{3}}。

  • 您永远不应该假设float32表示浮点数。在制作浮点数的字符串表示时有足够的流浪,如果尝试了足够的次数,这将导致失败。

  • 您应该只测试浮点数之间的相等性,如果您确实需要两个数字在位上相等(通常在创建字符串表示时无法保留)。通常情况下,您希望float(string(number))==number使用的“公差范围内”标准。

如果您的情况允许,您应该考虑以二进制格式保存数据阵列。这将保留保存/加载数字的位表示(如果您真的关心按位相等),并且作为额外的好处,这需要更少的存储空间。

您遇到浮点精度问题:字符串表示形式与二进制表示形式不同。试试这个:

numpy.allclose

我第一次尝试时import numpy as np import random a=random.random() np.float32( str(a)) == a False),也许你不会,但有浮点数,print a => 0.893117245932不是那个数字。

如果您需要将它们保存为字符串,则应使用this is not enough to uniquely specify the binary representation - 这将使用数组中的值生成二进制字符串,例如float(string(number))(假设为numpy.fromstring(numpy.tostring(array), dtype=numpy.float32) == array )。

如果您不关心精度,那么使用array.dtype==numpy.float32中使用的容差测试近似相等可能是有意义的。