繁体   English   中英

python 字典理解如何与 lambda 函数一起工作

[英]How does python dict comprehension work with lambda functions inside

我的目标是使用agg function 聚合一个 pandas DataFrameGroupBy Object。

为了做到这一点,我正在生成一个字典,我将通过**dict使用 dict 解包将其解包到 kwargs 。 这个字典需要包含新的列名作为键和一个元组作为值。 元组的第一个值是列名,它被压缩成一个系列并作为lambda series: ...

agg_dict = {
   f"{cat_name}_count": ('movement_state', lambda series: series.value_counts()[cat_name]) 
   for cat_name in ml_data['category_column'].cat.categories
}

# Aggregating
agg_ml_data = ml_data.groupby(['col1', 'col2']).agg(**agg_dict)

现在实际发生的事情对我来说有点奇怪。

假设:

ml_data['category_column'].cat.categories
Index(['cat1', 'cat2', 'cat3'], dtype='object')

一组的正确值计数是

one_group['category_column'].value_counts()
     | category_column
cat1 | 2
cat2 | 9
cat3 | 6

一组预期的 output:

cat1_count cat2_count cat3_count
2 9 6

一组实际 output

cat1_count cat2_count cat3_count
6 6 6

不知何故,python 对 lambda function 没有按预期执行字典理解,并且在索引series.value_counts()[cat_name]时仅使用最后一个类别值cat3 我希望 lambda 函数像字典本身一样创建。 关于如何解决该问题的任何想法?

这是一个经典的 Python 陷阱。

当您在 lambda 表达式中使用自由变量(在本例中为cat_name )时,lambda 会捕获名称所指的变量,而不是该变量的值 所以在这种情况下, lambda “记住” cat_name是“该字典理解的循环变量”。 当调用 lambda 时,它会查找“该 dict 理解的循环变量”的值,现在,由于 dict 理解已经完成,它仍然保留在列表的最后一个值。

解决此问题的常用方法是使用默认参数来“冻结”该值,例如

lambda series, cat=cat_name: series.blah[cat]

有效地使用一个陷阱(Python 计算默认 arguments 在 function 定义时间)爬出另一个陷阱。 :-)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM