添加链接
link管理
链接快照平台
  • 输入网页链接,自动生成快照
  • 标签化管理网页链接

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement . We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

image 看到SearchParam的withFloatVectors方法,入参是‘’Float‘’ ,用float的话,会导致精度丢失,这个有什么解决方案吗?

为什么用float会导致精度丢失?据我所知还没有用double向量的模型

float精度只有小数点后7位,milvus存储的向量和embedding转化的向量都不止这些。
存储的向量:
embedding转化的向量:

然后查询的时候只能用float的话,其实是会把精度丢失掉

image 看到SearchParam的withFloatVectors方法,入参是‘’Float‘’ ,用float的话,会导致精度丢失,这个有什么解决方案吗?

为什么用float会导致精度丢失?据我所知还没有用double向量的模型

float精度只有小数点后7位,milvus存储的向量和embedding转化的向量都不止这些。 存储的向量: image embedding转化的向量: image

然后查询的时候只能用float的话,其实是会把精度丢失掉

你错误理解了精度和展示的定位。精度的意思,指的就是后面虽然有很多位,但是都不准。你用的是float数据类型,精度就只用这么多。展示出来的东西精度本来就是不对的,原因是js只能支持64位float,也就是double

image 看到SearchParam的withFloatVectors方法,入参是‘’Float‘’ ,用float的话,会导致精度丢失,这个有什么解决方案吗?

为什么用float会导致精度丢失?据我所知还没有用double向量的模型

float精度只有小数点后7位,milvus存储的向量和embedding转化的向量都不止这些。 存储的向量: image embedding转化的向量: image
然后查询的时候只能用float的话,其实是会把精度丢失掉

你错误理解了精度和展示的定位。精度的意思,指的就是后面虽然有很多位,但是都不准。你用的是float数据类型,精度就只用这么多。展示出来的东西精度本来就是不对的,原因是js只能支持64位float,也就是double

好的,了解了

你好,我遇到了跟你一样的问题,创建milvus向量字段类型是FloatVector,然后插入的向量是这种的 企业微信截图_17163602043077 但是获取到以后是这样的 企业微信截图_17163604598560 请问有什么解决办法么?

请问你怎么生成的向量?然后怎么打印的向量
floatvector打印出来不可能有那么多位数的

你好,我遇到了跟你一样的问题,创建milvus向量字段类型是FloatVector,然后插入的向量是这种的 企业微信截图_17163602043077 但是获取到以后是这样的 企业微信截图_17163604598560 请问有什么解决办法么?

请问你怎么生成的向量?然后怎么打印的向量 floatvector打印出来不可能有那么多位数的

这个是python一个自定义的工具类,用于提取照片的某些特征值生成的向量。

大概率你这个数据存错了,用了double格式。这点精度对于搜索不会有任何区别

经过提醒。我查看了代码。没有用double,因为定义集合时设置了向量类型是FloatVector,在存储数据时,不能用double格式的,那样会产生“Type mismatch for field 'feature': Float vector field's value type must be List”错误,所以用的List。然后存储的时候向量值是
,但是在milvus的可视化平台中,存储的向量值和postman中发送的请求参数一致。

大概率你这个数据存错了,用了double格式。这点精度对于搜索不会有任何区别

经过提醒。我查看了代码。没有用double,因为定义集合时设置了向量类型是FloatVector,在存储数据时,不能用double格式的,那样会产生“Type mismatch for field 'feature': Float vector field's value type must be List”错误,所以用的List。然后存储的时候向量值是 企业微信截图_17163654011856 ,但是在milvus的可视化平台中,存储的向量值和postman中发送的请求参数一致。 企业微信截图_17163652912278

他们目前不支持double,至于attu客户端显示的向量小数位数,是因为js会自动补小数,并不能当真。

大概率你这个数据存错了,用了double格式。这点精度对于搜索不会有任何区别

经过提醒。我查看了代码。没有用double,因为定义集合时设置了向量类型是FloatVector,在存储数据时,不能用double格式的,那样会产生“Type mismatch for field 'feature': Float vector field's value type must be List”错误,所以用的List。然后存储的时候向量值是 企业微信截图_17163654011856 ,但是在milvus的可视化平台中,存储的向量值和postman中发送的请求参数一致。 企业微信截图_17163652912278

