2015-02-05 4 views
1

이 함수는 birdnames 키와 가중치를 값으로 사용하여 파일을 사전에 읽는 것을 의미합니다. 그것은 내가 원하는 것을하고 있지만 모든 라인을 통과하지는 못하고 이유를 모르겠다! 여자애를 도와 줘?사전 파이썬에 파일 읽기

def bird_weights(filename): 
    bird_dict = {} 
    f = open(filename, "r") 
    for line in f: 
     new_line = line.split(":") 
     bird_type = new_line[0].capitalize() 
     bird_weight = new_line[1].strip().split(' ') 
     bw_list = [float(i) for i in bird_weight] 
     bird_dict[bird_type] = bw_list 
     if bird_type in bird_dict: 
      bird_dict[bird_type].extend(bw_list) 
     else: 
      bird_dict[bird_type] = bw_list 

    return bird_dict 

.txt 파일은 다음과 같습니다 : 여기 내 코드입니다

bluebird:78.3 89.3 77.0 
TANAGER: 111.9 107.65 
BlueBird: 69.9 
bluebirD: 91.9 
tanager: 108.0 110.0 

와 내가 무엇입니까 것은 코드가

{"Bluebird":[78.3, 89.3, 77.0, 69.9, 91.9],"Tanager": [111.9, 107.65, 108.0, 110.0]} 

을 생산하기위한 것입니다 :

{"Bluebird":[91.9, 91.9], "Tanager": [108.0, 110.0, 108.0, 110.0] } 

잘 모르겠습니다. 이유

+0

@eumiro 나중에 생각합니다. 업데이트됩니다. –

답변

0

언제든지 Bluebird을 볼 때 이미 이미 있던 내용을 덮어 쓰게됩니다.

for line in f: 
    ... 
    if bird_type in bird_dict: 
     bird_dict[bird_type].extend(bw_list) 
    else: 
     bird_dict[bird_type] = bw_list 

bird_type에 대한 기존 목록에 추가하려면 다음과 같은 것을보십시오.

+0

bw_list 란 무엇입니까? –

+0

원래 코드에서 새 가중치 목록. –

+0

코드와 결과가 업데이트되었습니다. 그것은 옳지 않습니다./ –

1

파이썬의 사전에 중복 키가 없기 때문입니다. 새 이름을 동일하게 만드는 '자본화'방법을 사용하고 있습니다.

1
def bird_weights(filename): 
    result = collections.defaultdict(list) 

    with open(filename, 'r') as f: 
     for line in f.readlines(): 
      bird_name, values = line.strip().split(':') 

      # normalization 
      bird_name = bird_name.strip().capitalize() 
      values = map(lambda v: float(v.strip()), values.strip().split(' ')) 

      result[bird_name].extend(values) 

    return result 
+1

기본 사전은 멋지고 우아합니다. –

+0

capitalize()를 호출하는 경우 lower()가 필요하지 않습니다. – helloV

+0

감사합니다. @helloV, 답변을 업데이트했습니다. – ozgur

0

파이썬 사전에는 같은 값의 키가 여러 개있을 수 없습니다.

당신 등 각 인스턴스에 정수를 추가 할 수 있습니다 : A의 extendappend을 변경

birds={} 
with open(file) as f: 
    for line in f: 
     k,_,v=line.partition(':') 
     k=k.capitalize() 
     v=map(float, v.split()) 
     birds.setdefault(k, []).append(v) 

{'Bluebird': [[78.3, 89.3, 77.0], [69.9], [91.9]], 
'Tanager': [[111.9, 107.65], [108.0, 110.0]]} 

또는를 : 구조의 나열 종류의 목록을 사용

keys={} 
birds={} 
with open(file) as f: 
    for line in f: 
     k,_,v=line.partition(':') 
     k=k.capitalize() 
     v=map(float, v.split()) 
     keys[k]=keys.setdefault(k, 0)+1 
     birds.setdefault('{} {}'.format(k, keys[k]), []).extend(v) 


{'Tanager 1': [111.9, 107.65], 
'Tanager 2': [108.0, 110.0], 
'Bluebird 3': [91.9], 
'Bluebird 2': [69.9], 
'Bluebird 1': [78.3, 89.3, 77.0]} 

또는 평면 목록 :

birds={} 
with open(file) as f: 
    for line in f: 
     k,_,v=line.partition(':') 
     k=k.capitalize() 
     v=map(float, v.split()) 
     birds.setdefault(k, []).extend(v) 

{'Bluebird': [78.3, 89.3, 77.0, 69.9, 91.9], 'Tanager': [111.9, 107.65, 108.0, 110.0]} 
0

그래서 이미 많은 해결책이 있다는 것을 알고 있습니다. 그러나 하나만 더 게시 할 것입니다 :)

당신의 인생을 조금 더 편하게하고 싶고 코드에 혼란스럽지 않으려면 너무 쉽게, 때로는 가장 짧지 만 읽을 수있는 솔루션을 구현하는 데 도움이됩니다. 이 코드 조각에서 무언가를 변경하려고 할 때 당신이하고있는 일을 절반 만 이해하면 현재 반쯤은 어려움을 겪을 것입니다.

그래서 여기 내 공정하게 표현 솔루션이며, 난 당신이 정확하게 당신이 당신의 bird_weights() 기능을 통해 읽을 때 내가 무슨 짓을했는지 이해할 수있을 것 같아요 :

class Bird(object): 
    def __init__(self, name, weights): 
     self.name = name 
     self.weights = weights 

    def __str__(self): 
     return self.name + ':' + str(self.weights) 

def get_float_list(weights): 
    return [float(i.strip()) for i in weights.strip().split(' ')] 

def print_birds(birdlist): 
    print '{' 
    for i in birdlist: 
     print str(i) + ',' 
    print '}' 

def bird_weights(f): 
    birdlist = [] 
    for line in f: 
     name, weights = line.split(':') 
     birdy = Bird(name.capitalize(), get_float_list(weights)) 
     birdlist.append(birdy) 
    print_birds(birdlist) 

해피 :)

편집을 펄럭 : 죄송합니다. 지금은 열린 파일 개체 (또는 테스트를 위해 내가했던 것처럼 문자열 목록)를이 함수에 전달해야한다는 점을 잊어 버렸습니다.