将每一行转换为几列dataframe Pandas DataFrame

时间:2016-03-04 09:27:21

标签: numpy pandas

我有一个Pandas数据框,其每一行都包含一个索引列表(一列名为“Indexes”,其中有一个逗号分隔的值字符串):

'索引'

'1,4,6,3,2,5,6,8'

'1,7,5,10,23,50'

我想使用apply来创建一个新矩阵(DataFrame?),其每一行在原始数据帧的相应行中列出的值上有1,在其他地方为0。假设我知道新列的数量,因为我有最小和最大索引(比如说0和10)。我可以使用iterrows / itertuples来构建一个新的矩阵,但有没有更有效的方法呢?我有一个1000万行的矩阵,但即使在100k这个很长一段时间。

[实施例]:

为便于理解,我将提供一个示例和所需的输出:

假设MAX_INDEX = 4且MIN_INDEX = 0:

输入:

'1,3,2,4-'

'0,1'

输出将是5列矩阵,有两行,如下所示:

0 1 1 1 1

1 1 0 0 0

[编辑] 问题仍然存在 - 虽然我发现它非常慢,只是因为我使用append创建了新的矩阵,而不是分配内存a-priori而只插入新行。所以一个解决方案是:

m=np.empty(shape=[df.shape[0],numFeatures])
i=0
for row in df.itertuples():
    idxs = row[4] # column of peattributes
    idxs = map(lambda(x):int(x),idxs.split(','))
    r=np.zeros(numFeatures)
    r[idxs] = 1
    m[i,]=r
    i+=1

感谢, 丹

1 个答案:

答案 0 :(得分:0)

编辑:检查表示整数的字符串是否在原始字符串中要快得多(四次):

rng_str = [str(i) for i in range(MIN_INDEX, MAX_INDEX+1)]
s = df['Indexes'].apply(lambda row: [int(i in row) for i in rng_str])
pd.DataFrame(s.tolist())

注意:最后一步从一系列列表转换为数据帧。最后这样做比在apply内更快。

以下原始答案

我有一个解决方案,我很想知道它是否比你的速度更快。第一步是将字符串转换为list:

df['Indexes'] = df['Indexes'].apply(lambda s: [int(x) for x in s.split(',')])

然后我可以使用apply函数逐行生成输出:

rng = range(MIN_INDEX, MAX_INDEX+1)
df.apply(lambda row: [int(i in row['Indexes']) for i in rng], axis=1)

输出:

0    [0, 1, 1, 1, 1]
1    [1, 1, 0, 0, 0]