У меня df 4400 строк. Создал этот df при чтении файла xlsx.

Чтобы прояснить мой вопрос, я создал пример df.

Это дает следующий результат (упрощенная версия моей истинной проблемы):

shop          amount
0   shop A      15
1   product 1   4
2   product 2   5
3   product 3   6
4   BBBB        19
5   product 1   7
6   product 2   9
7   product 3   3
8   CCCC        21
9   product 1   6
10  product 2   7
11  product 3   8
12  DDDD        18
13  product 1   4
14  product 2   3
15  product 3   11

Как видите, за каждым названием магазина указано общее количество трех товаров, проданных в этом магазине. В каждом магазине есть одни и те же товары. Но у каждого магазина совершенно разные названия.

Имея 4400 строк и множество магазинов со всеми разными названиями (но с одними и теми же продуктами), я хотел бы развернуть мои df: shopnames в качестве первого столбца и всех продуктов в качестве имен столбцов. И логично, что количество товаров в магазине правильно в правом столбце.

Нет (для меня) никакого способа отличить название магазина от названия продукта. Однако: список продуктов под каждым названием магазина точно такой же и в том же порядке.

Я сам не знаю, как отфильтровать все названия магазинов из названий продуктов. Надеюсь, у кого-то из вас есть идея для меня. Еще раз большое спасибо! привет ян

Ps: я использовал этот код для создания примера df:

d = {'shop': ['shop A', 'product 1', 'product2','product 3','BBBB', 'product 1', 'product 2','product 3','CCCC', 'product 1', 'product 2', 'product 3','DDDD', 'product 1', 'product 2', 'product 3'], 'amount': [15,4,5,6,19,7,9,3,21,6,7,8, 18,4,3,1]}

df = pd.DataFrame(data=d)

df
1
Janneman 14 Сен 2020 в 16:50

2 ответа

Лучший ответ

У вас есть опечатка в наборе данных, product2 должно быть product 2. После исправления вы можете сделать следующее:

import pandas as pd
import numpy as np

d = {'shop': ['shop A', 'product 1', 'product 2','product 3','shop B', 'product 1', 'product 2','product 3','shop C', 'product 1', 'product 2', 'product 3','shop D', 'product 1', 'product 2', 'product 3'], 'amount': [15,4,5,6,19,7,9,3,21,6,7,8, 18,4,3,1]}


df = pd.DataFrame(data=d)

# Create grouping column
df['g']  = np.where(df['shop'].str.contains('shop'), df['shop'], np.nan)
df = df.ffill()

# Get rows that have totals by shop
total_rows = df.groupby('g')['amount'].idxmax().values

# Drop total rows
df = df.loc[~df.index.isin(total_rows)]

# Rename columns
df.columns = ['product','amount','shop']

# Pivot
df.pivot_table(index='shop',columns='product',values='amount')

Выход

product product 1   product 2   product 3
shop            
shop A          4           5           6
shop B          7           9           3
shop C          6           7           8
shop D          4           3           1
1
Chris 14 Сен 2020 в 14:02

Предположим, что названия ваших магазинов уникальны, а товары повторяются:

d = {'shop': ['shop A', 'product 1', 'product 2','product 3','BBBB', 'product 1', 'product 2','product 3','CCCC', 'product 1', 'product 2', 'product 3','DDDD', 'product 1', 'product 2', 'product 3'], 'amount': [15,4,5,6,19,7,9,3,21,6,7,8, 18,4,3,1]}

df = pd.DataFrame(data=d)

g = df.groupby('shop').size().reset_index()
df['g'] = np.where(df['shop'].isin(g[g[0]==1]['shop'].values), df['shop'], np.nan)
# # Create grouping column
# df['g']  = np.where(df['shop'].str.contains('shop'), df['shop'], np.nan)
df = df.ffill()

# Get rows that have totals by shop
total_rows = df.groupby('g')['amount'].idxmax().values

# Drop total rows
df = df.loc[~df.index.isin(total_rows)]

# Rename columns
df.columns = ['product','amount','shop']

# Pivot
df.pivot_table(index='shop',columns='product',values='amount')
0
Chris 14 Сен 2020 в 14:27