2012-06-20 43 views
0

是否可以根據字符串的值創建變量名稱?來自字符串的Python名稱變量

我有一個腳本,它將讀取信息塊的文件並將它們存儲在字典中。然後將每個塊的字典附加到「主」字典中。文件中的信息塊數量會有所不同,並使用「完成」一詞來指示塊的結束。

我想要做這樣的事情:

master={} 
block=0 
for lines in file: 
    if line != "done": 
    $block.append(line) 
    elif line == "done": 
    master['$block'].append($block) 
    block = block + 1 

如果一個文件有像這樣的內容:

eggs 
done 
bacon 
done 
ham 
cheese 
done 

結果將與3所列出的字典:

master = {'0': ["eggs"], '1': ["bacon"], '2': ["ham", "cheese"]} 

這怎麼可能完成?

+0

讓你的字典實際上是一個python字典。 –

+0

在我看來,你不需要字典,因爲你使用從0開始的整數對字典項目進行索引。使用列表來代替。 –

+0

也許我不應該包含這個例子,但我仍然想知道是否有一種方法可以根據字符串的值命名變量(而不僅僅是一個字典鍵) – Rauffle

回答

3

我真的建議你使用一個列表,而不是。有沒有什麼特別的地方,爲什麼你需要數組是這樣的字典?

在情況下,你可以使用數組做,你可以這樣做:

with open("yourFile") as fd: 
    arr = [x.strip().split() for x in fd.read().split("done")][:-1] 

輸出:

[['eggs'], ['bacon'], ['ham', 'cheese']] 

如果你想數串指數,你可以使用這個:

with open("yourFile") as fd: 
    l = [x.strip().split() for x in fd.read().split("done")][:-1] 
    print dict(zip(map(str,range(len(l))),l)) 
+0

@Downvoters:你能解釋一下這個動作嗎? – SuperSaiyan

+0

爲什麼有人不喜歡這個?在我看來,它比其他答案更爲正確,因爲它不僅回答了問題,而且還提供了比OP更精緻的數據結構。 –

+0

@Rauffle:我沒有得到你。什麼?? – SuperSaiyan

0

使用setattr或globals()。
請參閱How do I call setattr() on the current module?

+0

閱讀問題,這實際上不是他詢問 –

+0

事實上,如果是這樣,你的答案是正確的,所以我會在那裏留下一個,並提出你的觀點。 –

2

您似乎誤解了詞典是如何工作的。他們拿鑰匙作爲物品,所以這裏不需要任何魔法。

但是,我們可以通過使用collections.defaultdict來根據需要製作子列表,從而使您的代碼更好。

from collections import defaultdict 

master = defaultdict(list) 
block = 0 
for line in file: 
    if line == "done": 
     block += 1 
    else: 
     master[block].append(line) 

但是,如果你想要連續的,編號的索引 - 這就是列表的用途,那麼我會建議不需要字典。在這種情況下,我建議你遵循Thrustmaster's first suggestion,或者,作爲一種替代方案:

from itertools import takewhile 

def repeat_while(predicate, action): 
    while True: 
     current = action() 
     if not predicate(current): 
      break 
     else: 
      yield current 

with open("test") as file: 
    action = lambda: list(takewhile(lambda line: not line == "done", (line.strip() for line in file))) 
    print(list(repeat_while(lambda x: x, action))) 
0

這是您的代碼,對於juxtapos銀行足球比賽:

master={} 
block=0 
for lines in file: 
    if line != "done": 
    $block.append(line) 
    elif line == "done": 
    master['$block'].append($block) 
    block = block + 1 

由於在後由法拓士所提到的,它使在這裏使用一個嵌套列表更有意義。以下是你如何做到這一點;我已經改變了儘可能少的結構從原來的代碼:

master=[[]] # Start with a list containing only a single list 
for line in file: # Note the typo in your code: you wrote "for lines in file" 
    if line != "done": 
    master[-1].append(line) # Index -1 is the last element of your list 
    else: # Since it's not not "done", it must in fact be "done" 
    master.append([]) 

這裏唯一的事情是,你會在你的master列表的末尾有一個額外的列表結束,所以你應該添加一行到del ETE最後,空子列表:

del master[-1] 
1

我覺得「做」是註定要失敗的那一剎那。考慮名單:

eggs 
done 
bacon 
done 
rare steak 
well done stake 
done 

從法拓士(我給了一個+1我盜竊)偷我建議:

>>> dict(enumerate(l.split() for l in open(file).read().split('\ndone\n') if l)) 
{0: ['eggs'], 1: ['bacon'], 2: ['ham', 'cheese']} 

我知道這需要一個結尾的「\ n」。如果有問題,可以使用「open(file).read()+'\ n'」甚至「+'\ n \ ndone \ n'」,如果最終完成是可選的。