Python:字典中的列表的列表

3 投票
3 回答
1054 浏览
提问于 2025-04-16 05:00
def makecounter():
     return collections.defaultdict(int)

class RankedIndex(object):
  def __init__(self):
    self._inverted_index = collections.defaultdict(list)
    self._documents = []
    self._inverted_index = collections.defaultdict(makecounter)


def index_dir(self, base_path):
    num_files_indexed = 0
    allfiles = os.listdir(base_path)
    self._documents = os.listdir(base_path)
    num_files_indexed = len(allfiles)
    docnumber = 0
    self._inverted_index = collections.defaultdict(list)

    docnumlist = []
    for file in allfiles: 
            self.documents = [base_path+file] #list of all text files
            f = open(base_path+file, 'r')
            lines = f.read()

            tokens = self.tokenize(lines)
            docnumber = docnumber + 1
            for term in tokens:  
                if term not in sorted(self._inverted_index.keys()):
                    self._inverted_index[term] = [docnumber]
                    self._inverted_index[term][docnumber] +=1                                           
                else:
                    if docnumber not in self._inverted_index.get(term):
                        docnumlist = self._inverted_index.get(term)
                        docnumlist = docnumlist.append(docnumber)
            f.close()
    print '\n \n'
    print 'Dictionary contents: \n'
    for term in sorted(self._inverted_index):
        print term, '->', self._inverted_index.get(term)
    return num_files_indexed
    return 0

我在执行这段代码时遇到了索引错误:列表索引超出范围。

上面的代码生成了一个字典,这个字典用'词语'作为键,存储这个词语出现的文档编号,文档编号以列表的形式呈现。比如,如果'猫'这个词出现在1.txt、5.txt和7.txt这三个文档中,字典的内容会是: 猫 <- [1,5,7]

现在,我需要修改它,加入词频的统计,也就是说,如果'猫'这个词在文档1中出现了两次,在文档5中出现了三次,在文档7中出现了一次,期望的结果是: 词语 <- [[文档编号, 词频], [文档编号, 词频]] <--字典中的列表的列表!!! 猫 <- [[1,2],[5,3],[7,1]]

我尝试了很多方法,但都没有成功。我不知道该如何修改这个数据结构来实现上述功能。

提前谢谢你。

3 个回答

0

也许你可以创建一个简单的类,用来存储(文档名,出现频率)。

然后你的字典可以包含这个新数据类型的列表。你也可以使用列表的列表,但使用一个单独的数据类型会更整洁。

1

这里有一个你可以使用的通用算法,不过你需要根据自己的代码做一些调整。这个算法会生成一个字典,里面包含每个文件的单词计数。

filedicts = {}
for file in allfiles:
  filedicts[file] = {}

  for term in terms:
    filedict.setdefault(term, 0)
    filedict[term] += 1
6

首先,使用一个工厂。可以从下面的代码开始:

def makecounter():
    return collections.defaultdict(int)

然后再使用:

self._inverted_index = collections.defaultdict(makecounter)

接下来是这个循环:

        for term in tokens:  
                self._inverted_index[term][docnumber] +=1

这样在每个 self._inverted_index[term] 中会留下一个像这样的字典:

{1:2,5:3,7:1}

在你的例子中。因为你想要的是在每个 self._inverted_index[term] 中放一个列表的列表,所以在循环结束后,添加:

self._inverted_index = dict((t,[d,v[d] for d in sorted(v)])
                            for t in self._inverted_index)

一旦创建好(无论是这样还是其他方式——我只是展示一个简单的构建方法!),这个数据结构在使用上会和你构建时让它变得复杂一样麻烦,当然(字典的字典在使用和构建上都更有用且简单),不过,嘿,这就是个人喜好嘛。

撰写回答