Агрегирование по случайным подмножествам n строк кадра данных в python - PullRequest
1 голос
/ 30 марта 2020

Я пытаюсь объединить случайные подмножества фрейма данных python с n строками. Мой текущий подход состоит в том, чтобы l oop проходить через строки и назначать «идентификатор группы» в новом столбце, а затем агрегировать в этом столбце, но мой фрейм данных содержит сотни тысяч строк, и это слишком медленно. Каков более эффективный способ сделать это?

rand = np.random.RandomState(1)
df = pd.DataFrame({'column1': rand.randn(300000), 'column2': rand.rand(300000)})
df['groupid'] = 0
df = df.sample(frac=1).reset_index(drop=True) #randomize dataframe rows
group_size = [1, 10, 100, 1000, 10000]
for size in group_size:
        group_num = 0
        for position in range(0, len(df), size):
            df.iloc[position:position + size, df.columns.get_loc('groupid')] =  group_num
            group_num+=1

        results = df.groupby(['groupid'], as_index=True).agg({'column1': 'mean', 'column2': 'mean'})

Редактировать: мне нужно использовать каждую строку данных ровно один раз. Выходными данными должен быть кадр данных с каждой строкой, представляющей среднее значение столбца1 и столбца2 для каждой группы (так, чтобы results.shape[0] = np.ceil(df.shape[0]/size))

Обновление: Мне удалось быстро достичь желаемого поведения с помощью сначала рандомизируют фрейм данных, а затем используют itertools для создания списка с повторяющимися последовательными числами:

rand = np.random.RandomState(1)
df = pd.DataFrame({'column1': rand.randn(300000), 'column2': rand.rand(300000)})
df = df.sample(frac=1).reset_index(drop=True) #randomize dataframe rows
group_size = [1, 10, 100, 1000, 10000]
for size in group_size:
        df['groupid'] = list(itertools.chain.from_iterable(itertools.repeat(x, size) for x in range(int(np.ceil(df.shape[0]/size)))))[0:df.shape[0]]
        results = df.groupby(['groupid'], as_index=True).agg({'column1': 'mean', 'column2': 'mean'})

Ответы [ 2 ]

1 голос
/ 30 марта 2020

Вы можете использовать функцию np.random.shuffle для случайного перемешивания массива:

n = df.shape[0]
for gs in group_size:

    a = np.hstack([np.repeat(np.arange(gs), n//gs), np.arange(n%gs)]) 
    np.random.shuffle(a)

    df[f'group_size_{gs}'] = a

Обратите внимание, что np.random.shuffle изменяет массив на месте.

0 голосов
/ 30 марта 2020

Pandas имеет встроенный метод выборки.

df = df.sample(n=10)

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

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...