Python 基于列表筛选列表列
具有如下所示的大数据帧:Python 基于列表筛选列表列,python,pandas,Python,Pandas,具有如下所示的大数据帧: userid user_mentions 1 [2, 3, 4] 1 [3] 2 NaN 2 [1,3] 3 [1,4,5] 3 [4] user_indications columns是每个用户提到的用户标识的列表。例如,第一行表示: 用户1提到了用户2、3和4 我需要在userid列中的用户之间创建一个提及网络。也就是说,我想要userid列中的每个用户被user
userid user_mentions
1 [2, 3, 4]
1 [3]
2 NaN
2 [1,3]
3 [1,4,5]
3 [4]
user_indications columns是每个用户提到的用户标识的列表。例如,第一行表示:
用户1提到了用户2、3和4
我需要在userid列中的用户之间创建一个提及网络。也就是说,我想要userid列中的每个用户被userid列中的其他用户提及的次数。所以基本上,首先我需要这样的东西:
filtered = df[df['user_mentions'].isin(df['userid'].unique())]
但这对列表列不起作用
如果我解决了上面的问题,那么我就可以使用groupby['userid','user_indications']
编辑
最终输出应为:
Source Target Number
1 2 1
1 3 2
2 1 1
2 3 1
3 1 1
3 5 1
在您的编辑之后,我必须同意@jpp 对于未经编辑的原始问题,在收集每个用户的提及次数方面,您可以:
df['counts'] = df['userid'].apply(lambda x: df['user_mentions'].dropna().sum().count(x))
df[['userid','counts']].groupby('userid').first()
收益率:
counts
userid
1 2
2 1
3 3
在您的编辑之后,我必须同意@jpp 对于未经编辑的原始问题,在收集每个用户的提及次数方面,您可以:
df['counts'] = df['userid'].apply(lambda x: df['user_mentions'].dropna().sum().count(x))
df[['userid','counts']].groupby('userid').first()
收益率:
counts
userid
1 2
2 1
3 3
这不是一项非常适合熊猫/NumPy的任务。因此,我建议您使用创建一个计数字典,然后根据字典构造一个数据帧:
from collections import defaultdict
dd = defaultdict(lambda: defaultdict(int))
for row in df.itertuples(index=False):
vals = row.user_mentions
if vals == vals:
for val in vals:
dd[row.userid][val] += 1
df = pd.DataFrame([(k, w, dd[k][w]) for k, v in dd.items() for w in v],
columns=['source', 'target', 'number'])
print(df)
source target number
0 1 2 1
1 1 3 2
2 1 4 1
3 2 1 1
4 2 3 1
5 3 1 1
6 3 4 2
7 3 5 1
当然,你不应该把名单放在熊猫系列的第一位。这是一个嵌套的指针层,如果可能的话应该避免使用。这不是一个非常适合Pandas/NumPy的任务。因此,我建议您使用创建一个计数字典,然后根据字典构造一个数据帧:
from collections import defaultdict
dd = defaultdict(lambda: defaultdict(int))
for row in df.itertuples(index=False):
vals = row.user_mentions
if vals == vals:
for val in vals:
dd[row.userid][val] += 1
df = pd.DataFrame([(k, w, dd[k][w]) for k, v in dd.items() for w in v],
columns=['source', 'target', 'number'])
print(df)
source target number
0 1 2 1
1 1 3 2
2 1 4 1
3 2 1 1
4 2 3 1
5 3 1 1
6 3 4 2
7 3 5 1
当然,你不应该把名单放在熊猫系列的第一位。这是一个嵌套的指针层,如果可能的话应该避免使用。这里有一种方法
# Remove the `NaN` rows
df = df.dropna()
# Construct a new DataFrame
df2 = pd.DataFrame(df.user_mentions.tolist(),
index=df.userid.rename('source')
).stack().astype(int).to_frame('target')
# Groupby + size
df2.groupby(['source', 'target']).size().rename('counts').reset_index()
source target counts
0 1 2 1
1 1 3 2
2 1 4 1
3 2 1 1
4 2 3 1
5 3 1 1
6 3 4 2
7 3 5 1
这里有一条路
# Remove the `NaN` rows
df = df.dropna()
# Construct a new DataFrame
df2 = pd.DataFrame(df.user_mentions.tolist(),
index=df.userid.rename('source')
).stack().astype(int).to_frame('target')
# Groupby + size
df2.groupby(['source', 'target']).size().rename('counts').reset_index()
source target counts
0 1 2 1
1 1 3 2
2 1 4 1
3 2 1 1
4 2 3 1
5 3 1 1
6 3 4 2
7 3 5 1
您刚刚完全更改了输入数据帧…@rahlf23 user 1在第一行和第二行分别提到了user 3。因此,用户1已经两次提到用户3,对应于output@rahlf23对不起,这个问题很模糊。刚刚编辑您刚刚完全更改了输入数据帧…@rahlf23用户1在第一行和第二行分别提到了用户3。因此,用户1已经两次提到用户3,对应于output@rahlf23对不起,这个问题很模糊。刚刚编辑