2014-03-04 5 views
1

У меня есть CSV-файл, как это:Преобразование csv в словарь с несколькими значениями?

pos,place 
6696,266835 
6698,266835 
938,176299 
940,176299 
941,176299 
947,176299 
948,176299 
949,176299 
950,176299 
951,176299 
770,272944 
2751,190650 
2752,190650 
2753,190650 

Я хочу, чтобы преобразовать его в словарь, как следующее:

{266835:[6696,6698],176299:[938,940,941,947,948,949,950,951],190650:[2751,2752,2753]} 

И затем, заполнить недостающие числа в диапазоне от значений:

{{266835:[6696,6697,6698],176299:[938,939,940,941,942,943,944,945,946947,948,949,950,951],190650:[2751,2752,2753]} 
} 

Прямо сейчас я пытался построить словарь, используя решение, предложенное here, но он переписывает старое значение Wi го нового.

Любая помощь будет отличной.

Вот функция, я написал для преобразования csv2dict

def csv2dict(filename): 
""" 
reads in a two column csv file, and the converts it into dictionary 
""" 
import csv 
with open(filename) as f: 
    f.readline()#ignore first line 
    reader=csv.reader(f,delimiter=',') 
    mydict=dict((rows[1],rows[0]) for rows in reader) 
return mydict 
+0

Посмотрите на [csv.DictReader] (http://docs.python.org/3/library/csv.html#csv.DictReader). Я бы привел пример, но я никогда не использовал его сам, поэтому я тоже буду разбираться в документах! Это, безусловно, возможно алгоритмически, но я думаю, что 'csv.DictReader' сделает тяжелую работу для вас. –

+0

Я добавил функцию, которую я написал для преобразования cdv в словарь. – msakya

+0

Что со вторым набором фигурных скобок, или это ошибка? Что касается заполнения значения, вы можете получить минимальное и максимальное количество конечных точек и просто генерировать диапазон для каждого (без учета значений промежуточного уровня). –

ответ

4

Самый простой заключается в использовании collections.defaultdict() со списком:

import csv 
from collections import defaultdict 

data = defaultdict(list) 

with open(inputfilename, 'rb') as infh: 
    reader = csv.reader(infh) 
    next(reader, None) # skip the header 

    for col1, col2 in reader: 
     data[col2].append(int(col1)) 
     if len(data[col2]) > 1: 
      data[col2] = range(min(data[col2]), max(data[col2]) + 1) 

Это также расширяет диапазоны «на лету», когда вы читаете данные.

+0

В чем преимущества расширения списка на диапазон во время чтения, а не на прохождение каждой клавиши после ее чтения? –

+1

@adsmith: не очень много преимуществ, на самом деле, но это упростило код здесь. –

+0

СПАСИБО. он работал, мне пришлось изменить последнюю строку, чтобы преобразовать строки в список в integer. данные [col2] = диапазон (min (карта (int, данные [col2])), max (карта (int, данные [col2])) + 1) – msakya

1

Основываясь на том, что вы пробовали -

from collections import default dict 

# open archive reader 
myFile = open ("myfile.csv","rb") 
archive = csv.reader(myFile, delimiter=',') 
arch_dict = defaultdict(list) 

for rows in archive: 
    arch_dict[row[1]].append(row[0]) 

print arch_dict 
Смежные вопросы