转载请注明:http://mp.blog.csdn.net/postedit/79131443

首先编写HtmlUtils类,这个类将一些常用方法集成到一个类里面。

工具类

public class HtmlUtil {/** 启动JS*/public static WebClient iniParam_Js() {final WebClient webClient = new WebClient(BrowserVersion.CHROME);// 启动JSwebClient.getOptions().setJavaScriptEnabled(true);//将ajax解析设为可用webClient.getOptions().setActiveXNative(true);//设置Ajax的解析器webClient.setAjaxController(new NicelyResynchronizingAjaxController());// 禁止CSSwebClient.getOptions().setCssEnabled(false);// 启动客户端重定向webClient.getOptions().setRedirectEnabled(true);// JS遇到问题时,不抛出异常webClient.getOptions().setThrowExceptionOnScriptError(false);// 设置超时webClient.getOptions().setTimeout(10000);//禁止下载照片webClient.getOptions().setDownloadImages(false);return webClient;}/** 禁止JS*/public static WebClient iniParam_NoJs() {final WebClient webClient = new WebClient(BrowserVersion.CHROME);// 禁止JSwebClient.getOptions().setJavaScriptEnabled(false);// 禁止CSSwebClient.getOptions().setCssEnabled(false);// 将返回错误状态码错误设置为falsewebClient.getOptions().setThrowExceptionOnFailingStatusCode(false);// 启动客户端重定向webClient.getOptions().setRedirectEnabled(true);// 设置超时webClient.getOptions().setTimeout(5000);//禁止下载照片webClient.getOptions().setDownloadImages(false);return webClient;}/*** 根据url获取页面,这里需要加载JS* @param url* @return 网页* @throws FailingHttpStatusCodeException* @throws MalformedURLException* @throws IOException*/public static HtmlPage getPage_Js(String url) throws FailingHttpStatusCodeException, MalformedURLException, IOException{final WebClient webClient = iniParam_Js();HtmlPage page = webClient.getPage(url);//webClient.waitForBackgroundJavaScriptStartingBefore(5000);return page;}/*** 根据url获取页面,这里不加载JS* @param url* @return 网页* @throws FailingHttpStatusCodeException* @throws MalformedURLException* @throws IOException*/public static HtmlPage getPage_NoJs(String url) throws FailingHttpStatusCodeException, MalformedURLException, IOException{final WebClient webClient = iniParam_NoJs();HtmlPage page = webClient.getPage(url);return page;}
}

这样做的原因是使用HtmlUnit时经常需要设置JS,CSS等,这些代码都是大量重复的,为了减少代码量,我将这些方法写到一起。

根据姓名和机构获取匹配的学者的所有论文信息

public class GetArticles_CNC {public static void main(String[] args) throws FailingHttpStatusCodeException, MalformedURLException, IOException {// 禁止日志的输出LogManager.getLogManager().reset();long time1 = System.currentTimeMillis();System.out.println(getAllArticles("吴启夏", "华中理工大学"));    }/*** 以专家的姓名为关键词使用知网的学者搜索获取专家的所有论文的链接* * @param author 作者姓名* @param expertOrg 作者机构* @return 论文对应链接的list集合* @throws FailingHttpStatusCodeException* @throws MalformedURLException* @throws IOException*/public static List<String> getAllArticles(String author, String expertOrg)throws FailingHttpStatusCodeException, MalformedURLException, IOException {// 获取客户端,禁止JSWebClient webClient = HtmlUtil.iniParam_Js();// 获取搜索页面@SuppressWarnings("deprecation")String url = "http://kns.cnki.net/kcms/detail/knetsearch.aspx?sfield=au&skey=" + URLEncoder.encode(author);//获取搜索页面,搜索页面包含多个学者,机构通常是非完全匹配,姓名是完全匹配的,我们需要对所有的学者进行匹配操作HtmlPage page = webClient.getPage(url);//获取搜索页面的机构对应的节点DomElement orgDom = page.getFirstByXPath("/html/body/div[7]/div[1]/div/p[1]");if (orgDom == null)// 当机构节点为空时表示没有搜索到结果,直接返回空return null;//获取机构名称String firstOrg = orgDom.asText();// 判断学者机构和专家机构是否匹配if (firstOrg.equals(expertOrg))// 如果匹配则返回该学者的所有论文链接集合return getArticlesOnCurAuthor(page);else {// 否则需要获取其他同名作者的机构并判断是否匹配并判断DomElement dupNameAuthorsDom = page.getFirstByXPath("/html/body/div[7]/div[2]/ul");//包含其他学者的节点if (dupNameAuthorsDom == null)return null;//循序每一个学者的节点并判断是否匹配for (DomElement authorDom : dupNameAuthorsDom.getChildElements()) {String curOrg = authorDom.getFirstElementChild().getNextElementSibling().asText();if (curOrg.equals(expertOrg)) {String onclickAttr = authorDom.getFirstElementChild().getFirstElementChild().getAttribute("onclick");String id = onclickAttr.substring(onclickAttr.indexOf(",") + 2, onclickAttr.lastIndexOf("'"));String curUrl = url + "&code=" + id;HtmlPage curPage = webClient.getPage(curUrl);return getArticlesOnCurAuthor(curPage);}}}return null;}/*** 获取某个学者页面中的所有的论文,这里的论文包含期刊论文,会议论文和硕博论文* * @param page* @return* @throws IOException*/public static List<String> getArticlesOnCurAuthor(HtmlPage page) throws IOException {List<String> articlesList = new LinkedList<>();WebClient webClient = page.getWebClient();page.getElementById("lcatalog_1").click();// 发表在期刊上的文献page.getElementById("lcatalog_3").click();// 发表在会议上的文献page.getElementById("lcatalog_2").click();// 发表在博硕上的文献webClient.waitForBackgroundJavaScriptStartingBefore(5000);// 设置等待时间为5sHtmlPage jPage = (HtmlPage) webClient.getWebWindowByName("framecatalog_1").getEnclosedPage();HtmlPage cPage = (HtmlPage) webClient.getWebWindowByName("framecatalog_3").getEnclosedPage();HtmlPage sPage = (HtmlPage) webClient.getWebWindowByName("framecatalog_2").getEnclosedPage();articlesList.addAll(getPageArticles(jPage, 1));articlesList.addAll(getPageArticles(cPage, 2));articlesList.addAll(getPageArticles(sPage, 3));return articlesList;}/*** 根据页面类型获取所有分页论文* * @param page 当前页面* @param type 页面类型 1表示期刊论文页面,2表示会议论文页面,3表示硕博论文页面* @return 所有论文列表的字符串形式* @throws IOException*/public static List<String> getPageArticles(HtmlPage page, int type) throws IOException {List<String> articlesList = new LinkedList<>();// 获取不同类型页面分页数目String id = "";// 页面中论文总数节点的id属性值if (type == 1)id = "pc_CJFQ";else if (type == 2)id = "pc_CPFD";else if (type == 3)id = "pc_CMFD";DomElement aCountDom = page.getElementById(id);// 论文数量节点// 如果论文数量节点为空则直接返回空字符串if (aCountDom == null)return articlesList;HtmlPage tempPage = page;articlesList.addAll(getArticlesByNode(tempPage));// 将当前页面中的所有论文添加到while (true) {DomElement nextDom = null;// 获取下一个及节点try {nextDom = tempPage.getAnchorByText("下一页");} catch (ElementNotFoundException e) {// TODO: handle exception}if (nextDom == null)break;tempPage = nextDom.click();// 获取下一页页面page.getWebClient().waitForBackgroundJavaScriptStartingBefore(1000);// 设置等待时间为1SarticlesList.addAll(getArticlesByNode(tempPage));// 将当前页面中的所有论文添加到}return articlesList;}/*** 根据节点获取单个页面的所有论文信息* * @param page*            页面,这里的页面指包含论文的页面,期刊论文页面、会议论文页面和硕博论文页面* @return*/public static List<String> getArticlesByNode(HtmlPage page) {DomElement articlesNode = page.getFirstByXPath("/html/body/div[1]/div/div[2]/ul");List<String> articlesList = new LinkedList<>();for (DomElement li : articlesNode.getChildElements()) {HtmlAnchor anchor = (HtmlAnchor) li.getFirstElementChild().getNextElementSibling();String articleUrl = "http://kns.cnki.net" + anchor.getHrefAttribute();String articleTitle = anchor.asText();articlesList.add(articleTitle + ";" + articleUrl);}return articlesList;}/*** 以姓名和机构为关键词,使用知网的高级搜索获取专家的所有论文* * @param author 专家姓名* @param org 专家机构* @return 论文list* @throws IOException*/public static List<String> getArticlesByKeywords(String author, String org) throws IOException {HtmlPage researchPage = HtmlUtil.getPage_Js("http://kns.cnki.net/kns/brief/result.aspx?dbprefix=SCDB");// 获取知网的高级搜索页面HtmlTextInput authorInput = researchPage.getFirstByXPath("//*[@id=\"au_1_value1\"]");// 作者文本框authorInput.setText(author);// 将作者填入HtmlTextInput orgInput = researchPage.getFirstByXPath("//*[@id=\"au_1_value2\"]");// 机构文本框orgInput.setText(org);// 将机构填入HtmlButtonInput searchButton = researchPage.getFirstByXPath("//*[@id=\"btnSearch\"]");// 提交按钮searchButton.click();// 获取提交后的页面researchPage.getWebClient().waitForBackgroundJavaScriptStartingBefore(5000);// 等待5S// 获取文章的iFrame页面HtmlPage articlePage = (HtmlPage) researchPage.getWebClient().getWebWindowByName("iframeResult").getEnclosedPage();// 获取第一篇文章节点DomElement firstArticleDom = ((DomElement) articlePage.getFirstByXPath("//*[@id=\"ctl00\"]/table/tbody/tr[2]/td/table/tbody")).getFirstElementChild().getNextElementSibling();while (firstArticleDom != null) {HtmlPage authorPage = getMatchedUrl(firstArticleDom, org);if (authorPage != null)return getArticlesOnCurAuthor(authorPage);else {firstArticleDom = firstArticleDom.getNextElementSibling();}}return null;}/*** 根据机构名获取匹配的学者主页* * @param articleDom 文章节点* @param org 机构* @return 如果学者主页的机构名和专家机构名匹配则返回匹配的学者主页,否则返回null* @throws IOException*/public static HtmlPage getMatchedUrl(DomElement articleDom, String org) throws IOException {DomElement authorDom = articleDom.getFirstElementChild().getNextElementSibling().getNextElementSibling();for (DomElement curAuthorAnchor : authorDom.getChildElements()) {if (curAuthorAnchor.getChildElementCount() != 0) {HtmlPage curPage = curAuthorAnchor.click();DomElement orgDom = curPage.getFirstByXPath("/html/body/div[7]/div[1]/div/p[1]/a");if (orgDom.asText().contains(org))return curPage;}}return null;}
}

最后程序的运行结果为:

[支持网络建模和仿真的Modelica模型管理框架;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSFZ201304018&dbcode=CJFQ&dbname=CJFD2013&v=, 基于交付物的汽车产品研发项目管理研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=XXGY201307000&dbcode=CJFQ&dbname=CJFD2013&v=, 协同环境中基于轻量化的3D异构CAD模型干涉检查;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX201301013&dbcode=CJFQ&dbname=CJFD2013&v=, 基于Fuzzy-PID的UUV姿态控制器研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JCGC201112023&dbcode=CJFQ&dbname=CJFD2011&v=, 基于参数树状约束的零部件族结构模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX201117010&dbcode=CJFQ&dbname=CJFD2011&v=, 集成项目管理与工作流的层次化过程模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX201114011&dbcode=CJFQ&dbname=CJFD2011&v=, 并发试验环境下的设备排程研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=SJSJ201104084&dbcode=CJFQ&dbname=CJFD2011&v=, 工作流的动态变更处理方法;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF201102017&dbcode=CJFQ&dbname=CJFD2011&v=, 大规模定制环境下的参数驱动产品配置设计方法研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX201015015&dbcode=CJFQ&dbname=CJFD2010&v=, 产品全生命周期数据信息的域建模方法;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF201002025&dbcode=CJFQ&dbname=CJFD2010&v=, 工作流的动态变更处理方法;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF201102017&dbcode=CJFQ&dbname=CJFD2011&v=, 大规模定制环境下的参数驱动产品配置设计方法研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX201015015&dbcode=CJFQ&dbname=CJFD2010&v=, 产品全生命周期数据信息的域建模方法;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF201002025&dbcode=CJFQ&dbname=CJFD2010&v=, 基于智能化配置的产品方案设计方法;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200919001&dbcode=CJFQ&dbname=CJFD2009&v=, 基于产品模型的多级产品配置研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=WJSJ200803008&dbcode=CJFQ&dbname=CJFD2008&v=, 面向飞机制造企业的计划管理系统的设计;http://kns.cnki.net/kcms/detail/detail.aspx?filename=WJSJ200736006&dbcode=CJFQ&dbname=CJFD2007&v=, 基于智能客户端的PLM系统体系框架;http://kns.cnki.net/kcms/detail/detail.aspx?filename=WJSJ200736013&dbcode=CJFQ&dbname=CJFD2007&v=, 可视化产品配置技术的研究与实现;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JCYY200705005&dbcode=CJFQ&dbname=cjfd2007&v=, 变量-知识体表达的产品开发过程模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200705014&dbcode=CJFQ&dbname=cjfd2007&v=, 基于五维状态空间的产品建模方法研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200704007&dbcode=CJFQ&dbname=cjfd2007&v=, 面向产品开发的项目管理在产品数据管理中的研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJJ200701019&dbcode=CJFQ&dbname=cjfd2007&v=, 网络化协同产品开发机理与模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200701009&dbcode=CJFQ&dbname=cjfd2007&v=, PLM系统中工作流访问控制模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX2006S2051&dbcode=CJFQ&dbname=cjfd2006&v=, 基于事物特性表的参数化产品配置;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF200610017&dbcode=CJFQ&dbname=cjfd2006&v=, 支持协同的3维轻量化模型与圈阅工具的研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJJ200609006&dbcode=CJFQ&dbname=cjfd2006&v=, 基于智能代理的主动式协同服务框架研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JXKX200607030&dbcode=CJFQ&dbname=cjfd2006&v=, 模具数字化制造;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZZXD200605015&dbcode=CJFQ&dbname=cjfd2006&v=, 基于规则和约束的多层递阶产品开发过程管理;http://kns.cnki.net/kcms/detail/detail.aspx?filename=HZLG200510013&dbcode=CJFQ&dbname=CJFD2005&v=, 工作流系统中业务工具动态集成模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJJ200510002&dbcode=CJFQ&dbname=CJFD2005&v=, 产品生命周期管理的访问控制模型研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF200509035&dbcode=CJFQ&dbname=CJFD2005&v=, 产品全生命周期管理在某企业的规划与实施;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSFZ200201005&dbcode=CJFQ&dbname=cjfd2002&v=, 基于PDM的版本管理研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=HZLG200112010&dbcode=CJFQ&dbname=cjfd2001&v=, 企业产品数据管理的实施与应用开发;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJJ200109003&dbcode=CJFQ&dbname=cjfd2001&v=, CIMS环境下产品信息编码原理的研究与应用;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200105019&dbcode=CJFQ&dbname=cjfd2001&v=, 基于PDM的工艺管理研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200401010&dbcode=CJFQ&dbname=CJFD2004&v=, PDM中多资源约束下的项目管理技术;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSGG200410068&dbcode=CJFQ&dbname=CJFD2004&v=, 基于产品结构的工程变更研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=ZGJX200412006&dbcode=CJFQ&dbname=CJFD2004&v=, 产品数据管理中的工程变更管理的建模与实现;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSFZ200402002&dbcode=CJFQ&dbname=CJFD2004&v=, 集成化工艺信息管理系统InteCAPP的研究与开发;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJF200411027&dbcode=CJFQ&dbname=CJFD2004&v=, 基于条件约束满足问题的产品配置研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=JSJJ200411003&dbcode=CJFQ&dbname=CJFD2004&v=, 支持网络建模和仿真的Modelica模型管理框架;http://kns.cnki.net/kcms/detail/detail.aspx?filename=AGLU201307005018&dbcode=CPFD&dbname=CPFD2013&v=, 煤粉O2/CO2气氛下反应动力学及NOx生成与排放的中试研究;http://kns.cnki.net/kcms/detail/detail.aspx?filename=2009145055.nh&dbcode=CMFD&dbname=CMFD2010&v=]

使用HtmlUnit爬取知网论文相关推荐

  1. python爬取会议论文pdf_【python2.7】爬取知网论文

    # -*- coding: utf-8 -*- import time import urllib import urllib2 import cookielib from lxml import e ...

  2. [python爬虫] BeautifulSoup和Selenium简单爬取知网信息测试

    作者最近在研究复杂网络和知识图谱内容,准备爬取知网论文相关信息进行分析,包括标题.摘要.出版社.年份.下载数和被引用数.作者信息等.但是在爬取知网论文时,遇到问题如下:   1.爬取内容总为空,其原因 ...

  3. Python3爬取知网文章

    分析 首先,我们看一下入口的网站,在输入关键词搜索之前和之后它的网址并没有什么变化,所以我们不能通过直接请求它来得到文章. 搜索前 搜索后 所以,我们应该换一种思路.打开开发者工具后,我们可以看到如下 ...

  4. java+selenium爬取知网数据

    使用selenium工具爬取知网相关数据,思路:根据几个关键词搜索出相关的内容,然后爬取列表中所有论文的访问链接. 注意:直接爬取的链接是不能用的,需要自己拼接一下.具体看代码.新手,代码写的有点乱. ...

  5. 爬虫练习(一)爬取知网、万方、维普文献标题、作者、刊物来源等信息

    刚刚开始学习Python,今天一周整,浏览了站内一些大侠博客相关内容,自己也尝试着写了一个爬虫. 直接借鉴了几位大侠的经验,如有冒犯之处恳请海涵. 先说说目的吧,本爬虫的目的是根据EXCEL文件的作者 ...

  6. 爬取知网博硕士文献及中国专利存到mysql数据库中的代码及其注意事项

    今天因为需要做了一个爬取知网博硕士论文及中国专利的爬虫,在制作的过程中遇到了不少坑,在网上查资料时都是很老的资源,在现在知网的反爬虫下不起作用,所以我来写这篇文章来供大家参考.(这篇文章主要介绍通过改 ...

  7. 使用Scrapy、PhantomJS和Selenium爬取知网文献摘要

    使用Scrapy.PhantomJS和Selenium爬取知网文献摘要.以下例子用于爬取"医药卫生科技"类文献摘要. 1.使用Scrapy创建项目 scrapy startproj ...

  8. python爬虫爬取知网

    python爬虫爬取知网 话不多说,直接上代码! import requests import re import time import xlrd from xlrd import open_wor ...

  9. python抓取文献关键信息,python爬虫——使用selenium爬取知网文献相关信息

    python爬虫--使用selenium爬取知网文献相关信息 写在前面: 本文章限于交流讨论,请不要使用文章的代码去攻击别人的服务器 如侵权联系作者删除 文中的错误已经修改过来了,谢谢各位爬友指出错误 ...

最新文章

  1. WR:中国46个饮用水供水系统评估水源水对龙头水细菌群落的“烙印”
  2. 例题;假设一张纸厚度为0.001米,对折多少次高度可以超过珠峰高度(8848)米。一个篮球第二次弹起的高度是第一次弹起高度的2/3,问弹起n次以后的高度是多少。 主要学习for循环...
  3. java uuid会重复吗_记一次订单号重复的事故,快看看你的 uuid 在并发下还正确吗?...
  4. python语言有什么用-python语言的优势是什么
  5. php中this的含义
  6. Android ListView 圆角
  7. [渝粤教育] 西南科技大学 理论力学 在线考试复习资料
  8. 2022年科技与IT十大趋势
  9. 作为评审人完成了对其他小组第一阶段成果的评价
  10. 你就要清楚的知道,自己日后的“盈利模式”是什么?
  11. 60 岁的 COBOL 凭什么活到现在?
  12. angular—— Dynamic Templates
  13. 【php更换数据库为orcle】phpstudy+orcle
  14. Overload和Override详解
  15. Mac搭建Linux虚拟机
  16. Kinect for Windows SDK开发入门(五):景深数据处理 下
  17. CentOS 7 安装 Weadmin(ITOSS)
  18. android版本8.1.0和9的区别,安卓8.1和9.0的区别是什么
  19. 尚硅谷周阳学习微服务《二》
  20. 920C. Swap Adjacent Elements

热门文章

  1. 利用TF_IDF算法计算两英文文章的文本相似度 C++实现
  2. Closed Caption 和 Subtitle 的区别
  3. 论文阅读笔记-场景图谱-图谱生成:Scene Graph Generation from Objects, Phrases and Region Captions
  4. PHP 操作图片水印
  5. Excel如何将符合要求的所有数据全部查找出来
  6. Qt解析XML相关(QDom方式)
  7. 拆长虹iho3000_(CA版)四川长虹iho-3000t晶晨s905l-b刷全网通系统教程可救砖头
  8. 监控告警 Metrics - Prometheus
  9. 苹果消息是先推送到服务器,iPhone消息推送机制实现与探讨
  10. 2021年华为总监知乎1867赞的Java面试题全集解析助我修行,不吃透感觉都对不起他(上)