2014-11-24 64 views
0

我要创建一个基于CSV文件看起来像这样一本字典创建字典:从文本文件的Python

'song, 2000, 184950' 
'boom, 2009, 83729' 
'boom, 2010, 284500' 
'boom, 2011, 203889' 
'pow, 2000, 385920' 
'pow, 2001, 248930' 
从这个

,我要创建一个包含字的字典键,然后将类对象列表作为值。

这是我迄今为止...

class Counter(): 
    __slots__ = ('year', 'count') 
    _types = (int, int) 

def readfile(file): 
    d = dict() 
    with open(file) as f: 
     for line in f: 
      element = line.split(,) 
      for word in element: 
       if word in d: 
        d[word].append([Count(int(element[1]), int(element[2]))]) 
       else: 
        d[word] = [Count(int(element[1]), int(element[2]))] 
    print(d) 

我得到的输出是奇怪的,它是给我一本词典类似地雷应该是什么样子,但它的使用计数(183930 )作为关键字而不是名称。如果它已经在字典中列出,我还需要它将该类添加到该值。

例如,因为'繁荣'应该已经在字典中{'boom' : Count(year = 2009, count = 83729)}我希望那里有一个计数对象列表中的一个值。

预期输出:

{'song' : [Count(year= 2000, count= 184950)], 'boom' : [Count(year=2009, count=83729), 
Count(year=2010, count= 284500), Count(year=2011, count=203889)], 'pow' : ...etc..} 
+0

@Martijn你确定'''应该在csv例子中?我认为他们对字符串有意义,但不能作为示例csv。 – Vyktor 2014-11-24 20:10:57

+0

@Vyktor:OP在他们的样本中使用了这个;我会留给他们删除它。 – 2014-11-24 20:12:59

+0

您的代码无效;它缺少引号(以逗号为例),而发布的'Counter()'类将不起作用。你可以给我们*工作代码*? – 2014-11-24 20:14:50

回答

0

有了这个循环:

for word in element: 
    if word in d: 
     d[word].append([Count(int(element[1]), int(element[2]))]) 
    else: 
     d[word] = [Count(int(element[1]), int(element[2]))] 

你迭代槽上线的所有的话,那么你打电话(对第一行):

d['song'].append([Count(int('2000'), int('184950'))]) 
d['2000'].append([Count(int('2000'), int('184950'))]) 
d['184950'].append([Count(int('2000'), int('184950'))]) 

只需使用:

for line in f: 
    element = line.split(,) 
    word = element[0] 
    if word in d: 
     d[word].append(Count(int(element[1]), int(element[2]))) 
    else: 
     d[word] = [Count(int(element[1]), int(element[2]))] 

你,如果你使用collections.defaultdict也可以代替你的病情if word in d

import collections 

def readfile(file): 
    d = collections.defaultdict(list) 
    with open(file) as f: 
     for line in f: 
      element = line.split(,) 
      word = element[0] 
      d[word].append(Count(int(element[1]), int(element[2]))) 

    print(d) 
+0

或者您可以使用'd.setdefault(word,[])。append(...)'(使用常规的'dict'而不是'defaultdict')。 – 2014-11-24 20:47:09

+0

@Martijn很好,我不知道这个......但是对我来说似乎有点奇怪(特别是/不是这种情况/如果你有多个分支代码可以填充字典,你将不得不复制每个地方的默认值)。 – Vyktor 2014-11-24 20:54:34

+0

谢谢!这对我有用! defaultdict对我来说是新的,所以谢谢你给我一种替代方式! @Vyktor – kbaumzie 2014-11-25 15:39:07

0

下面是一些简单的代码,做你在找什么。

from collections import defaultdict 
from pprint import pprint 


class Counter(object): 
    __slots__ = ('year', 'count') 

    def __init__(self, year, count): 
     self.year = year 
     self.count = count 

    def __str__(self): 
     return "Counter(year=%d, count=%d)" % (self.year, self.count) 

    def __repr__(self): 
     return self.__str__() 


def import_counts(): 
    counts = defaultdict(list) 
    with file('data.csv') as f: 
     for line in f: 
      name, year, count = line.split(',') 
      name, year, count = name.strip(), int(year.strip()), int(count.strip()) 
      counts[name].append(Counter(year, count)) 

    return counts 

pprint(import_counts()) 

但是,我将数据格式更改为正确的CSV,如下所示。

song, 2000, 184950 
boom, 2009, 83729 
boom, 2010, 284500 
boom, 2011, 203889 
pow, 2000, 385920 
pow, 2001, 248930 

产生的输出是如下:

{ 
    'boom': [ 
     Counter(year=2009, count=83729), 
     Counter(year=2010, count=284500), 
     Counter(year=2011, count=203889) 
    ], 
    'pow': [ 
     Counter(year=2000, count=385920), 
     Counter(year=2001, count=248930) 
    ], 
    'song': [ 
     Counter(year=2000, count=184950) 
    ] 
} 

别注意,如果给定的一个无效的CSV上述不验证输入和将错误。