如何遍历 pandas 数据帧中的嵌套 for 循环?
How to iterate through a nested for loop in pandas dataframe?
我正在尝试遍历 Hacker News 数据集,并试图创建在 HN 论坛上找到的 3 个类别(即帖子类型),即 ask_posts、show_posts 和 other_posts.
简而言之,我试图找出每个帖子每个类别的平均评论数(如下所述)。
import pandas as pd
import datetime as dt
df = pd.read_csv('HN_posts_year_to_Sep_26_2016.csv')
ask_posts = []
show_posts = []
other_post = []
total_ask_comments = 0
total_show_comments = 0
for i, row in df.iterrows():
title = row.title
comments = row['num_comments']
if title.lower().startswith('ask hn'):
ask_posts.append(title)
for post in ask_posts:
total_ask_comments += comments
elif title.lower().startswith('show hn'):
show_posts.append(title)
for post in show_posts:
total_show_comments += comments
else:
other_post.append(title)
avg_ask_comments = total_ask_comments/len(ask_posts)
avg_show_comments = total_show_comments/len(show_posts)
print(total_ask_comments)
print(total_show_comments)
print(avg_ask_comments)
print(avg_show_comments)
结果分别是;
395976587
250362315
和
43328.21829521829
24646.81187241583
这些看起来很高,我不确定是否是因为这是我构造嵌套循环的方式的问题。这种方法是否正确?我使用 for 循环来执行此操作至关重要。
感谢我的所有 help/verification 代码。
这个post没有具体回答关于遍历数据帧的问题;但它为您提供了一个更快的替代解决方案。
循环遍历 Pandas 数据帧以收集现有信息将会非常缓慢。使用过滤来获取您想要的信息要快得多。
>>> show_posts = df[df.title.str.contains("show hn", case=False)]
>>> show_posts
id ... created_at
52 12578335 ... 9/26/2016 0:36
58 12578182 ... 9/26/2016 0:01
64 12578098 ... 9/25/2016 23:44
70 12577991 ... 9/25/2016 23:17
140 12577142 ... 9/25/2016 20:06
... ... ... ...
292995 10177714 ... 9/6/2015 14:21
293002 10177631 ... 9/6/2015 13:50
293019 10177511 ... 9/6/2015 13:02
293028 10177459 ... 9/6/2015 12:38
293037 10177421 ... 9/6/2015 12:16
[10189 rows x 7 columns]
>>> ask_posts = df[df.title.str.contains("ask hn", case=False)]
>>> ask_posts
id ... created_at
10 12578908 ... 9/26/2016 2:53
42 12578522 ... 9/26/2016 1:17
76 12577908 ... 9/25/2016 22:57
80 12577870 ... 9/25/2016 22:48
102 12577647 ... 9/25/2016 21:50
... ... ... ...
293047 10177359 ... 9/6/2015 11:27
293052 10177317 ... 9/6/2015 10:52
293055 10177309 ... 9/6/2015 10:46
293073 10177200 ... 9/6/2015 9:36
293114 10176919 ... 9/6/2015 6:02
[9147 rows x 7 columns]
您可以通过这种方式快速获取号码
>>> num_ask_comments = ask_posts.num_comments.sum()
>>> num_ask_comments
95000
>>> num_show_comments = show_posts.num_comments.sum()
>>> num_show_comments
50026
>>>
>>> total_num_comments = df.num_comments.sum()
>>> total_num_comments
1912761
>>>
>>> # Get a ratio of the number ask comments to total number of comments
>>> num_ask_comments / total_num_comments
0.04966642460819726
>>>
此外,.startswith()
与 .contains()
会得到不同的数字(我不确定你想要哪个)。
>>> ask_posts = df[df.title.str.lower().str.startswith("ask hn")]
>>> len(ask_posts)
9139
>>>
>>> ask_posts = df[df.title.str.contains("ask hn", case=False)]
>>> len(ask_posts)
9147
>>>
.contains()
的模式参数可以是一个正则表达式——这非常有用。所以我们可以在标题的最开始指定所有以 "ask hn" 开头的记录,但是如果我们不确定它前面是否有空格,我们可以做
>>> ask_posts = df[df.title.str.contains(r"^\s*ask hn", case=False)]
>>> len(ask_posts)
9139
>>>
当您开始使用 Pandas 时,过滤器语句中发生的事情可能很难理解。例如df[df.title.str.contains("show hn", case=False)]
方括号中的表达式。
方括号 (df.title.str.contains("show hn", case=False)
) 内的语句产生的是一列 True 和 False 值 - 一个布尔过滤器(不确定它是否就是它的名字,但它具有这种效果)。
所以生成的布尔列用于 select 数据框中的行,df[<bool column>]
,它会生成一个包含匹配记录的新数据框。然后我们可以使用它来提取其他信息——比如评论列的总和。
我正在尝试遍历 Hacker News 数据集,并试图创建在 HN 论坛上找到的 3 个类别(即帖子类型),即 ask_posts、show_posts 和 other_posts.
简而言之,我试图找出每个帖子每个类别的平均评论数(如下所述)。
import pandas as pd
import datetime as dt
df = pd.read_csv('HN_posts_year_to_Sep_26_2016.csv')
ask_posts = []
show_posts = []
other_post = []
total_ask_comments = 0
total_show_comments = 0
for i, row in df.iterrows():
title = row.title
comments = row['num_comments']
if title.lower().startswith('ask hn'):
ask_posts.append(title)
for post in ask_posts:
total_ask_comments += comments
elif title.lower().startswith('show hn'):
show_posts.append(title)
for post in show_posts:
total_show_comments += comments
else:
other_post.append(title)
avg_ask_comments = total_ask_comments/len(ask_posts)
avg_show_comments = total_show_comments/len(show_posts)
print(total_ask_comments)
print(total_show_comments)
print(avg_ask_comments)
print(avg_show_comments)
结果分别是;
395976587
250362315
和
43328.21829521829
24646.81187241583
这些看起来很高,我不确定是否是因为这是我构造嵌套循环的方式的问题。这种方法是否正确?我使用 for 循环来执行此操作至关重要。
感谢我的所有 help/verification 代码。
这个post没有具体回答关于遍历数据帧的问题;但它为您提供了一个更快的替代解决方案。
循环遍历 Pandas 数据帧以收集现有信息将会非常缓慢。使用过滤来获取您想要的信息要快得多。
>>> show_posts = df[df.title.str.contains("show hn", case=False)]
>>> show_posts
id ... created_at
52 12578335 ... 9/26/2016 0:36
58 12578182 ... 9/26/2016 0:01
64 12578098 ... 9/25/2016 23:44
70 12577991 ... 9/25/2016 23:17
140 12577142 ... 9/25/2016 20:06
... ... ... ...
292995 10177714 ... 9/6/2015 14:21
293002 10177631 ... 9/6/2015 13:50
293019 10177511 ... 9/6/2015 13:02
293028 10177459 ... 9/6/2015 12:38
293037 10177421 ... 9/6/2015 12:16
[10189 rows x 7 columns]
>>> ask_posts = df[df.title.str.contains("ask hn", case=False)]
>>> ask_posts
id ... created_at
10 12578908 ... 9/26/2016 2:53
42 12578522 ... 9/26/2016 1:17
76 12577908 ... 9/25/2016 22:57
80 12577870 ... 9/25/2016 22:48
102 12577647 ... 9/25/2016 21:50
... ... ... ...
293047 10177359 ... 9/6/2015 11:27
293052 10177317 ... 9/6/2015 10:52
293055 10177309 ... 9/6/2015 10:46
293073 10177200 ... 9/6/2015 9:36
293114 10176919 ... 9/6/2015 6:02
[9147 rows x 7 columns]
您可以通过这种方式快速获取号码
>>> num_ask_comments = ask_posts.num_comments.sum()
>>> num_ask_comments
95000
>>> num_show_comments = show_posts.num_comments.sum()
>>> num_show_comments
50026
>>>
>>> total_num_comments = df.num_comments.sum()
>>> total_num_comments
1912761
>>>
>>> # Get a ratio of the number ask comments to total number of comments
>>> num_ask_comments / total_num_comments
0.04966642460819726
>>>
此外,.startswith()
与 .contains()
会得到不同的数字(我不确定你想要哪个)。
>>> ask_posts = df[df.title.str.lower().str.startswith("ask hn")]
>>> len(ask_posts)
9139
>>>
>>> ask_posts = df[df.title.str.contains("ask hn", case=False)]
>>> len(ask_posts)
9147
>>>
.contains()
的模式参数可以是一个正则表达式——这非常有用。所以我们可以在标题的最开始指定所有以 "ask hn" 开头的记录,但是如果我们不确定它前面是否有空格,我们可以做
>>> ask_posts = df[df.title.str.contains(r"^\s*ask hn", case=False)]
>>> len(ask_posts)
9139
>>>
当您开始使用 Pandas 时,过滤器语句中发生的事情可能很难理解。例如df[df.title.str.contains("show hn", case=False)]
方括号中的表达式。
方括号 (df.title.str.contains("show hn", case=False)
) 内的语句产生的是一列 True 和 False 值 - 一个布尔过滤器(不确定它是否就是它的名字,但它具有这种效果)。
所以生成的布尔列用于 select 数据框中的行,df[<bool column>]
,它会生成一个包含匹配记录的新数据框。然后我们可以使用它来提取其他信息——比如评论列的总和。