Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/shell/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 为字符串指定唯一整数id的最有效方法是什么?_Python_Hash - Fatal编程技术网

Python 为字符串指定唯一整数id的最有效方法是什么?

Python 为字符串指定唯一整数id的最有效方法是什么?,python,hash,Python,Hash,我编写的程序处理大量对象,每个对象都有自己唯一的id,而id本身就是一个复杂结构的字符串(对象的十几个唯一字段由一些分隔符连接),长度很大 由于我必须快速处理大量这些对象,并且在处理时需要通过id引用它们,而且我没有能力更改它们的格式(我通过网络从外部检索它们),因此我希望将它们复杂的字符串id映射到我自己的内部整数id,并进一步使用它进行比较,以便将它们进一步传输到其他进程,等等 我要做的是使用一个简单的dict,其中键作为对象的字符串id,整数值作为对象的内部整数id 我的问题是:Pytho

我编写的程序处理大量对象,每个对象都有自己唯一的id,而id本身就是一个复杂结构的字符串(对象的十几个唯一字段由一些分隔符连接),长度很大

由于我必须快速处理大量这些对象,并且在处理时需要通过id引用它们,而且我没有能力更改它们的格式(我通过网络从外部检索它们),因此我希望将它们复杂的字符串id映射到我自己的内部整数id,并进一步使用它进行比较,以便将它们进一步传输到其他进程,等等

我要做的是使用一个简单的dict,其中键作为对象的字符串id,整数值作为对象的内部整数id

我的问题是:Python中有没有更好的方法来实现这一点?也许有一种方法可以手动计算一些散列,不管怎样?也许口述不是最好的解决办法


至于数字:系统中一次大约有10万个这样的唯一对象,因此整数容量就足够了。

出于比较目的,您可以
插入
字符串,然后将它们与
is
进行比较,而不是
=
,后者进行简单的指针比较,速度应尽可能快(或快于)比较两个整数:

>>> 'foo' * 100 is 'foo' * 100
False
>>> intern('foo' * 100) is intern('foo' * 100)
True
intern
保证
id(intern(A))==id(intern(B))
iff
A==B
。请确保
intern
任何字符串一经输入就立即输入。请注意,
intern
在Python 3.x中被称为
sys.intern

但是当您必须将这些字符串传递给其他进程时,您的
dict
解决方案似乎是最好的

str_to_id = {}
for s in strings:
    str_to_id.setdefault(s, len(str_to_id))
所以整数容量已经足够了


Python整数是大整数,所以这应该不会是问题。

如果它们存储在内存中,并且您将每个字符串作为对象而不是文本进行比较,我建议使用
id(string)
获取唯一整数。或者,如果要将它们存储在dict中,则可以使用带有一组匹配项的defaultdict并对其进行哈希:

>>> strings = 'a whole lot of strings which may share a hash'.split()
>>> storage = defaultdict(set)
>>> for s in strings:
...     storage[hash(s)].add(s)
>>> storage[hash('a')]
{'a', 'a'}

具体如何实现这一点取决于您如何使用它们,但基本思想应该是可行的。如果您可以发布一个具体的示例,说明您正在尝试做什么,那么可能更容易给出更详细的答案。

那么
散列函数如何

In [130]: hash
Out[130]: <function hash>

In [131]: hash('foo')
Out[131]: -740391237
[130]中的
:散列
出[130]:
在[131]中:散列('foo')
Out[131]:-740391237
不需要存储散列(除非您愿意):关键是对于值相等的对象,它们是相等的(尽管相反可能不是真的-无疑存在不相等的字符串或散列到相同值的其他对象;这就是散列的本质)

如果您知道密钥的范围(您可能知道),还可以使用一个完美的哈希函数生成器

完美哈希保证指定范围内的密钥与其哈希值具有双射关系。

您可以使用其中一种算法创建长消息的加密语音摘要,然后将其用作字典密钥。使用SHA-256的示例:

import hashlib
...
key = hashlib.sha256(longMessage).digest()
与使用哈希(longMessage)相比,这种方法发生冲突的可能性要小得多


但是,这可能会带来巨大的开销。除非内存使用是一个大问题,否则我只会将原始字符串用作键。

dict
是一个很好的解决方案。如果您有一种基于字符串ID生成唯一ID的方法,您可以将其作为自定义字符串类的哈希函数执行双重任务:

class ID_String(str):
    cached_hash = None
    def __hash__(self):
        # custom hash code here
        return custom_hash
    def ID(self):
        if self.cached_hash is None:
            self.cached_hash = self.__hash__()
        return self.cached_hash

为此,我使用了以下方法:

>>> from collections import defaultdict
>>> d = defaultdict(lambda: len(d))
>>> d["cats"]
0
>>> d["cars"]
1
>>> d["cats"]
0

id
只有在实习后才能用于此目的。比较两个对象的
id
与比较
是一样的。是的。这就是为什么我说作为对象而不是文本进行比较。实习当然是必要的,然后id会给出一个唯一的整数。感谢伟大的链接和建议,Marcin!碰撞是什么首先,我关心的是:我想使用我自己的哈希函数,扩展我对密钥结构的知识,但是为了处理冲突,我必须实现整个slots机制,而dict()免费提供给我,尽管它的内部散列可能更通用,因此不如我对特定字符串所做的有效。这对我不起作用,当我实际为两个字符串打印
intern
时:
featureVal是美分编码的特征值是4571865856 featureVal是数字槽编码的特征值ue是4571867200 featureVal是bn编码的特征值是4537878648 featureVal是沙特编码的特征值是4571865856
-请注意,
cents
一词与
saudi
的特征值完全相同。该行是
print“featureVal is”,featureVal print“Encoded feature value is”,id(内部)(str(功能值编码(“utf-8”))