Need to split and check if the list element is available in pandas df

Viewed 52

I need to get the items available from the two lists and then check if they are available in a string.

list1 = ['Cat', 'Dog', 'Crow']
list2 = ['Wild', 'Pet']

Df

ind              Camp      
1              Ball_Dog_Wild_Ear
2              Dog_Ball_Pet_Dos
3              Wild_Dos_Cat_Pre
4              Pet_Cer_Crow_Tre
5              Dos_Cat_Wild_Tre

I need to split the "Camp" based on "_" and then check on position 0 and 2 if the item from list exact matches.

Desired output:

ind              Camp      
1              Ball_Dog_Wild_Ear        False     #False because 0 position has ball(not in list)
2              Dog_Ball_Pet_Dos         True      #True because 0 and 2 both available in the list
3              Wild_Dos_Cat_Pre         True
4              Pet_Cer_Crow_Tre         True
5              Dos_Cat_Wild_Tre         False

I can do split via df['Camp'].str.rsplit("_", expand=True)

and check with .isin() but not sure how we can do for each rows to get the desired output.

3 Answers

Here is my suggestion:

#get all combinations of 2 from list1 &list2 both ways:
l = [(i,k) for i in list1 for k in list2] + [(i,k) for i in list2 for k in list1]

#get the items from positions 0 and 2 as tuple:
df['new']=df.Camp.apply(lambda x: (x.split('_')[0],x.split('_')[2]))

#check if this pair is in l:
df['check']=df.new.apply(lambda x: x in l)

del df['new']

>>>print(df)

   ind               Camp  check
0    1  Ball_Dog_Wild_Ear  False
1    2   Dog_Ball_Pet_Dos   True
2    3   Wild_Dos_Cat_Pre   True
3    4   Pet_Cer_Crow_Tre   True
4    5   Dos_Cat_Wild_Tre  False

With a list comprehension:

cond = lambda x, y: (x in list1 and y in list2) or (x in list2 and y in list1)
df["res"] = [cond(zeroth, second) for zeroth, _, second, _ in df.Camp.str.split("_")]

where cond checks if entries are in the corresponding lists in a cross manner.

>>> df

   ind               Camp    res
0    1  Ball_Dog_Wild_Ear  False
1    2   Dog_Ball_Pet_Dos   True
2    3   Wild_Dos_Cat_Pre   True
3    4   Pet_Cer_Crow_Tre   True
4    5   Dos_Cat_Wild_Tre  False

You can do it this way with itertools.product, set and isin:

from itertools import product

#create a set list of products from list1 and list2
sl = [set(i) for i in product(list1, list2)]

#split, slice for 0 and 2, apply set and check using isin set list(sl)
df['check'] = (df['Camp'].str.split('_', expand=True)
                         .loc[:,[0,2]].apply(set, axis=1).isin(sl))

df

Output:

   ind               Camp  check
0    1  Ball_Dog_Wild_Ear  False
1    2   Dog_Ball_Pet_Dos   True
2    3   Wild_Dos_Cat_Pre   True
3    4   Pet_Cer_Crow_Tre   True
4    5   Dos_Cat_Wild_Tre  False
Related