在Python中执行文本预处理时出错

在Python中执行文本预处理时出错,python,pandas,nltk,Python,Pandas,Nltk,我已经编写了两个函数来处理文本文档,并将它们转换成文字包。在此之前,我通过删除停止词、标记化等来清理文本,并将清理后的文本文档存储为一个列表,我打算将其作为参数传递给另一个函数,该函数将从中创建单词包功能 以下是功能: def cleaningDocs(doc,stem): # 'S' for Stemming, 'L' for Lemmatization """This function cleans each doc string by doing the following:

我已经编写了两个函数来处理文本文档,并将它们转换成文字包。在此之前,我通过删除停止词、标记化等来清理文本,并将清理后的文本文档存储为一个列表,我打算将其作为参数传递给另一个函数,该函数将从中创建单词包功能

以下是功能:

def cleaningDocs(doc,stem):  # 'S' for Stemming, 'L' for Lemmatization
    """This function cleans each doc string by doing the following: 
    i)   Removing punctuation and other non alphabetical characters
    ii)  Convert to Lower case and split string into words (tokenization)
    ii)  Removes stop words (most frequent words)
    iii) Doing Stemming and Lemmatization
    """

    # Removing punctuations and other non alphabetic characters
    import re
    alphabets_only=re.sub(r'[^a-zA-Z]'," ",doc)

    # Converting to lower case and splitting the words(tokenization)
    words_lower=alphabets_only.lower().split()

    # Removing stop words (Words like 'a', 'an', 'is','the' which doesn't contribute anything
    from nltk.corpus import stopwords
    useful_words = [w for w in words_lower if not w in set(stopwords.words("english"))] 

    # Doing Stemming or Lemmatization (Normalising the text)
    from nltk.stem import PorterStemmer, WordNetLemmatizer
    if (stem=='S'):  # Choosing between Stemming ('S') and Lemmatization ('L')
        stemmer=PorterStemmer()
        final_words=[stemmer.stem(x) for x in useful_words]
    else: 
        lemma=WordNetLemmatizer()
        final_words=[lemma.lemmatize(x) for x in useful_words]

    return(str(" ".join(final_words)))    
现在这里是文档字符串列表。这是一个pandas系列对象

type(docs)
Out[53]:
pandas.core.series.Series
此文档中的每个元素都是一个字符串。基本上每个元素都是一个文本文档,我想预处理每个文本文档(去掉停止词、柠檬化等),并将其保存为一个新的已处理列表

type(docs[0])
Out[55]:
str
理想情况下,我想这样做:

doc=[]
for x in docs:
    doc.append(cleaningDocs(x,"L"))
因此,对于docs系列中的每个字符串文档,我们使用停止词和其他内容将其删除,并将其保存回文档列表

上面的代码给了我这个错误:

---------------------------------------------------------------------------
TypeError                                 Traceback (most recent call last)
<ipython-input-56-61345bb4d581> in <module>()
      1 doc=[]
      2 for x in docs:
----> 3     doc.append(cleaningDocs(x,"L"))
      4 

<ipython-input-42-6e1c58274c3d> in cleaningDocs(doc, stem)
     13     # Removing punctuations and other non alphabetic characters
     14     import re
---> 15     alphabets_only=re.sub(r'[^a-zA-Z]'," ",doc)
     16 
     17     # Converting to lower case and splitting the words(tokenization)

/Users/mtripathi/anaconda/lib/python2.7/re.pyc in sub(pattern, repl, string, count, flags)
    153     a callable, it's passed the match object and must return
    154     a replacement string to be used."""
--> 155     return _compile(pattern, flags).sub(repl, string, count)
    156 
    157 def subn(pattern, repl, string, count=0, flags=0):

TypeError: expected string or buffer
如果您看到该函数按要求执行,请从原始文档中删除停止字并对其进行柠檬化,然后将其保存回新的已处理文档列表。但是,如果我一次只发送一个文档,它是有效的。在for循环中发送所有文档时,它会抛出一个错误,为什么会这样

编辑:

好的,我刚刚检查了文档中每个元素的类型,看到有一些问题发生了,有一些元素被转换为float。见下文:

for x in docs: 
    print(type(x))
<type 'str'>
<type 'str'>
<type 'str'>
<type 'float'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
<type 'str'>
对于文档中的x:
打印(类型(x))
有两件事:

1) 我想看看这个文档中浮动的元素。
2). 第二,如果我想将所有元素转换为字符串,我想我们可以这样做。astype()?

这里有两个主要思想:和

布尔索引允许您使用真/假数组选择序列的子集,函数应用程序将单个函数应用于序列中的每个项

首先,应用
isinstance
确定哪些元素是浮动的,然后切片序列以取回元素

然后只要应用
str
就可以了

import pandas as pd

test = pd.Series(["Hey", "I'm", 1.0, "or", 2.0, "floats"])
# Find floats 
floats = test[test.apply(lambda x: isinstance(x, float))]
# Make all strings
test_as_strings = test.apply(str)

看起来您正试图将一个列表
doc
传递到
re.sub()
,而您应该只传递一个字符串。我只传递一个字符串,如果您看到?。docs是一个系列,docs的元素是字符串,如上所示。当我在docs中为x执行操作时,我会得到一个字符串(文本文档),并传递该字符串。这就是为什么如果我只检查一个文档,它就会工作。请检查编辑。我在docsInvestigate中找到了一些float值,如果isinstance(x,str)为False,则通过。刚才看到了。我有一些缺失的值,它们被报告为nan,并被铸造为float。请添加一些解释。传授底层逻辑比仅仅给出代码更重要,因为它可以帮助OP和其他读者自己解决这个问题和类似的问题。
import pandas as pd

test = pd.Series(["Hey", "I'm", 1.0, "or", 2.0, "floats"])
# Find floats 
floats = test[test.apply(lambda x: isinstance(x, float))]
# Make all strings
test_as_strings = test.apply(str)