Pandas对象类型列数值替换:DataFrame中cited_ids与d列修改需求
Pandas DataFrame 处理需求与实现结果
原始DataFrame
id cited_ids dummy_paper d 2 [4] NaN NaN 4 [9,18,6] NaN NaN 6 [] 9 0 7 [2] NaN NaN 9 [4] 7 0 14 [18,6] 3 0 18 [7] 1 0
需完成的两项操作
- (i) 将
df['cited_ids']列表中,对应id的d值为0的元素替换为0; - (ii) 若
df['cited_ids']的列表中存在至少一个0,且该行原始d值不为0,则将该行d值设为1。
第一步操作后结果
id cited_ids dummy_paper d 2 [4] NaN NaN 4 [0,0,6] NaN NaN 6 [] 9 0 7 [2] NaN NaN 9 [4] 7 0 14 [0,6] 3 0 18 [0] 1 0
第二步操作后结果
id cited_ids dummy_paper d 2 [4] NaN NaN 4 [0,0,6] NaN 1 6 [] 9 0 7 [2] NaN NaN 9 [4] 7 0 14 [0,6] 3 0 18 [0] 1 0
补充信息
df['cited_ids']为object类型;df.to_dict()输出如下:
{ 'docdb': {0: 2, 1: 4, 2: 6, 3: 7, 4: 9, 5: 14, 6: 18}, 'cited_docdb': {0: [4], 1: [9, 18, 6], 2: [], 3: [2], 4: [4], 5: [18, 6], 6: [7]}, 'fronteer': {0: nan, 1: nan, 2: 9.0, 3: nan, 4: 7.0, 5: 3.0, 6: 1.0}, 'distance': {0: nan, 1: nan, 2: 0.0, 3: nan, 4: 0.0, 5: 0.0, 6: 0.0} }
实现代码
步骤1:替换cited_ids中的目标元素
先建立id到d值的映射,再遍历每个列表替换符合条件的元素:
# 创建id与对应d值的映射字典 id_to_d = df.set_index('id')['d'].to_dict() # 替换cited_ids中对应d值为0的id df['cited_ids'] = df['cited_ids'].apply( lambda lst: [0 if id_to_d.get(x, None) == 0 else x for x in lst] )
步骤2:更新d值
先保存原始d值,再根据条件筛选并更新:
# 保存原始d值用于判断 original_d = df['d'].copy() # 构建筛选条件:cited_ids包含0,且原始d值不为0(包括NaN) mask = df['cited_ids'].apply(lambda lst: 0 in lst) & (original_d.isna() | (original_d != 0)) # 对符合条件的行设置d值为1 df.loc[mask, 'd'] = 1
完整可运行代码
import pandas as pd import numpy as np # 构建原始DataFrame data = { 'id': [2,4,6,7,9,14,18], 'cited_ids': [[4],[9,18,6],[],[2],[4],[18,6],[7]], 'dummy_paper': [np.nan, np.nan, 9, np.nan,7,3,1], 'd': [np.nan, np.nan,0,np.nan,0,0,0] } df = pd.DataFrame(data) # 执行步骤1 id_to_d = df.set_index('id')['d'].to_dict() df['cited_ids'] = df['cited_ids'].apply( lambda lst: [0 if id_to_d.get(x, None) == 0 else x for x in lst] ) # 执行步骤2 original_d = df['d'].copy() mask = df['cited_ids'].apply(lambda lst: 0 in lst) & (original_d.isna() | (original_d != 0)) df.loc[mask, 'd'] = 1 print(df)
内容的提问来源于stack exchange,提问作者Lusian
相关产品推荐
相关产品推荐

