【问题标题】:How to determine the length of lists in a pandas dataframe column如何确定熊猫数据框列中列表的长度
【发布时间】:2016-12-27 06:48:15
【问题描述】:

如何在不迭代的情况下确定列中列表的长度?

我有一个这样的数据框:

                                                    CreationDate
2013-12-22 15:25:02                  [ubuntu, mac-osx, syslinux]
2009-12-14 14:29:32  [ubuntu, mod-rewrite, laconica, apache-2.2]
2013-12-22 15:42:00               [ubuntu, nat, squid, mikrotik]

我正在计算CreationDate 列中列表的长度并创建一个新的Length 列,如下所示:

df['Length'] = df.CreationDate.apply(lambda x: len(x))

这给了我这个:

                                                    CreationDate  Length
2013-12-22 15:25:02                  [ubuntu, mac-osx, syslinux]       3
2009-12-14 14:29:32  [ubuntu, mod-rewrite, laconica, apache-2.2]       4
2013-12-22 15:42:00               [ubuntu, nat, squid, mikrotik]       4

有没有更 Pythonic 的方式来做到这一点?

【问题讨论】:

    标签: python pandas


    【解决方案1】:

    您也可以将str 访问器用于某些列表操作。在这个例子中,

    df['CreationDate'].str.len()
    

    返回每个列表的长度。请参阅str.len 的文档。

    df['Length'] = df['CreationDate'].str.len()
    df
    Out: 
                                                        CreationDate  Length
    2013-12-22 15:25:02                  [ubuntu, mac-osx, syslinux]       3
    2009-12-14 14:29:32  [ubuntu, mod-rewrite, laconica, apache-2.2]       4
    2013-12-22 15:42:00               [ubuntu, nat, squid, mikrotik]       4
    

    对于这些操作,普通 Python 通常更快。 pandas 虽然处理 NaN。以下是时间:

    ser = pd.Series([random.sample(string.ascii_letters, 
                                   random.randint(1, 20)) for _ in range(10**6)])
    
    %timeit ser.apply(lambda x: len(x))
    1 loop, best of 3: 425 ms per loop
    
    %timeit ser.str.len()
    1 loop, best of 3: 248 ms per loop
    
    %timeit [len(x) for x in ser]
    10 loops, best of 3: 84 ms per loop
    
    %timeit pd.Series([len(x) for x in ser], index=ser.index)
    1 loop, best of 3: 236 ms per loop
    

    【讨论】:

      【解决方案2】:
      import pandas as pd
      
      data = {'os': [['ubuntu', 'mac-osx', 'syslinux'], ['ubuntu', 'mod-rewrite', 'laconica', 'apache-2.2'], ['ubuntu', 'nat', 'squid', 'mikrotik']]}
      index = ['2013-12-22 15:25:02', '2009-12-14 14:29:32', '2013-12-22 15:42:00']
      
      df = pd.DataFrame(data, index)
      
      # create Length column
      df['Length'] = df.os.map(len)
      
      # display(df)
                                                                    os  Length
      2013-12-22 15:25:02                  [ubuntu, mac-osx, syslinux]       3
      2009-12-14 14:29:32  [ubuntu, mod-rewrite, laconica, apache-2.2]       4
      2013-12-22 15:42:00               [ubuntu, nat, squid, mikrotik]       4
      

      %timeit

      import pandas as pd
      import random
      import string
      
      random.seed(365)
      
      ser = pd.Series([random.sample(string.ascii_letters, random.randint(1, 20)) for _ in range(10**6)])
      
      %timeit ser.str.len()
      252 ms ± 12.8 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
      
      %timeit ser.map(len)
      220 ms ± 7.2 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
      
      %timeit ser.apply(len)
      222 ms ± 8.31 ms per loop (mean ± std. dev. of 7 runs, 1 loop each)
      

      【讨论】:

        猜你喜欢
        • 2021-04-05
        • 1970-01-01
        • 2015-07-31
        • 2017-08-09
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-03-07
        • 1970-01-01
        相关资源
        最近更新 更多