一、前言
最近在研究大数据,要获取大数据的很好的方式就是使用网络爬虫,去爬网页上的数据,然后进行分析。下面小编就通过一个demo来爬一下“赶集网”的数据,然后用图表显示各种信息之间的情况。
二、知识点弥补
这里小编主要用到了两个知识点:
2.1 Jsoup
百度百科的理解是:jsoup 是一款Java 的HTML解析器,可直接解析某个URL地址、HTML文本内容。它提供了一套非常省力的API,可通过DOM,CSS以及类似于jQuery的操作方法来取出和操作数据。
从里面我们可以了解到,jsoup是解析html的API。
2.2 FusionCharts
可以说画图的JS库还是很多的,小编以前用过Highchart、Echarts这两个。现在重新接触了FusionChart,具体的使用,小编会在以后的博客中向大家介绍。
FusionCharts是InfoSoft Global公司的一个产品,InfoSoft Global 公司是专业的Flash图形方案提供商,他们还有几款其他的,基于Flash技术的产品,都非常的漂亮。 FusionCharts free 是一个跨平台,跨浏览器的flash图表组件解决方案,能够被 ASP.NET, ASP, PHP, JSP, ColdFusion, Ruby on Rails, 简单 HTML页面甚至PPT调用。你不需要知道任何关于flash编程的知识,你只需要知道你所用的编程语言就可以了。
三、代码实现
3.1 环境要求
log4j-1.2.17.jar
struts2-json-plugin-2.3.15.3.jar
xwork-core-2.2.3.jar
3.2 项目搭建
本项目小编使用Eclipse开发,打开Eclipse,建立一个Java Project,项目名为AresBigData_V1.0,建立包com.dmsd.util,在包中建立操作类BigDataUtil.java,然后引入相关的jar。项目结构如下:
3.3 根据网址和编码集获取网页的源代码
在BigDataUtil.java中写如下的方法:
/**
* 根据网址和编码集获取网页的源代码-王雷-2017年9月10日09:36:56
* @param url
* @param encoding
* @return
*/
public static String getHtmlResourceByUrl(String url,String encoding) {
InputStreamReader isr =null;
URLConnection uc = null;
URL urlObj = null;
BufferedReader reader =null;
StringBuilder sb = new StringBuilder();
try {
//创建网络链接
urlObj = new URL(url);
//打开网络链接
uc = urlObj.openConnection();
//建立文件写入流
isr = new InputStreamReader(uc.getInputStream(),encoding);
//建立文件缓冲流
reader = new BufferedReader(isr);
// 建立临时变量
String temp=null;
while ((temp=reader.readLine())!=null) {
sb.append(temp+"\n"); //一边读一边写
}
} catch (Exception e) {
e.printStackTrace();
}finally{
if (isr!=null) {
try {
isr.close();
} catch (Exception e2) {
e2.printStackTrace();
}
}
}
return sb.toString();
}
3.4 使用jsoup解析源代码
在BigDataUtil.java中写如下的方法:
import org.jsoup.Jsoup;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
org.jsoup.nodes.Document
private static Document document;
private static Element element;
private static Elements elementsByTag;
private static List<HashMap<String, Object>> findMessage;
/**
* 使用jsoup解析原网页-王雷-2017年9月10日10:03:59
* @param html
* @return
*/
public static List<HashMap<String,Object>> findMessage(String html){
//定义加载数据列表的容器
List<HashMap<String, Object>> list = new ArrayList<HashMap<String,Object>>();
//使用Jsoup解析源代码
document = Jsoup.parse(html);
//获取class="category-area" div元素的内容
element = document.getElementsByClass("category-area").get(0);
//获取该区域所有的a标签
elementsByTag = element.getElementsByTag("a");
for (Element ele : elementsByTag) {
HashMap<String, Object> map = new HashMap<String, Object>();
//获取:求职简历
String[] text = ele.text().split("\\(");
String txt = text[0];
String num =text[1].replaceAll("\\)", "");
map.put("txt", txt);
map.put("num", num);
list.add(map);
}
return list;
}
这里需要注意的是:小编使用的是jsoup,在前文中也提到过,是使用类似JavaScript的DOM来获取节点的,所以这里我们使用的document等要引入的是jsoup的document。
3.5 Chart图表显示
在WebRoot下把下载好的fusioncharts和JQuery引入进来,建立一个jsp页面xmlIndex.jsp,在这个jsp页面中,小编使用Ajax调用另一个data.jsp中的java代码:
<%@ page language="java" contentType="text/html; charset=utf-8"
pageEncoding="utf-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<title>My First chart using FusionCharts Suite XT</title>
<script type="text/javascript" src="fusioncharts/js/fusioncharts.js"></script>
<script type="text/javascript"
src="fusioncharts/js/themes/fusioncharts.theme.fint.js"></script>
<script type="text/javascript" src="js/jquery-3.2.0.min.js"></script>
<script type="text/javascript">
/**
* 显示表格
*/
FusionCharts.ready(function () {
var html ="";
//获取输入框的url地址
var url =$("#url").val();
alert(url);
//调用后台方法-解析url网页中的信息
$.ajax({
type:"post",
url:"data.jsp",
data:{url:url},
success:function(data){
var datas = eval("("+data+")");
//把解析返回成功的信息存储为xml格式(拼xml文件)
for(var i=0;i<datas.length;i++){
html+="<set label='"+datas[i].txt+"'"+" "+"value='"+datas[i].num+"' />";
}
html="<chart caption='赶集网' subcaption='类别数量分布' xaxisname='类别' yaxisname='数量' numberprefix='' palettecolors='#008ee4' bgalpha='0' borderalpha='20' canvasborderalpha='0' theme='fint' useplotgradientcolor='0' plotborderalpha='10' placevaluesinside='1' rotatevalues='1' valuefontcolor='#ffffff' captionpadding='20' showaxislines='1' axislinealpha='25' divlinealpha='10'>"+html+"</chart>";
var myChart = new FusionCharts({
"type": "column2d",
"renderAt": "chartContainer",
"width": "500",
"height": "300",
"dataFormat": "xml",
"dataSource":html
});
myChart.render();
}
});
});
</script>
</head>
<body>
<input id="url" value="http://bj.ganji.com/site/s/_java/" />
<div id="chartContainer">FusionCharts XT will load here!</div>
</body>
</html>
data.jsp:
<%@ page import="org.apache.struts2.json.*" %>
<%@ page language="java" import="java.util.*,com.dmsd.util.*" contentType="text/html; charset=utf-8"
pageEncoding="utf-8"%>
<%
request.setCharacterEncoding("UTF-8");
String url = request.getParameter("url");
String html = BigDataUtil.getHtmlResourceByUrl(url, "utf-8");
List<HashMap<String,Object>> list = BigDataUtil.findMessage(html);
out.print(JSONUtil.serialize(list));
%>
这里需要注意的是:Ajax在调用的时候可能会遇到编码的问题,经常会出现中文乱码的情况,这里小编总结了几点:
a) jQuery AJAX 请求,后台收到为乱码
可以显式设置contentType的编码为utf-8, 后台一般都能正常解码例如:
jQuery(form).ajaxSubmit({
url: "doLogin?user=a",
type: "post",
dataType: "json",
contentType: "application/x-www-form-urlencoded; charset=utf-8",
success: showLoginResponse
});
b) jQuery AJAX 返回乱码
检查页面的charset和pageEncoding是不是指定的数据类型。
<%@ page language=”java” import=”java.util.,com.dmsd.util.” contentType=”text/html; charset=utf-8” pageEncoding=”utf-8”%>
检查页面中是否有设置数据类型:
request.setCharacterEncoding(“UTF-8”);
3.6 效果展示
小编在赶集网中输入java,查询与java相关的工作。下面的图就是小编查出来的,可以看出,与jva相关的工作还是比较多的。小编就抓“类别”这一列的东西。把这些东西显示出来。
显示结果:
3.7 考虑的问题
通过url访问是必须要联网的,如果网络断了,怎么办?
- 这个其实很简单,刚开始的时候我们是通过Ajax来调用后台的方法的,如果后台方法访问超时,就会报超时的错误,即500。
四、小结
这个的效果还是差强人意的,在一定的范围内小编是可以忍受的。
但是关于性能方面还是需要多多尝试,进行测试的,这个就是我们要多多实验的。对于jsoup的性能也是要考虑的。加油!