Python 追加数据帧中所有行的单词或字符列表

Python 追加数据帧中所有行的单词或字符列表,python,pandas,Python,Pandas,有没有一种方法可以在不使用“for”循环的情况下附加数据帧中不同行中的列表 我可以通过使用“for”循环来实现这一点,但我希望以更有效的方式实现这一点,可能不需要使用“for”循环 d = {'col1': [1,2,3,4,5], 'col2': [['a'],['a','b','c'],['d'],['e'],['a','e','d']]} df = pd.DataFrame(data=d) word_list = [] for i in df['col2']: word_list =

有没有一种方法可以在不使用“for”循环的情况下附加数据帧中不同行中的列表

我可以通过使用“for”循环来实现这一点,但我希望以更有效的方式实现这一点,可能不需要使用“for”循环

d = {'col1': [1,2,3,4,5], 'col2': [['a'],['a','b','c'],['d'],['e'],['a','e','d']]}
df = pd.DataFrame(data=d)
word_list = []
for i in df['col2']:
  word_list = word_list + i

我想得到这样一个输出列表:['a','a','b','c','d','e','a','e','d']

找不到重复,列表的总和将返回一个组合列表

df.col2.sum()

['a', 'a', 'b', 'c', 'd', 'e', 'a', 'e', 'd']
或者使用Numpy

np.sum(df.col2.values)

一种方法是使用
panda
sum
函数:

In [1]: import pandas as pd
   ...: d = {'col1': [1,2,3,4,5], 'col2': [['a'],['a','b','c'],['d'],['e'],['a','e','d']]}
   ...: df = pd.DataFrame(data=d)

In [2]: df['col2'].sum()
Out[2]: ['a', 'a', 'b', 'c', 'd', 'e', 'a', 'e', 'd']
但是,
itertools.chain.from\u iterable
要快得多:

In [3]: import itertools
   ...: list(itertools.chain.from_iterable(df['col2']))
Out[3]: ['a', 'a', 'b', 'c', 'd', 'e', 'a', 'e', 'd']

In [4]: %timeit df['col2'].sum()
92.7 µs ± 1.03 µs per loop (mean ± std. dev. of 7 runs, 10000 loops each)

In [5]: %timeit list(itertools.chain.from_iterable(df['col2']))
20.4 µs ± 2.62 µs per loop (mean ± std. dev. of 7 runs, 100000 loops each)
在我的测试中,
itertools.chain.from\u iterable
对于较大的数据帧(~1000行)可以快30倍。另一个选择是

import functools
import operator

functools.reduce(operator.iadd, df['col2'], [])
它的速度几乎与itertools.chain.from\u iterable一样快。我为张贴的所有答案制作了一张图表:

(x轴是数据帧的长度)

如您所见,使用
sum
functools.reduce
运算符的所有操作都不可用,而
np.concat
稍好一些。然而,目前的三大赢家是
itertool.chain
itertool.chain.from\u iterable
,以及
functools.reduce
with
operators.iadd
。他们几乎不花时间。以下是用于生成绘图的代码:

import functools
import itertools
import operator
import random
import string

import numpy as np
import pandas as pd
import perfplot # see https://github.com/nschloe/perfplot for this awesome library


def gen_data(n):
    return pd.DataFrame(data={0: [
        [random.choice(string.ascii_lowercase) for _ in range(random.randint(10, 20))]
        for _ in range(n)
    ]})

def pd_sum(df):
    return df[0].sum()

def np_sum(df):
    return np.sum(df[0].values)

def np_concat(df):
    return np.concatenate(df[0]).tolist()

def functools_reduce_add(df):
    return functools.reduce(operator.add, df[0].values)

def functools_reduce_iadd(df):
    return functools.reduce(operator.iadd, df[0], [])

def itertools_chain(df):
    return list(itertools.chain(*(df[0])))

def itertools_chain_from_iterable(df):
    return list(itertools.chain.from_iterable(df[0]))

perfplot.show(
    setup=gen_data,
    kernels=[
        pd_sum,
        np_sum,
        np_concat,
        functools_reduce_add,
        functools_reduce_iadd,
        itertools_chain,
        itertools_chain_from_iterable
    ],
    n_range=[10, 50, 100, 500, 1000, 1500, 2000, 2500, 3000, 4000, 5000],
    equality_check=None
)

或者使用
numpy。连接

print(np.concatenate(df['col2']).tolist())
输出:

['a', 'a', 'b', 'c', 'd', 'e', 'a', 'e', 'd']
好的,另一种方式(仅供参考):

或:


这对我没用。我得到的
[['a'],['a','b','c'],['d'],['e'],['a','e','d']
和的复杂度为O(n^2),因此对于较大的数据帧,30x将变得更高。它实际上不适用于任何有100k+行的情况。所有可能的答案都可以在jezrael的这篇文章中找到。这个问题的概念没有什么不同,但方法是你能学到的。伟大的天才:)谢谢@meW.)很高兴您喜欢它。很抱歉再次向您推荐,但这比我的
functools慢30-40倍。对于1000行的数据帧,请使用上面的reduce
解决方案。@anky_91我测试了第一个和第二个,我正在谈论第二个。我们的答案有些相似,如果您感兴趣,我为所有答案添加了完整的性能比较。
from functools import reduce
reduce(lambda x,y: x+y,df.col2.values)
from functools import reduce
import operator
reduce(operator.add,df.col2.values)

#['a', 'a', 'b', 'c', 'd', 'e', 'a', 'e', 'd']