Pandas从str.extractall('#')中给出错误

2024-04-24 13:27:32 发布

您现在位置:Python中文网/ 问答频道 /正文

我正试图过滤tweet文本中的所有#关键字。我使用str.extractall()来提取所有带有#关键字的关键字。 这是我第一次使用pandas从tweetText中过滤关键字。输入、代码、预期输出和错误如下所示。

输入:

userID,tweetText 
01, home #sweet home
01, #happy #life 
02, #world peace
03, #all are one
04, world tour

等等。。。总的数据文件是用GB大小的scraped tweets和其他几列组成的。但我只对两个专栏感兴趣。

代码:

import re
import pandas as pd

data = pd.read_csv('Text.csv', index_col=0, header=None, names=['userID', 'tweetText'])

fout = data['tweetText'].str.extractall('#')

print fout 

预期产量:

userID,tweetText 
01,#sweet
01,#happy 
01,#life 
02,#world
03,#all

错误:

Traceback (most recent call last):
  File "keyword_split.py", line 7, in <module>
    fout = data['tweetText'].str.extractall('#')
  File "/usr/local/lib/python2.7/dist-packages/pandas/core/strings.py", line 1621, in extractall
    return str_extractall(self._orig, pat, flags=flags)
  File "/usr/local/lib/python2.7/dist-packages/pandas/core/strings.py", line 694, in str_extractall
    raise ValueError("pattern contains no capture groups")
ValueError: pattern contains no capture groups

提前谢谢你的帮助。根据用户id筛选关键字的最简单方法应该是什么?

输出更新:

当仅使用此选项时,输出如下 s.name = "tweetText" data_1 = data[~data['tweetText'].isnull()]

本例中的输出是空的[],用户id仍在列表中,对于那些具有关键字的用户,有一个关键字数组而不是列表形式。

当仅使用此选项时,输出我们所需的内容,但使用NAN

s.name = "tweetText"
data_2 = data_1.drop('tweetText', axis=1).join(s)

这里的输出是正确的格式,但是那些没有关键字的输出还没有考虑并且没有

如果有可能的话,我们可以忽略这些用户ID,完全不显示在输出中。在接下来的阶段中,我试图计算关键字的频率,其中NAN或空的[]也将被计算在内,并且该频率可能会损害将来的分类。

enter image description here


Tags: 代码用户inpypandasworlddataline
3条回答

如果您不是太依赖于使用extractall,您可以尝试以下操作来获得最终输出:

from io import StringIO
import pandas as pd
import re


data_text = """userID,tweetText
01, home #sweet home
01, #happy #life 
02, #world peace
03, #all are one
"""

data = pd.read_csv(StringIO(data_text),header=0)

data['tweetText'] = data.tweetText.apply(lambda x: re.findall('#(?=\w+)\w+',x))
s = data.apply(lambda x: pd.Series(x['tweetText']),axis=1).stack().reset_index(level=1, drop=True)
s.name = "tweetText"
data = data.drop('tweetText', axis=1).join(s)

     userID tweetText
0       1    #sweet
1       1    #happy
1       1     #life
2       2    #world
3       3      #all
4       4       NaN

通过执行以下操作,可以删除textweet列返回Nan的行:

data = data[~data['tweetText'].isnull()]

这应该返回:

   userID tweetText
0       1    #sweet
1       1    #happy
1       1     #life
2       2    #world
3       3      #all

我希望这能有帮助。

extractall函数需要一个regex模式,其中捕获组作为第一个参数,您已经为其提供了#

可能的参数是(#\S+)。大括号表示一个捕获组,换句话说,extractall函数需要从每个字符串中提取什么。

示例:

data="""01, home #sweet home
01, #happy #life 
02, #world peace
03, #all are one
"""

import pandas as pd
from io import StringIO

df = pd.read_csv(StringIO(data), 
                 header=None, 
                 names=['col1', 'col2'],
                 index_col=0)

df['col2'].str.extractall('(#\S+)')

上面的代码不再出现错误ValueError: pattern contains no capture groups(这意味着问题已经解决),但这在当前版本的pandas中遇到了一个错误(我正在使用'0.18.1')。

返回的错误为:

AssertionError: 1 columns passed, passed data had 6 columns

这个问题被描述为here

如果您尝试df['col2'].str.extractall('#(\S)')(这将为您提供每个标签的第一个字母),您将看到只要捕获的组只包含一个字符(与问题描述匹配),那么extractall函数就可以工作。由于问题已经结束,应该在即将发布的熊猫版中解决。

在微积分中设置大括号:

fout = data['tweetText'].str.extractall('(#)')

而不是

fout = data['tweetText'].str.extractall('#')

希望能奏效

相关问题 更多 >