使用beautifulsoup进行Python web抓取-无法从Clinicaltrials.gov中提取主要研究者
免责声明:我是一个Python和网络抓取noob,但我正在尽最大努力学习 我试图从clinicaltrials.gov上的研究中提取3个关键数据点。他们有一个API,但是API没有捕获我需要的东西。我想得到1个研究的简短描述,2个主要研究者PI,3个与研究相关的关键词。我相信我的代码捕获了1和3,但不是2。我似乎不明白为什么我得不到首席调查员的名字。以下是我代码中的两个站点: 这是我的代码我知道PI代码是错误的,但我想证明我尝试过:使用beautifulsoup进行Python web抓取-无法从Clinicaltrials.gov中提取主要研究者,python,web-scraping,beautifulsoup,html-parsing,export-to-csv,Python,Web Scraping,Beautifulsoup,Html Parsing,Export To Csv,免责声明:我是一个Python和网络抓取noob,但我正在尽最大努力学习 我试图从clinicaltrials.gov上的研究中提取3个关键数据点。他们有一个API,但是API没有捕获我需要的东西。我想得到1个研究的简短描述,2个主要研究者PI,3个与研究相关的关键词。我相信我的代码捕获了1和3,但不是2。我似乎不明白为什么我得不到首席调查员的名字。以下是我代码中的两个站点: 这是我的代码我知道PI代码是错误的,但我想证明我尝试过: import pandas as pd import re
import pandas as pd
import requests
from bs4 import BeautifulSoup
import csv
fields=['PI','Project_Summary', 'Keywords']
with open(r'test.csv', 'a') as f:
writer = csv.writer(f)
writer.writerow(fields)
urls = ['https://clinicaltrials.gov/ct2/show/NCT03436992','https://clinicaltrials.gov/ct2/show/NCT03530579']
for url in urls:
response = requests.get(url)
soup = BeautifulSoup(response.content, 'html.parser')
#get_keywords
for rows in soup.find_all("td"):
k = rows.get_text()
Keywords = k.strip()
#get Principal Investigator
PI = soup.find_all('padding:1ex 1em 0px 0px;white-space:nowrap;')
#Get description
Description = soup.find(class_='ct-body3 tr-indent2').get_text()
d = {'Summary2':[PI,Description,Keywords]}
df = pd.DataFrame(d)
print (df)
import csv
fields=[PI,Description, Keywords]
with open(r'test.csv', 'a') as f:
writer = csv.writer(f)
writer.writerow(fields)
您可以使用以下选择器 i、 e.PI=soup。选择“一个”。tr-table“封面[页眉=名称]”。文本
这个。是,而[]是选择器。之间的空格是一个,指定右侧检索的元素是左侧元素的子元素。您可以使用以下选择器 i、 e.PI=soup。选择“一个”。tr-table“封面[页眉=名称]”。文本
这个。是,而[]是选择器。中间的空格是一个指定右边检索的元素是左边元素的子元素的空格我只是用pandas来获取表。这将返回数据帧列表。然后,您可以通过迭代来查找PI:
tables = pd.read_html(url)
for table in tables:
try:
if 'Principal Investigator' in table.iloc[0,0]:
pi = table.iloc[0,1]
except:
continue
我只是用熊猫来弄桌子。这将返回数据帧列表。然后,您可以通过迭代来查找PI:
tables = pd.read_html(url)
for table in tables:
try:
if 'Principal Investigator' in table.iloc[0,0]:
pi = table.iloc[0,1]
except:
continue
因此,有很多方法可以遍历DOM树,而您的方法非常脆弱。这意味着您选择的用于开始搜索的选择器非常具体,并且绑定到CSS样式,CSS样式的更改要比整个文档的结构容易得多 但是如果我是你的话,我会根据一些标准过滤一些节点,然后在筛选噪音的时候专注于那个特定的组 因此,查看您显示的这些URL,数据的结构似乎很整齐,并且使用了表。基于此,我们可以做出如下假设 它是表中的数据 它将包含其中的principal Investors字符串 此时,我们在精炼的_表列表中有一个强大的候选表,它可能实际上包含我们的主表,并且理想情况下大小为1,假设我们使用的主要调查者过滤器不在其他表中的任何其他位置
principal_investigator = [ele for ele in refined_tables.findAll('td') if 'name' in ele.attrs['headers']][0].text
在这里,通过查看站点所做的是,他们使用属性头在表行中分配td标记的角色
因此,本质上,只需从顶层思考,并开始通过简单的步骤尽可能地缩小范围,以帮助您找到所需的内容。因此,有许多方法可以遍历DOM树,而您的方法非常脆弱。这意味着您选择的用于开始搜索的选择器非常具体,并且绑定到CSS样式,CSS样式的更改要比整个文档的结构容易得多 但是如果我是你的话,我会根据一些标准过滤一些节点,然后在筛选噪音的时候专注于那个特定的组 因此,查看您显示的这些URL,数据的结构似乎很整齐,并且使用了表。基于此,我们可以做出如下假设 它是表中的数据 它将包含其中的principal Investors字符串 此时,我们在精炼的_表列表中有一个强大的候选表,它可能实际上包含我们的主表,并且理想情况下大小为1,假设我们使用的主要调查者过滤器不在其他表中的任何其他位置
principal_investigator = [ele for ele in refined_tables.findAll('td') if 'name' in ele.attrs['headers']][0].text
在这里,通过查看站点所做的是,他们使用属性头在表行中分配td标记的角色
因此,本质上,只需从顶层思考,并开始通过简单的步骤尽可能缩小范围,以帮助您找到所需内容。我成功地获得了PI,但我也没有看到关键字被选中。你想得到的关键词是什么?我设法得到了PI,但我也没有看到关键词被选中。你想得到的关键词是什么?谢谢大家!我使用了QHarr的代码,在大多数情况下,这是有效的。但是,当我添加clinicaltrials.gov URL并且没有列出PI时,我会得到一个“非类型”对象没有属性“文本错误”。我怎么能避开这个?我会帮你编辑的。你能提供当前失败的url吗?这样我就可以添加到代码中了。谢谢!我真的很感激。谢谢大家!我使用了QHarr的代码,在大多数情况下,这是有效的。但是,当我添加clinicaltrials.gov URL并且没有列出PI时,我会得到一个“非类型”对象没有属性“文本错误”。我怎么能避开这个?我会帮你编辑的。你能提供当前失败的url吗?这样我就可以添加到代码中了。谢谢!我真的很感激。