2010-07-30 1 views
2

У меня есть dict, { "foo": set(["a", "b"]), "bar": set(["c", "d"]) }, и мне задан элемент одного из двух наборов, а также имя другого. Мне нужно удалить этот элемент. Как мне это сделать? Моя лучшая попытка заключается в следующем:Удалите данный элемент из другого набора в dict из двух наборов

keys = dict.keys() 
if Element in dict[keys[0]].union(dict[keys[1]]): 
    dict[keys[abs(keys.index(Other_Set) - 1)]].remove(Element) 

Это, кажется, немного чрезмерно; есть ли способ улучшить его?

ответ

3

Попробуйте это:

dictionary['foo' if otherset == 'bar' else 'bar'].discard(element) 
+0

Мне нравится это лучше всего. Я бы просто заменил удаление сбрасыванием, как указал Мэтью. – Plumenator

+0

@Plumenator, да, понял, что было бы лучше сразу после. :-) – carl

+0

Поскольку ключи ('foo' и 'bar') введены пользователем, это будет выглядеть не так красиво, как только реализовано, но тем не менее мне оно нравится. Спасибо за помощь. :) – Fraxtil

1

Как насчет:

keys = dict.keys() 
dict[keys[1 - keys.index(Other_Set)]].discard(Element) 

С discard, вы не получите KeyError если элемент не в наборе. Таким образом, вам не нужен ваш чек (другой вариант - просто игнорировать KeyError). И 1 - устраняет необходимость в abs.

0
element = "b" 
other = "bar" 
d = { "foo": set(["a", "b"]), "bar": set(["b", "c"]) } 
theSet = d[[s for s in d.iterkeys() if s != other][0]] 
theSet.discard(element) 
1

Это один может удовлетворить вас, если вы не знаете, априорно имена ключей в dct:

dct={ "foo": set(["a", "b"]), "bar": set(["c", "d"]) } 

element='b' 
other_set='bar' 

for key,value in dct.iteritems(): 
    if key != other_set: 
     value.discard(element) 

print(dct) 
# {'foo': set(['a']), 'bar': set(['c', 'd'])} 
2

Используйте словарь для поиска другой комплект:

>>> other={'foo':'bar','bar':'foo'} 
>>> d = { "foo": set(["a", "b"]), "bar": set(["b", "c"]) } 
>>> element = "b" 
>>> setname = "bar" 
>>> d[other[setname]].discard(element) 
>>> d 
{'foo': set(['a']), 'bar': set(['c', 'b'])} 
0

Мой вариант, общий для любого числа множеств, вынимает данный пункт для всех остальных:

dict_of_sets={'foo':set(['a','b','c']),'bar': set(['d','b','e']),'onemore': set(['a','e','b'])} 
givenset,givenitem='bar','b' 
otherset= (key for key in dict_of_sets if key != givenset) 
for setname in otherset: 
    dict_of_sets[setname].discard(givenitem) 

print dict_of_sets 

"""Output: 
{'foo': set(['c', 'a']), 'bar': set(['e', 'b', 'd']), 'onemore': set(['e', 'a'])} 
""" 
-1

Это гораздо более «вещий» путь:

>>> d = { "foo": set(["a", "b"]), "bar": set(["b", "c"]) } 

>>> d['foo']-=d['bar'] 
>>> d 
{'foo': set(['a']), 'bar': set(['c', 'b'])} 

Конечно d['foo'] может быть d[hashable_key] с hashable_key с пользовательским вводом или что у вас есть.

Recall that the operators- &^| на множествах перегружены соответствующие методы мутируют из:

a_set.difference_update(other_set) # also "-" 
a_set.intersection_update(other_set) # also "&" 
a_set.symmetric_difference_update(other_set) # also "^" 
a_set.update(other_set) # also "-" 

Вы можете использовать дополненное назначение -= изменить заданное значение «Foo» на месте. Все эти другие предлагаемые здесь предложения - слишком многословны для меня.

Редактировать Я неправильно читаю OP и игнорирую это как ответ. Я проголосовал the best solution.

+0

Я не понимаю. Как это решает проблему OP? – Plumenator

+0

@Plumenator: Я неправильно читаю OP и фокусируюсь на результате различий между наборами. Сожалею... –