I want to subtract the two following tuples from each other to get the desired result (also included below). Note that the subtraction is based on only the a of the (a, b).
# the two tuples
first = [(('the',), 431), (('and',), 367)]
second = [(('the',), 100), (('hello',), 100)]
# the desired result
first = [(('and',), 367)]
second = [(('hello',), 100)]
I tried map(operation.sub, first, second)
, didn't work. Tried b = map(sub, first, second)
, didn't work. Says unsupported operand type(s) for -: 'tuple' and 'tuple .
Thanks for your help and time in advance.
Edit : A solution that would help me most would include creating an intersection of the two tuples and subtracting that from each of the tuples.
Edit: I want to subtract based on common items. Hope that clarifies it.
Here is what you are looking for -
# the two tuples
first = [(('the',), 431), (('and',), 367)]
second = [(('the',), 100), (('hello',), 100)]
interim1 = {i[0][0]:i[1] for i in first}
interim2 = {i[0][0]:i[1] for i in second}
op1 = [ ((item,),interim1[item]) for item in interim1 if item not in interim2]
op2 = [ ((item,),interim2[item]) for item in interim2 if item not in interim1]
print(op1)
print(op2)
Intersection (Edit)
intersection = [ ((item,),interim1[item]) for item in interim1 if item in interim2]
print(intersection)
Union (Extra)
union = set().union(*[ op1, op2, intersection])
print(union)
Output
[(('the',), 431)]
[(('and',), 367)]
[(('hello',), 100)]
{(('hello',), 100), (('and',), 367), (('the',), 431)}
You can use set
with below list comprehension to get the desired result as:
>>> first = [(('the',), 431), (('and',), 367)]
>>> second = [(('the',), 100), (('hello',), 100)]
>>> [t for t in first+second if t[0] in set(f[0] for f in first) ^ (set(s[0] for s in second))]
[(('and',), 367), (('hello',), 100)]
Explanation:
Here, I am using set to get the non-common words in the two list by performing XOR (also know as Exclusive OR) on two sets. For example:
>>> first_words = set(f[0] for f in first)
>>> second_words = set(s[0] for s in second)
>>> first_words ^ second_words
set([('hello',), ('and',)])
Then I am iterating on both the list within list comprehension and checking whether they are present in above set of non-common words tuples. If they are present, then we are keeping it as the part of new list as:
>>> result = [t for t in first+second if t[0] in first_words ^ second_words]
# where `result` will hold value `[(('and',), 367), (('hello',), 100)]`
## If your resultant lists contains only two variable,
## then you may assign them directly to individual variable as:
# f, s = [t for t in first+second if t[0] in first_words ^ second_words]
## where `f` first required tuple will hold
# >>> f
# (('and',), 367)
## and `s` second required tuple will hold
# >>> s
# (('hello',), 100)
Maybe follow is what you want:
# the two tuples
first = [(('the',), 431), (('and',), 367)]
second = [(('the',), 100), (('hello',), 100)]
first_keys = set(_[0][0] for _ in first)
second_keys = set(_[0][0] for _ in second)
first = [_ for _ in first if _[0][0] not in second_keys]
second = [_ for _ in second if _[0][0] not in first_keys]
multi = [
[(('the',), 431), (('and',), 367)],
[(('the',), 100), (('hello',), 100)]
]
def get_key(x):
return x[0][0]
def occur_counts(set_x):
cnt = {}
for x in set_x:
cnt[get_key(x)] = cnt.get(get_key(x), 0) + 1
return cnt
def do_one(single, total_cnt):
single_cnt = occur_counts(single)
return [_ for _ in single if single_cnt[get_key(_)] == total_cnt[get_key(_)]]
total_cnt = occur_counts(sum(multi, []))
answer = [do_one(_, total_cnt) for _ in multi]
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.