他们目前不支持double,至于attu客户端显示的向量小数位数,是因为js会自动补小数,并不能当真。

好的,谢谢。

python/javascript这些语言的浮点型是跟系统的位数走的,64位系统就会以64位来表示浮点数,但实际上在调用milvus rpc接口的时候其实都是以float32传输。对于用户来说就像变了个魔术似的。
但java是强制要求Float也就是32位输入,熟悉java的用户不应该有这种迷惑。
以32位浮点输入就已经明确告诉你向量在后台是以32位数据传输,存储,以及计算。所以它根本不可能再变出64位精度的小数给你。
向量近似近邻检索已经是一个模糊检索的概念,用来比对相似的事物。如果说我们要比较两张人脸是否相似,难道我们会去关心这两人的头发数量是否相等么?在大部分场景下,用64位精度的向量就相当于掩耳盗铃,非但对召回率没什么影响,计算负载和内存负载还大了一倍,得不偿失。

python/javascript这些语言的浮点型是跟系统的位数走的,64位系统就会以64位来表示浮点数,但实际上在调用milvus rpc接口的时候其实都是以float32传输。对于用户来说就像变了个魔术似的。 但java是强制要求Float也就是32位输入,熟悉java的用户不应该有这种迷惑。 以32位浮点输入就已经明确告诉你向量在后台是以32位数据传输,存储,以及计算。所以它根本不可能再变出64位精度的小数给你。 向量近似近邻检索已经是一个模糊检索的概念,用来比对相似的事物。如果说我们要比较两张人脸是否相似,难道我们会去关心这两人的头发数量是否相等么?在大部分场景下,用64位精度的向量就相当于掩耳盗铃,非但对召回率没什么影响,计算负载和内存负载还大了一倍,得不偿失。

你好,我使用python的两种方式查询了同一个id的向量值,可是得到的向量值却不相同,一种是根据向量id,另一种是根据向量值。请问为什么查询结果向量值的精度会不一样呢?

你用的是python sdk,我说过python语言对于浮点型的数值总是转成64位显示。
如果你懂得怎么在python sdk里调试的话,你会看到query()接口会调用到这里: https://github.com/milvus-io/pymilvus/blob/473f62fee6cb5e446f571471884d0d7303d01ab6/pymilvus/client/entity_helper.py#L481

我们把这几行代码改成如下:

      if field_data.type == DataType.FLOAT_VECTOR:
           dim = field_data.vectors.dim
           if len(field_data.vectors.float_vector.data) >= index * dim:
               start_pos, end_pos = index * dim, (index + 1) * dim
               entity_row_data[field_data.field_name] = []
               print(field_data.vectors.float_vector)
               for x in field_data.vectors.float_vector.data[start_pos:end_pos]:
                   print(x)
                   entity_row_data[field_data.field_name].append(np.single(x))
               print(entity_row_data[field_data.field_name])

打断点进入,你会看到 field_data.vectors.float_vector 这个是由Milvus rpc接口返回的结构体,打印出来的值是32位浮点型。
然后for x in field_data.vectors.float_vector.data[start_pos:end_pos] 这行里的 x 打印出来就变成了64位浮点型,所以知道我为何说“python语言对于浮点型的数值总是转成64位显示”了吧。
后面几行又做了什么呢? append(np.single(x)),看到np.single(x)了吧,这是numpy的single,指代float32浮点型。这里是把64位的x又cut成了32位浮点数。
所以你看到的query的结果里都是以32位浮点型显示。

再来看search()接口干了什么。
https://github.com/milvus-io/pymilvus/blob/473f62fee6cb5e446f571471884d0d7303d01ab6/pymilvus/client/abstract.py#L480

if dtype == DataType.FLOAT_VECTOR:
                field2data[name] = vectors.float_vector.data[start * dim : end * dim], field_meta
                continue

它直接把rpc接口返回的response包装成SearchResult给你,然后SearchResult里面是直接提取向量数据,没有经过numpy.single的转化,所以python自动用64位浮点型来表示。