2011-07-13 24 views

Trả lời

7

Dưới đây là một cách:

result = dict(d2) 
for k in d1: 
    if k in result: 
     result[k] = (result[k] + d1[k])/2.0 
    else: 
     result[k] = d1[k] 
+0

Tôi muốn giới thiệu sử dụng 'd2.copy () 'thay vì' dict (d2) '. Đó là một trifle nhanh hơn (và nhanh hơn cho một dict với vài mặt hàng, lên đến khoảng hai lần nhanh), và theo ý kiến ​​của tôi một chút rõ ràng hơn. –

+0

Tôi cũng nhân với 0,5 thay vì chia. – psihodelia

2

Tuy nhiên, một cách khác:

result = dict(d1) 
for (k,v) in d2.items(): 
    result[k] = (result.get(k,v) + v)/2.0 
+0

+1: Rất xảo quyệt! Bạn cần phải sửa chữa các tên biến mặc dù. – phant0m

+0

cũng được phát hiện và được sửa đổi cẩn thận. cảm ơn. – Frank

6

Điều này sẽ làm việc cho bất kỳ số lượng các từ điển:

dicts = ({"a": 5},{"b": 2, "a": 10}, {"a": 15, "b": 4}) 
keys = set() 
averaged = {} 
for d in dicts: 
    keys.update(d.keys()) 
for key in keys: 
    values = [d[key] for d in dicts if key in d] 
    averaged[key] = float(sum(values))/len(values) 
print averaged 
# {'a': 10.0, 'b': 3.0} 

Cập nhật: @mhyfritz cho thấy cách bạn có thể giảm 3 dòng thành một!

dicts = ({"a": 5},{"b": 2, "a": 10}, {"a": 15, "b": 4}) 
averaged = {} 
keys = set().union(*dicts) 
for key in keys: 
    values = [d[key] for d in dicts if key in d] 
    averaged[key] = float(sum(values))/len(values) 
print averaged 
+2

+1 cho giải pháp tổng quát! –

+1

+1. Như một lưu ý phụ, bạn có thể viết 'keys = set(). Union (* dicts)'. Điều này làm cho việc sử dụng thực tế là một 'tập' của một' dict' (chỉ) chứa 'dict''s _keys_. – mhyfritz

+0

@mhyfritz: Heh, điều này thật tuyệt! - BTW: @user có hoạt động trong các câu trả lời không? – phant0m

3

Câu hỏi của bạn là theo cách 'Pythonic' nhất.

Tôi nghĩ rằng đối với một vấn đề như thế này, cách Pythonic là một điều rất rõ ràng. Có nhiều cách để thực hiện giải pháp cho vấn đề này! Nếu bạn thực sự chỉ có 2 dicts thì các giải pháp cho rằng điều này là tuyệt vời vì chúng đơn giản hơn nhiều (và dễ đọc hơn và duy trì kết quả). Tuy nhiên, nó thường là một ý tưởng tốt để có giải pháp chung vì nó có nghĩa là bạn sẽ không cần phải sao chép số lượng lớn của logic cho các trường hợp khác, nơi bạn có 3 từ điển, ví dụ.

Là phụ lục, câu trả lời của phant0m rất hay vì nó sử dụng rất nhiều tính năng của Python để làm cho giải pháp có thể đọc được. Chúng tôi nhìn thấy một danh sách hiểu:

[d[key] for d in dicts if key in d] 

Sử dụng rất hữu ích set loại Python:

keys = set() 
keys.update(d.keys()) 

Và nói chung, sử dụng tốt các phương pháp loại Python và globals:

d.keys() 
keys.update(...) 
keys.update 
len(values) 

tư duy và thực hiện một thuật toán để giải quyết vấn đề này là một điều, nhưng làm cho nó thanh lịch và dễ đọc bằng cách sử dụng sức mạnh của ngôn ngữ là những gì hầu hết mọi người sẽ coi là 'Pythonic'.

(Tôi sẽ sử dụng giải pháp phant0m của)

+0

+1: Cảm ơn bạn đã phân tích tốt đẹp :) – phant0m

+0

@ phant0m cảm ơn vì giải pháp tuyệt vời :) – adamnfish

+0

+1, bây giờ phân tích tôi: P –

0

Một Counter và một số phát điện rất hữu ích trong tình huống này

Trường hợp chung:

>>> d1 = { 'apples': 2, 'oranges':5 } 
>>> d2 = { 'apples': 1, 'bananas': 3 } 
>>> all_d=[d1,d2] 
>>> from collections import Counter 
>>> counts=Counter(sum((d.keys() for d in all_d),[])) 
>>> counts 
Counter({'apples': 2, 'oranges': 1, 'bananas': 1}) 
>>> s=lambda k: sum((d.get(k,0) for d in all_d)) 
>>> result_set=dict(((k,1.0*s(k)/counts[k]) for k in counts.keys())) 
>>> result_set 
{'apples': 1.5, 'oranges': 5.0, 'bananas': 3.0} 
0
d1 = { 'apples': 2, 'oranges':5 } 
d2 = { 'apples': 1, 'bananas': 3, 'oranges':0 } 
dicts = [d1, d2] 

result_dict = {} 

for dict in dicts: 
    for key, value in dict.iteritems(): 
     if key in result_dict: 
      result_dict[key].append(value) 
     else: 
      result_dict[key] = [value] 

for key, values in result_dict.iteritems(): 
    result_dict[key] = float(sum(result_dict[key]))/len(result_dict[key]) 

print result_dict 
Các vấn đề liên quan