将(lambda)函数映射到字符串列表会使'float'对象无法迭代 [英] mapping a (lambda) function to lists of strings fails 'float' object not iterable

查看:120
本文介绍了将(lambda)函数映射到字符串列表会使'float'对象无法迭代的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我尝试了解Python脚本出现问题的地方.我有一个pandas系列列表(diagnoses),每个列表都有一个字符串列表(从不为空).我可以并且确实使用diagnoses.map(type)

I try to understand where my Python script goes awry. I have a pandas Series (diagnoses) of lists, each a list of strings (never empty). I can and did verify this with diagnoses.map(type) and

for x in diagnoses[0]:
    type x

但是,当我将lambda函数映射到该系列列表时,我得到了TypeError: 'float' object not iterable.

Yet when I would map a lambda function to this Series of lists, I get a TypeError: 'float' object not iterable.

想象数据看起来像这样:

Imagine the data looking like this:

LopNr   AR  var3    va4 var5    var6    var7    var8    var9    var10   DIAGNOS
6   2011                                    S834
6   2011                                    K21 S834

代码是:

from pandas import *
tobacco = lambda lst: any( (((x >= 'C30') and (x<'C40')) or ((x >= 'F17') and (x<'F18')))  for x in lst)
treatments = read_table(filename,usecols=[0,1,10])
diagnoses = treatments['DIAGNOS'].str.split(' ')
treatments['tobacco'] = diagnoses.map(tobacco)

这是怎么回事,我该如何解决?

What is going on, and how can I fix this?

PS:如果首先使用IOpro导入源文本文件并从该适配器构建数据帧,则相同的代码肯定会在非常相似的Series上运行,请参见下文.我不确定为什么会更改相关的数据类型,只要我能验证pandas系列在任何一种情况下都具有字符串列表……这是使用Python 2.7.6和pandas 0.13.1的.

PS: The same code definitely runs on a very similar Series if I import the source text file with IOpro first and build a dataframe from that adapter, see below. I am not sure why that would change the relevant datatypes, as far as I could verify the pandas Series has lists of strings in either case… This is with Python 2.7.6 and pandas 0.13.1.

import iopro
adapter = iopro.text_adapter(filename,parser='csv',field_names=True,output='dataframe',delimiter='\t')
treatments = adapter[['LopNr','AR','DIAGNOS']][:]

推荐答案

如果数据缺少DIAGNOS的值,则可能发生TypeError: 'float' object is not iterable.例如,当数据如下所示:

The TypeError: 'float' object is not iterable could happen if the data is missing a value for DIAGNOS. For example, when data looks like this:

LopNr   AR  var3    va4 var5    var6    var7    var8    var9    var10   DIAGNOS
6   2011    a   a   a   a   a   a   a   a   S834
6   2011    a   a   a   a   a   a   a   a   
6   2011    a   a   a   a   a   a   a   a   K21 S834

然后

    In [68]: treatments = pd.read_table('data', usecols=[0,1,10])

In [69]: treatments
Out[69]: 
       LopNr    AR   DIAGNOS
0          6  2011      S834
1          6  2011       NaN
2          6  2011  K21 S834

[3 rows x 3 columns]

DIAGNOS列中的NaN是问题的根源,因为str.split(' ')保留NaN:

The NaN in the DIAGNOS column is the source of the problem, since str.split(' ') preserves the NaN:

In [70]: diagnoses = treatments['DIAGNOS'].str.split(' ')

In [71]: diagnoses
Out[72]: 
0         [S834]
1            NaN
2    [K21, S834]
Name: DIAGNOS, dtype: object

当调用diganose.map(tobacco)时,NaN被传递给tobacco函数.由于NaN是浮点且不可迭代,因此for x in lst循环会引发TypeError.

The NaN gets passed to the tobacco function when diganose.map(tobacco) is called. Since NaN is a float and not iterable, the for x in lst loop raises the TypeError.

为避免此错误,请替换treatments['DIAGNOS']中的NaN:

To avoid this error, replace the NaNs in treatments['DIAGNOS']:

import pandas as pd

def tobacco(lst):
    return any((('C30' <= x < 'C40') or ('F17' <= x <'F18')) for x in lst)

treatments = pd.read_table('data', usecols=[0,1,10])
treatments['DIAGNOS'].fillna('', inplace=True)
diagnoses = treatments['DIAGNOS'].str.split(' ')
treatments['tobacco'] = diagnoses.map(tobacco)
print(treatments)

收益

       LopNr    AR   DIAGNOS tobacco
0          6  2011      S834   False
1          6  2011             False
2          6  2011  K21 S834   False

[3 rows x 4 columns]

这篇关于将(lambda)函数映射到字符串列表会使'float'对象无法迭代的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