给定这样的数据框df
:
0 1
1 [12]
1 [13]
2 [11,12]
1 [10,0,1]
....
我想在'12'
的每个列表中计算某个值,例如df
。所以我试过了:
df.apply(list.count('12'))
但收到错误:TypeError: descriptor 'count' requires a 'list' object but received a 'str'
。但它们lists
正好df[1]
!我该如何纠正?谢谢!
答案 0 :(得分:1)
必须在列上应用count
。
# Test data
df = pd.DataFrame({1: [[1], [12], [13], [11,12], [10,0,1]]})
df[1].apply(lambda x: x.count(12))
0 0
1 1
2 0
3 1
4 0
Name: 1, dtype: int64
在某些值未存储在列表中时处理案例的修改
# An example with values not stored in list
df = pd.DataFrame({1: [12, [12], [13], [11,12], [10,0,1], 1]})
_check = 12
df[1].apply(lambda l: l.count(_check) if (type(l) is list) else int(l == _check))
0 1
1 1
2 0
3 1
4 0
5 0
Name: 1, dtype: int64
答案 1 :(得分:1)
我认为您可以先尝试选择列作为系列ix
然后apply
功能x.count(12)
:
import pandas as pd
d = { 0:pd.Series([1,1,2,1]),
1:pd.Series([[12], [13], [11,12 ],[10,0,1]])}
df = pd.DataFrame(d)
print df
0 1
0 1 [12]
1 1 [13]
2 2 [11, 12]
3 1 [10, 0, 1]
print df.ix[:, 1]
0 [12]
1 [13]
2 [11, 12]
3 [10, 0, 1]
Name: 1, dtype: object
print df.ix[:, 1].apply(lambda x: x.count(12))
0 1
1 0
2 1
3 0
Name: 1, dtype: int64
或使用iloc
选择:
print df.iloc[:, 1].apply(lambda x: x.count(12))
0 1
1 0
2 1
3 0
Name: 1, dtype: int64
编辑:
我认为专栏1
包含NaN
。
您可以使用:
print df
0 1
0 1 NaN
1 1 [13]
2 2 [11, 12]
3 1 [10, 0, 1]
print df.ix[:, 1].notnull()
0 False
1 True
2 True
3 True
Name: 1, dtype: bool
print df.ix[df.ix[:, 1].notnull(), 1].apply(lambda x: x.count(12))
1 0
2 1
3 0
Name: 1, dtype: int64
EDIT2:
如果您希望按索引(例如0:2
)和列1
中的NaN进行过滤:
print df
0 1
0 1 NaN
1 1 [13]
2 2 [11, 12]
3 1 [10, 0, 1]
#filter df by index - only 0 to 2
print df.ix[0:2, 1]
0 NaN
1 [13]
2 [11, 12]
Name: 1, dtype: object
#boolean series, where is not nul filtered df
print df.ix[0:2, 1].notnull()
0 False
1 True
2 True
Name: 1, dtype: bool
#get column 1: first is filtered to 0:2 index and then if is not null
print df.ix[0:2, 1][df.ix[0:2, 1].notnull()]
1 [13]
2 [11, 12]
Name: 1, dtype: object
#same as above, but more nice
df1 = df.ix[0:2, 1]
print df1
0 NaN
1 [13]
2 [11, 12]
Name: 1, dtype: object
print df1[df1.notnull()]
1 [13]
2 [11, 12]
Name: 1, dtype: object
#apply count
print df1[df1.notnull()].apply(lambda x: x.count(12))
1 0
2 1
Name: 1, dtype: int64
答案 2 :(得分:0)
您可以使用条件生成器表达式:
df = df = pd.DataFrame({0: [1, 1, 2, 1, 1, 2], 1: [np.nan, [13], [11, 12], [10, 0, 1], [12], [np.nan, 12]]})
target = 12
>>> sum(sub_list.count(target)
for sub_list in df.iloc[:, 1]
if not np.isnan(sub_list).all())
3
这类似于以下条件列表理解:
>>> [sub_list.count(12) for sub_list in df.iloc[:, 1] if not np.isnan(sub_list).all()]
[0, 1, 0, 1, 1]
不同之处在于前者懒惰地评估列表中的每个项目而不是首先生成整个列表,因此通常更有效。