Панды - разный набор ключевых слов для разных идентификаторов, поиск, если строка содержит ключевое слово - PullRequest
0 голосов
/ 17 ноября 2018

У меня есть 2 набора фреймов данных

   IDs    Keywords
0  1234   APPLE ABCD
1  1234   ORANGE
2  1234   LEMONS
3  5346   ORANGE
4  5346   STRAWBERRY
5  5346   BLUEBERRY
6  8793   TEA COFFEE

Второй кадр данных:

   IDs    Name         
0  1234   APPLE ABCD ONE
1  5346   APPLE ABCD   
2  1234   STRAWBERRY YES 
3  8793   ORANGE AVAILABLE  
4  8793   TEA AVAILABLE
5  8793   TEA COFFEE

Я хотел бы искать ключевые слова на основе уровня идентификаторов, используйте его для второго кадра данных и найдите столбец: Имя если ключевые слова, содержащиеся в названии для тех же идентификаторов, существуют, укажите любой индикатор True, иначе False.

Например: Для идентификаторов 1234 ключевыми словами являются APPLE ABCD, ORANGE, LEMONS. Итак, во втором фрейме данных: Индексная строка 0 с APPLE ABCD ONE будет иметь значение True, поскольку «APPLE ABCD» является частью ключевых слов

Для идентификаторов 5346 ключевыми словами являются ОРАНЖЕВЫЙ, КЛУБНИЧНЫЙ, ЧЕРНЫЙ. Таким образом, во втором информационном кадре индексная строка 1 с APPLE ABCD будет иметь значение False.

   IDs    Name               Indicator
0  1234   APPLE ABCD ONE     True
1  5346   APPLE ABCD         False
2  1234   STRAWBERRY YES     False
3  8793   ORANGE AVAILABLE   False
4  8793   TEA AVAILABLE      False
5  8793   TEA COFFEE         True

Ответы [ 3 ]

0 голосов
/ 19 ноября 2018

Вы можете сделать это, используя в основном pandas операции, которые также будут более эффективными.

# Let there be two DataFrames: kw_df, name_df

# Group all keywords of each ID in a list, associate it with the names
kw_df = kw_df.groupby('IDs').aggregate({'Keywords': list})
merge_df = name_df.join(kw_df, on='IDs')

# Check if any keyword is in the name
def is_match(name, kws):
    return any(kw in name for kw in kws)

merge_df['Indicator'] = merge_df.apply(lambda row: is_match(row['Name'], row['Keywords']), axis=1)
print(merge_df)

Это дает следующий вывод:

    IDs              Name                         Keywords  Indicator
0  1234    APPLE ABCD ONE     [APPLE ABCD, ORANGE, LEMONS]       True
1  5346        APPLE ABCD  [ORANGE, STRAWBERRY, BLUEBERRY]      False
2  1234    STRAWBERRY YES     [APPLE ABCD, ORANGE, LEMONS]      False
3  8793  ORANGE AVAILABLE                     [TEA COFFEE]      False
4  8793     TEA AVAILABLE                     [TEA COFFEE]      False
5  8793        TEA COFFEE                     [TEA COFFEE]       True
0 голосов
/ 19 ноября 2018

Вы можете использовать merge при использовании groupby и lambda следующим образом:

>>> df.merge(df2).groupby(['IDs','Name']).apply(lambda x: any(x['Name'].str.contains('|'.join(x['Keywords'])))).rename('Indicator').reset_index()
    IDs              Name  Indicator
0  1234        APPLE ABCD       True
1  1234    STRAWBERRY YES      False
2  5346        APPLE ABCD      False
3  8793  ORANGE AVAILABLE      False
4  8793     TEA AVAILABLE       True
0 голосов
/ 17 ноября 2018

Вам необходимо:

# create a list of tuples from 1st dataframe
kw = list(zip(df1.IDs, df1.Keywords))

def func(ids, name):
    if (ids,name.split(" ")[0]) in kw:
        return True
    return False

df2['Indicator'] = df2.apply(lambda x: func(x['IDs'],x['Names']), axis=1)  

Редактировать

Создать список кортежей с комбинацией идентификаторов и ключевых слов

kw = list(zip(df1.IDs, df1.Keywords))
# [(1234, 'APPLE ABCD'), (1234, 'ORANGE'), (1234, 'LEMONS'), (5346, 'ORANGE'), (5346, 'STRAWBERRY'), (5346, 'BLUEBERRY'), (8793, 'TEA COFFEE')]

unique_kw = list(df1['Keywords'].unique())
# ['APPLE ABCD', 'ORANGE', 'LEMONS', 'STRAWBERRY', 'BLUEBERRY', 'TEA COFFEE']

def samp(x):
    for u in unique_kw:
        if u in x:
            return u
    return None

# This will fetch the keywords from column which will be used for compare  
df2['indicator'] = df2['Names'].apply(lambda x: samp(x))

df2['indicator'] = df2.apply(lambda x: True if (x['IDs'], x['indicator']) in kw else False, axis=1)

Вывод:

    IDs     Names               indicator
0   1234    APPLE ABCD ONE      True
1   5346    APPLE ABCD          False
2   1234    NO STRAWBERRY YES   False
3   8793    ORANGE AVAILABLE    False
4   8793    TEA AVAILABLE       False
5   8793    TEA COFFEE          True
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...