如何使用 Python 循环抓取不同的页面
How to loop to scrape different pages with Python
因此,我的 objective 使用此代码提取有关我的 NFL 球队中一名新秀的信息。我想将他的表现与上赛季在他的位置上排名前 10 的球员进行比较,他们在第一个赛季打了 10 多场比赛。
为此,我参考了 Towards Data Science 中的 post,他们解释了如何抓取 NFL 数据。
这是我的代码:
#url page
url_mac = 'https://www.pro-football-reference.com/years/2021/passing.htm'
#opening URL with BS
html_mac = urlopen(url_mac)
stats_macpage = BeautifulSoup(html_mac)
#collecting table rows
column_headers = stats_macpage.findAll('tr')[0]
column_headers = [i.getText() for i in column_headers.findAll('th')]
#getting stats of each row
rows = stats_macpage.findAll('tr')[1:]
qb_stats = []
for i in range(len(rows)):
qb_stats.append([col.getText() for col in rows[i].findAll('td')])
#creating a data frame
data = pd.DataFrame(qb_stats, columns = column_headers[1:])
#rename column of sack yards from yards to y_sack
new_columns = data.columns.values
new_columns[-6] = 'y_sack'
data.columns = new_columns
#selecting specifics stats
categories = ['Cmp%', 'Yds', 'TD', 'Int', 'Y/A', 'Rate']
#first filter
data_radar = data[['Player', 'Tm'] + categories]
#selecting specific player
data_mac = data_radar[data_radar['Player'] == 'Mac Jones']
我为我想要数据的所有 11 名球员都做了这件事,并且在决赛中连接了起来,但你可以想象我的代码看起来有多糟糕。
如何改进它以创建循环?我已经尝试了一些东西,但是对于所有这些想法,它们要么效果不佳,要么超出了我成功执行的能力。
我的想法是获取过去 20 年的所有数据并尝试逐年查找,但这看起来有点不必要,因为我已经知道我想要什么年份。我的问题特别在这部分,因为在决赛中我可以创建一个列表,然后是一个“如果”,并且只取我列表中每个球员的第一年打了 > 10 场比赛。
url_mac = 'https://www.pro-football-reference.com/years/2021/passing.htm'
谢谢大家
要将 2011-2021 年的所有表加载到一个数据框中,您可以使用此示例:
import pandas as pd
# url page
url_mac = "https://www.pro-football-reference.com/years/{}/passing.htm"
all_dfs = []
for year in range(2011, 2022):
print("Getting table for year {}".format(year))
df = pd.read_html(url_mac.format(year))[0]
df = df[~df["Rk"].eq("Rk")]
df["Year"] = year
all_dfs.append(df)
df = pd.concat(all_dfs)
print(df)
df.to_csv("data.csv", index=False)
打印:
Rk Player Tm Age Pos G GS QBrec Cmp Att Cmp% Yds TD TD% Int Int% 1D Lng Y/A AY/A Y/C Y/G Rate QBR Sk Yds.1 NY/A ANY/A Sk% 4QC GWD Year
0 1 Drew Brees* NOR 32 QB 16 16 13-3-0 468 657 71.2 5476 46 7.0 14 2.1 279 79 8.3 8.8 11.7 342.3 110.6 82.3 24 158 7.81 8.23 3.5 3 4 2011
1 2 Tom Brady* NWE 34 QB 16 16 13-3-0 401 611 65.6 5235 39 6.4 12 2.0 262 99 8.6 9.0 13.1 327.2 105.6 73.8 32 173 7.87 8.25 5.0 1 2 2011
2 3 Matthew Stafford DET 23 QB 16 16 10-6-0 421 663 63.5 5038 41 6.2 16 2.4 243 73 7.6 7.7 12.0 314.9 97.2 60.5 36 257 6.84 6.98 5.2 3 4 2011
3 4 Eli Manning* NYG 30 QB 16 16 9-7-0 359 589 61.0 4933 29 4.9 16 2.7 218 99 8.4 8.1 13.7 308.3 92.9 64.2 28 199 7.67 7.45 4.5 5 6 2011
...
并保存 data.csv
(来自 LibreOffice 的屏幕截图):
使用 pandas
来解析这些表。只需遍历 url 中的季节(不要忘记在数据框中添加它,否则你会赢;不知道哪些行代表什么季节:
import pandas as pd
# To get last 10 seasons
years_look_back = 10
years_list = list(range(2021,2021-(years_look_back+1),-1))
years_list.reverse()
# Or just make a list of specific years:
years_list = [2001, 2005, 2008, 2010, 2011, 2015]
cols = ['Player', 'Tm','Cmp%', 'Yds', 'TD', 'Int', 'Y/A', 'Rate']
df_list = []
for year in years_list:
url_mac = f'https://www.pro-football-reference.com/years/{year}/passing.htm'
temp_df = pd.read_html(url_mac)[0][cols]
temp_df['Season'] = year
temp_df = temp_df[~temp_df["Player"].eq("Player")]
df_list.append(temp_df)
print(f'Collect: {year}')
data_radar = pd.concat(df_list)
#selecting specific player
data_mac = data_radar[data_radar['Player'] == 'Mac Jones']
因此,我的 objective 使用此代码提取有关我的 NFL 球队中一名新秀的信息。我想将他的表现与上赛季在他的位置上排名前 10 的球员进行比较,他们在第一个赛季打了 10 多场比赛。
为此,我参考了 Towards Data Science 中的 post,他们解释了如何抓取 NFL 数据。
这是我的代码:
#url page
url_mac = 'https://www.pro-football-reference.com/years/2021/passing.htm'
#opening URL with BS
html_mac = urlopen(url_mac)
stats_macpage = BeautifulSoup(html_mac)
#collecting table rows
column_headers = stats_macpage.findAll('tr')[0]
column_headers = [i.getText() for i in column_headers.findAll('th')]
#getting stats of each row
rows = stats_macpage.findAll('tr')[1:]
qb_stats = []
for i in range(len(rows)):
qb_stats.append([col.getText() for col in rows[i].findAll('td')])
#creating a data frame
data = pd.DataFrame(qb_stats, columns = column_headers[1:])
#rename column of sack yards from yards to y_sack
new_columns = data.columns.values
new_columns[-6] = 'y_sack'
data.columns = new_columns
#selecting specifics stats
categories = ['Cmp%', 'Yds', 'TD', 'Int', 'Y/A', 'Rate']
#first filter
data_radar = data[['Player', 'Tm'] + categories]
#selecting specific player
data_mac = data_radar[data_radar['Player'] == 'Mac Jones']
我为我想要数据的所有 11 名球员都做了这件事,并且在决赛中连接了起来,但你可以想象我的代码看起来有多糟糕。
如何改进它以创建循环?我已经尝试了一些东西,但是对于所有这些想法,它们要么效果不佳,要么超出了我成功执行的能力。
我的想法是获取过去 20 年的所有数据并尝试逐年查找,但这看起来有点不必要,因为我已经知道我想要什么年份。我的问题特别在这部分,因为在决赛中我可以创建一个列表,然后是一个“如果”,并且只取我列表中每个球员的第一年打了 > 10 场比赛。
url_mac = 'https://www.pro-football-reference.com/years/2021/passing.htm'
谢谢大家
要将 2011-2021 年的所有表加载到一个数据框中,您可以使用此示例:
import pandas as pd
# url page
url_mac = "https://www.pro-football-reference.com/years/{}/passing.htm"
all_dfs = []
for year in range(2011, 2022):
print("Getting table for year {}".format(year))
df = pd.read_html(url_mac.format(year))[0]
df = df[~df["Rk"].eq("Rk")]
df["Year"] = year
all_dfs.append(df)
df = pd.concat(all_dfs)
print(df)
df.to_csv("data.csv", index=False)
打印:
Rk Player Tm Age Pos G GS QBrec Cmp Att Cmp% Yds TD TD% Int Int% 1D Lng Y/A AY/A Y/C Y/G Rate QBR Sk Yds.1 NY/A ANY/A Sk% 4QC GWD Year
0 1 Drew Brees* NOR 32 QB 16 16 13-3-0 468 657 71.2 5476 46 7.0 14 2.1 279 79 8.3 8.8 11.7 342.3 110.6 82.3 24 158 7.81 8.23 3.5 3 4 2011
1 2 Tom Brady* NWE 34 QB 16 16 13-3-0 401 611 65.6 5235 39 6.4 12 2.0 262 99 8.6 9.0 13.1 327.2 105.6 73.8 32 173 7.87 8.25 5.0 1 2 2011
2 3 Matthew Stafford DET 23 QB 16 16 10-6-0 421 663 63.5 5038 41 6.2 16 2.4 243 73 7.6 7.7 12.0 314.9 97.2 60.5 36 257 6.84 6.98 5.2 3 4 2011
3 4 Eli Manning* NYG 30 QB 16 16 9-7-0 359 589 61.0 4933 29 4.9 16 2.7 218 99 8.4 8.1 13.7 308.3 92.9 64.2 28 199 7.67 7.45 4.5 5 6 2011
...
并保存 data.csv
(来自 LibreOffice 的屏幕截图):
使用 pandas
来解析这些表。只需遍历 url 中的季节(不要忘记在数据框中添加它,否则你会赢;不知道哪些行代表什么季节:
import pandas as pd
# To get last 10 seasons
years_look_back = 10
years_list = list(range(2021,2021-(years_look_back+1),-1))
years_list.reverse()
# Or just make a list of specific years:
years_list = [2001, 2005, 2008, 2010, 2011, 2015]
cols = ['Player', 'Tm','Cmp%', 'Yds', 'TD', 'Int', 'Y/A', 'Rate']
df_list = []
for year in years_list:
url_mac = f'https://www.pro-football-reference.com/years/{year}/passing.htm'
temp_df = pd.read_html(url_mac)[0][cols]
temp_df['Season'] = year
temp_df = temp_df[~temp_df["Player"].eq("Player")]
df_list.append(temp_df)
print(f'Collect: {year}')
data_radar = pd.concat(df_list)
#selecting specific player
data_mac = data_radar[data_radar['Player'] == 'Mac Jones']