爬!扒@切#存$构%查

  1. 云栖社区>
  2. 博客>
  3. 正文

爬!扒@切#存$构%查

厉力文武 2018-08-03 15:33:15 浏览1349
展开阅读全文

    喜欢java主要是喜欢它的简单,一次调用的背后是许多开发者默默的付出,讨厌java主要是讨厌它的简单,一次调用的背后完全不知道系统私下里都干了些啥。计算机技术经历几十年发展,底层的东西日趋完善,后来人在前辈的基础上快速构建,把产品推向市场,反馈迭代再反馈再迭代,变现盈利才是王道。当下有些强业务型互联网企业重融资重逼格,满嘴设计模式数据结构算法大全,闭口不谈运营模式产品形态用户体验~!@#$%^&*()......

    爬是爬虫,网页爬取,爬网页是技术活有难度有挑战,有些站点不喜欢被爬,爬烦了容易被拉黑,有些页面不是静态的,来来回回多步交互才能完成爬取,有些站点需要验证登录,各种形式验证码考验人脑眼手配合更别提机器识别了。

​​    <dependency>
      <groupId>org.apache.httpcomponents</groupId>
      <artifactId>fluent-hc</artifactId>
      <version>4.5.3</version>
    </dependency>

	String html = Executor.newInstance()
		.execute(Request.Get("http://www.url.com")					// 目标地址
		.userAgent("Mozilla/5.0 Chrome/85.0.252.101 Safari/536.86")		// 浏览器UA
		.viaProxy("127.0.0.1:2017")									// 代理服务
		.connectTimeout(5000)										// 连接超时
		.socketTimeout(10000))										// 套接字超时
		.returnContent()											// 返回CT对象
		.asString(Charset.forName("UTF-8"));							// 设置字符集
wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==

    扒是扒取HTML网页标签提取有价值内容,虽然每个站点都遵循html规范,但标签的定义差别还是非常大的,如果是有针对性的爬取某几家站点,可以通过配置的方式定义标签从而在元素集合中快速定位到信息。

getElementById(String id)			// <h1 id="title" cid="560" docid="8168976">标题</h1>
getElementsByTag(String tag) 		// <a target="_blank" href="new.htm" title="财经"></a>
getElementsByClass(String class)		// <div class="post"><a href="http://aaa.com"</a></div>
getElementsByAttribute(String key) 	// <img src="captchay?w=240&h=50" w="240" h="50"/>
getElementsByAttributeValue(String key, String value)	// <span class="txt"><a target="_blank" ...

    <dependency>
      <groupId>org.jsoup</groupId>
      <artifactId>jsoup</artifactId>
      <version>1.10.2</version>
    </dependency>

	Document doc = Jsoup.parse(htm);
	Elements div = doc.getElementsByAttributeValue("class", "txt");
	for(Element d : div) {
		for(Element l : d.getElementsByTag("a")) {
			System.out.print(l.attr("href") + " : ");
			System.out.print(l.attr("title") + " : ");
			System.out.println(l.text());
		}
	}
wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==

     切是切分对中文文章或语句进行分词,每个单词由偏移、词性和词三部分构成一个item对象,所有对象构成一个集合通过迭代器可以遍历,用户可以添加自己的字典,也可以指定切分过滤策略,扩展性很不错,调用仅一行代码,返回一个容器。

	<dependency>
		<groupId>org.ansj</groupId>
		<artifactId>ansj_seg</artifactId>
		<version>5.0.0</version>
	</dependency>

	// 未指定策略切分
	Result rst = ToAnalysis.parse(article);
	// 初始化用户字典
	UserDefineLibrary.insertWord("网络", "n",  1000);
	// 指定词性过滤分词
	FilterRecognition flt = new FilterRecognition();
	flt.insertStopNatures("w");
	Result rst = ToAnalysis.parse(article).recognition(flt);
wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==

     存是指将数据保存起来,mongodb作为类结构化存储解决方案高效稳定分布式相当好用,对数据类型和长度没有传统关系型数据库定义时那么费劲上心,很容易就能满足入门级建库建表的要求,一般复杂性的操作都能满足,用过绝对爱不释手。

    <dependency>
      <groupId>org.mongodb</groupId>
      <artifactId>mongo-java-driver</artifactId>
      <version>3.0.2</version>
    </dependency>

	GtMongo tm = new GtMongo();
	Gt.TuMongoOpen("127.0.0.1",12345);
	Gt.TuMongoGetDatabase("my_mongodb");
	Gt.TuMongoGetCollection("my_collecttion");
	Gt.TuMongoInsert(
		new Document("title, "一带一路高峰时刻")
			.append("url", "http://www.yidaiyilu.com")
			.append("text", "一带一路”国际合作高峰论坛举行")
			......
			.append("keys","一带一路")
	);
wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==

    构是构建索引,依托elk(Elasticsearch、Logstash和Kibana)日志分析系统,特点是分布式,零配置,自动发现,索引自动分片,索引副本机制,restful风格接口,多数据源,自动搜索负载,开源的伸缩性好,玩的好不好全看自己水平高低了。

​
    <dependency>
      <groupId>org.elasticsearch.client</groupId>
      <artifactId>transport</artifactId>
      <version>5.1.1</version>
    </dependency>

	try {
		String now = new SimpleDateFormat("yyyy-MM-dd").format(new Date()) + "T" + new SimpleDateFormat("HH:mm:ss.SS+0800").format(new Date());
		TransportClient tc = new PreBuiltTransportClient(Settings.EMPTY).addTransportAddress(new InetSocketTransportAddress(new InetSocketAddress(TE_HOST, TE_PORT)));
		String jsn[] = {
			"{\"@time\":\"" + now + "\",\"data\":{\"area\":\"area1\",\"msg\":\"msg1\",\"uid\":\"111\",\"keys\":\"key1\"}}",
			"{\"@time\":\"" + now + "\",\"data\":{\"area\":\"area2\",\"msg\":\"msg2\",\"uid\":\"222\",\"keys\":\"key2\"}}",
			"{\"@time\":\"" + now + "\",\"data\":{\"area\":\"area3\",\"msg\":\"msg3\",\"uid\":\"333\",\"keys\":\"key3\"}}"
			};
		for (int i = 0; i < jsn.length; i ++) {
			IndexResponse ir = tc.prepareIndex(TE_NAME, TE_TYPE).setSource(jsn[i]).get();
				System.out.println(ir.getId() + ", " + ir.getType() + ", " + ir.getIndex());
			}
		
		tc.close();
	} catch (Exception e) {
		e.printStackTrace();
	}
wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==

    查是查询,上面说了,自动发现自动创建,逻辑处理不复杂的话上手十分简单,但对中文的处理和复杂逻辑搜索还是需要花点功夫研究下的。

try {
		Settings st = Settings.builder().put("cluster.name", "elasticsearch").put("node.name", "kafka").build();
		TransportClient tc = new PreBuiltTransportClient(st).addTransportAddress(new InetSocketTransportAddress(new InetSocketAddress(TE_HOST, TE_PORT)));

//		SearchResponse sr = tc.prepareSearch("logstash-*").get();																	// 全量数据
//		SearchResponse sr = tc.prepareSearch("logstash-*").setQuery(QueryBuilders.matchQuery("uid", "111")).get();					// 指定字段
//		SearchResponse sr = tc.prepareSearch("logstash-*").setQuery(QueryBuilders.regexpQuery("area", ".*1")).get();			// 正则表达
//		SearchResponse sr = tc.prepareSearch("logstash-*").setQuery(QueryBuilders.wildcardQuery("area", "*e*")).get();				// 通配符号
		
		QueryBuilder qb = QueryBuilders.boolQuery()
			.must(QueryBuilders.termQuery("area", "area1"))
			.must(QueryBuilders.regexpQuery("keys", "k.*"))
			.mustNot(QueryBuilders.termQuery("uid", "xyz"));
		SearchResponse sr = tc.prepareSearch("logstash-*").setQuery(qb).get();
		
		SearchHits sh = sr.getHits();
		System.out.println("共搜到: " + sh.getTotalHits() + "条结果!");
		
		for(SearchHit ht : sh){
			System.out.println(ht.getSourceAsString());
		}
		
		tc.close();
	} catch (Exception e) {
		System.out.println("共搜到: 0条结果!");
		e.printStackTrace();
	}
wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==

    关于“爬!扒@切#存$构%查”的话题就这么多,抛砖引玉蜻蜓点水,总之入门十分简单,深钻还是有一定难度的。每个模块花不了几行就能实现最初级的功能,java能成为最广泛的应用开发语言确实是有它显著优势的,虽说有些开发语言随着某个领域的突破会快速发展壮大,但java和c、c++还将长期存在,保持强大的生命力。

网友评论

登录后评论
0/500
评论
厉力文武
+ 关注