Python 无需重构即可重用词典

Python 无需重构即可重用词典,python,algorithm,python-2.7,dictionary,data-structures,Python,Algorithm,Python 2.7,Dictionary,Data Structures,p/S:项目中的方法 正在重新创建新的子键字典。它很慢(我已经试过了)。下面shx2给出的使用Subdiview的答案在效率方面非常好 我有一本python字典,例如 d={"a1":Obj1, "a2":Obj2,"a3":Obj3,...,"a10":Obj10} 其中Obj1到Objn是一些自建python类的对象 问题是,在1亿次的循环中,我在每次迭代中需要不同的密钥子集,比如说我需要“a1”到“a3”,我现在要做的是重建字典 d1={"a1":Obj1, "a2":Obj2,"a3"

p/S:项目中的方法 正在重新创建新的子键字典。它很慢(我已经试过了)。下面shx2给出的使用Subdiview的答案在效率方面非常好

我有一本python字典,例如

d={"a1":Obj1, "a2":Obj2,"a3":Obj3,...,"a10":Obj10}
其中
Obj1
Objn
是一些自建python类的对象

问题是,在1亿次的循环中,我在每次迭代中需要不同的密钥子集,比如说我需要
“a1”
“a3”
,我现在要做的是重建字典

d1={"a1":Obj1, "a2":Obj2,"a3":Obj3}
只要我想用它。最后,我重建了1亿本字典

有没有一种更有效的方法来处理这种情况(例如,在循环中每次不重建字典的情况下静音
d
中我不感兴趣的键?

一种(面向速度的)解决方案是使用

如果需要不是连续索引的关键帧子集,仍然可以使用以下内容:

subseries3 = series.ix[[1,3,8]]
虽然在这种情况下,它可能会慢一点,因为这种索引(与切片相反)会导致创建一个新的序列(而不是原始序列的视图,后者要快得多)


pandas.Series
有一个界面,在某些方面类似于
dict
s,因此您不需要对其余代码进行太多(或根本不需要)更改。

您的问题还不清楚,但如果我理解正确,您可以使用。如果你的字典是这样的:

d = {'a1': 1, 'a2': 2, 'a3': 3, 'a4': 4, 'a5': 5}
然后:

您可以使用以下“轻量级”子目录视图类。这可能是最快的方法,因为它避免了在每次迭代时创建新的dict(创建视图对象很快)



如果您已经将密钥子集存储为
,则可以通过避免在
\uuuuu init\uuuuuu
中转换为-
来获得更高的速度,需要注意的是
集(dict)
不会在Python 2.7中创建视图(正如公认的答案所暗示的那样)。它创建了一个集合,这样做实际上相当慢。Python2.7中的字典视图可通过字典上的
view*
方法访问(在本例中,我们希望
dict.viewkeys()

以1亿次的循环进行访问,每次迭代我都需要不同的密钥子集
-您能解释一下吗?您是否有一个数据结构来保存每次迭代的所有子集?是否@shx2,哪个子集取决于输入数据,可以假定这些子集在高级中是未知的。@william007使用键访问项目时有问题吗?@thefourtheye没有问题,但假设子集是
“a1”
“a2”
“a3”
,使用
d
,而不重建新词典,
“a10”在d
中将返回true,这不是我想要的。如果子集是(1,3,8)怎么办?在这种情况下,我想,它类似于创建一个新的
dict
?@thefourtheye,在这种情况下,是的(但更容易编码),但如果索引是连续的,它不是。@shx2是否可以使用字符串键?在我的例子中,字符串键可能类似于“3dsfd”@shx2,但我如何知道键的子集是(1,3,8)?由于字符串可以是任何类似“342dfsaf”的字符串,谢谢,这与我的想法一致of@shx2/@william007,你在这里所取得的成就是,你现在做的不是1亿个字典的重建,而是1亿个集合的重建。这不会提高性能。@shx2,是的,但是您也可以创建原始字典的子字典,并使用它们来代替或使用原始字典。无论采用哪种方法,都必须在循环内部或循环开始之前创建1亿个哈希。@shx2谢谢,我已经测试过这种方法。这种方法确实比重新创建字典快。我将您的答案从列表改为集合,因为如果不进行转换,答案会更快。即使我在一个集合中通过,在子视图中使用集合(键),它也会运行得较慢。@DebanshuKundu它确实运行得更快!即使有列表转换,它也会运行得更快,但是没有转换肯定会更快。谢谢,但这不是我要问的问题,所以很抱歉。我需要的是一个字典
d
其中
“a1”在d
中返回true,而
“a2”在d
中返回false,
d[“a1”]
将返回1,
d[“a2”]
将抛出异常,如果子集是
“a1”、“a3”、“a5”
@william007:再次,请您解释一下您从哪里获得这些密钥。什么样的数据结构保存您想要用来制作新dict的值
“a1”、“a2”、“a3”
?您可以假设这些值是由用户给定的,也可以假设包含它们的任何数据结构。
d = {'a1': 1, 'a2': 2, 'a3': 3, 'a4': 4, 'a5': 5}
>>> operator.itemgetter('a1', 'a3', 'a5')(d)
(1, 3, 5)
from UserDict import DictMixin

class SubDictView(DictMixin):

    def __init__(self, dct, keys):
        self._dct = dct
        self._keys = keys

    def __getitem__(self, key):
        if key not in self._keys:
            raise KeyError(key)
        return self._dct[key]

    def keys(self):
        return set(self._dct) & self._keys

    def __setitem__(self, key, val):
        raise RuntimeError('SubDictView is read-only')

    def __delitem__(self, key):
        raise RuntimeError('SubDictView is read-only')

d = {'a': 1, 'b': 2, 'c': 3}
dv = SubDictView(d, {'b', 'c'})
print dv
# {'c': 3, 'b': 2}
print 'a' in dv
# False
print dv['b']
# 2
print dv.get('a', 999)
# 999