Заполнить значение для строки фрейма данных на основе условия - PullRequest
2 голосов
/ 14 июля 2020

Фон

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

product_name    price
Women's pant    20.00
Men's Shirt     30.00
Women's Dress   40.00
Blue Shirt      30.00
...

Я хочу создать новый столбец с именем

пол

, который будет содержать значения Women, Men или Unisex на основе строки в product_name

Желаемый результат будет выглядеть так:

product_name    price   gender
Women's pant    20.00   women
Men's Shirt     30.00   men
Women's Dress   40.00   women
Blue Shirt      30.00   unisex

Мой подход

Я решил, что сначала я должен создать новый столбец с пустым значением для каждой строки. Затем я должен пропустить oop через каждую строку в фрейме данных и проверить строку df [product_name], чтобы увидеть, мужское ли это, женское или мужское, и заполнить соответствующее значение гендерной строки.

Вот это мой код:

df['gender'] = ""
for product_name in df['product_name']:
    if 'women' in product_name.lower():
        df['gender'] = 'women'
    elif 'men' in product_name.lower():
        df['gender'] = 'men'
    else:
        df['gender'] = 'unisex'

Однако я получаю следующий результат:

product_name    price   gender
Women's pant    20.00   men
Men's Shirt     30.00   men
Women's Dress   40.00   men
Blue Shirt      30.00   men

Я был бы очень признателен за помощь здесь, поскольку я новичок в библиотеках python и pandas.

Ответы [ 4 ]

4 голосов
/ 14 июля 2020

Вы можете использовать понимание списка с if/else, чтобы получить результат:

df['gender'] = ['women' if 'women' in word 
                else "men" if "men" in word
                else "unisex" 
                for word in df.product_name.str.lower()]

df

   product_name    price    gender
0   Women's pant    20.0    women
1   Men's Shirt     30.0    men
2   Women's Dress   40.0    women
3   Blue Shirt      30.0    unisex

В качестве альтернативы вы можете использовать numpy select для достижения тех же результатов:

cond1 = df.product_name.str.lower().str.contains("women")
cond2 = df.product_name.str.lower().str.contains("men")
condlist = [cond1, cond2]
choicelist = ["women", "men"]
df["gender"] = np.select(condlist, choicelist, default="unisex")

Обычно для строк итерация python выполняется намного быстрее; Вы должны это проверить.

2 голосов
/ 14 июля 2020

Вы также можете использовать np.where + Series.str.contains,

import numpy as np

df['gender'] = (
    np.where(df.product_name.str.contains("women", case=False), 'women',
             np.where(df.product_name.str.contains("men", case=False), "men", 'unisex'))
)

    product_name  price  gender
0   Women's pant   20.0   women
1    Men's Shirt   30.0     men
2  Women's Dress   40.0   women
3     Blue Shirt   30.0  unisex
2 голосов
/ 14 июля 2020

Попробуйте превратить ваш оператор for в функцию и использовать apply. Так что что-то вроде -

def label_gender(product_name):
    '''product_name is a str'''
    if 'women' in product_name.lower():
        return 'women'
    elif 'men' in product_name.lower():
        return 'men'
    else:
        return 'unisex'

df['gender'] = df.apply(lambda x: label_gender(x['product_name']),axis=1)

Хорошее описание использования apply / lambda можно найти здесь: https://towardsdatascience.com/apply-and-lambda-usage-in-pandas-b13a1ea037f7

1 голос
/ 14 июля 2020

Используйте np.where .str.contains и regex first word` во фразе. Так что;

#np.where(if product_name has WomenORMen, 1st Word in Phrase, otherwise;unisex)



 df['Gender']=np.where(df.product_name.str.contains('Women|Men')\
                      ,df.product_name.str.split('(^[\w]+)').str[1],'Unisex')


 
    product_name  price  gender
0   Women's pant   20.0   Women
1    Men's Shirt   30.0     Men
2  Women's Dress  640.0   Women
3    Blue Shirt    30.0  Unisex
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...