根据行重复进行Numpy Array可变次数

问题描述

我正在尝试使用熊猫数据框创建一个numpy数组。数据框中的一列名为“ repeat”(重复),指示要重复的值,另一列名为“ times”,指示应重复该值多少次。

这是我尝试过的:

import pandas as pd
import numpy as np

df = pd.DataFrame({'repeat': [1,4,3,2],'times': [2,5,1]})
np.repeat(df['repeat'].values,df['times'])

但是,这将输出以下内容

array([1,1,4,4,4,4,4,3,3,3,3,2])

这就是我想要的:

desired = np.array([[1,1],[4,4],[3,3],[2]])

array([list([1,1]),list([4,4,4,4,4]),list([3,3,3,3]), 清单([2])], dtype = object)

如何有效地沿行重复每个值相应的次数?这里有一个很好的numpy或pandas解决方案吗?

解决方法

您可以通过根据大小将原始结果拆分为索引来获得数组数组:

r = [1,4,3,2]
t = [2,5,1]
np.split(np.repeat(r,t),np.cumsum(t[:-1]))

这将返回一个数组列表,可以说这是一种比列表数组更有效的数据存储方式。请记住,数组适用于连续的数字数据块,而列表适用于任意对象。

,

让我们尝试重复索引和分组依据:

(df.loc[df.index.repeat(df['times']),'repeat']
   .groupby(level=0)
   .agg(list).values
)

输出

array([list([1,1]),list([4,4]),list([3,3]),list([2])],dtype=object)
,

我会做

import itertools
[list(itertools.repeat(x,y)) for x,y  in zip(df['repeat'],df['times'])]
Out[301]: [[1,1],[4,4],[3,3],[2]]

一些时间

#df=pd.concat([df]*100)

%timeit [list(itertools.repeat(x,df['times'])]
178 µs ± 521 ns per loop (mean ± std. dev. of 7 runs,10000 loops each)

%timeit df.loc[df.index.repeat(df['times']),'repeat'].groupby(level=0).agg(list).values
20.2 ms ± 562 µs per loop (mean ± std. dev. of 7 runs,10 loops each)

def func():
    r = df['repeat']
    t = df['times']
    return np.split(np.repeat(r,np.cumsum(t[:-1]))
%timeit func()
45.1 ms ± 846 µs per loop (mean ± std. dev. of 7 runs,10 loops each)