通过WebMagic认识正则表达式和XPATH

 
 

最近在自学JAVA的过程中,偶然想到了做个爬虫程序,经过简单的对比,发现了WebMagic这个库,在使用库的过程中因为涉及到正则表达式和XPATH,所以做个笔记,记录一下,否则稍微过段时间不看就忘记了。 以内涵社区为例,打开内涵社区,然后右键“检查”(Chrome浏览器,得到如下html,这里只截取其中一部分作为示例)

<div class="detail-wrapper">

<div class="header ">

<a href="http://neihanshequ.com/user/50634720394//">

![](http://upload-images.jianshu.io/upload_images/2761682-5711d755117472ef?imageMogr2/auto-orient/strip%7CimageView2/2/w/1240)

<div class="name-time-wrapper left">

<span class="name">我是MC秀芹</span>

<span class="time timeago" title="2017-07-19 07:43:53000">

07-19 07:43

</span>

</div>

</a>

</div>

<div class="content-wrapper">

<a target="_blank" class="image share_url" href="http://neihanshequ.com/p63821171027/" data-group-id="63821171027" >

<div class="upload-txt no-mb">

<h1 class="title">

<p>今年18岁的我,年纪轻轻月薪就已经达到1500了,加上提成满勤再加上我天生的睿智头脑,平常帮客人拿下拖鞋点下烟得点小费可以拿到2200,觉得自己这几年过得也不容易,现在这么有钱,觉得不知道怎么花了,开始花钱大手大脚了,以前网吧包夜都是自己带瓶水,现在敢喝冰红茶了,还是一晚上买两瓶,甚至吃泡面要加两根肠,我觉得现在有点迷失自我,有什么办法!能回到初心!</p>

</h1>

</div>

</a>

</div>

然后,开始我们的爬虫程序:
创建一个类GithubRepoPageProcessor(为什么叫Github...因为跟着写demo的时候创建的,懒得修改了)继承PageProcessor,并实现方法:

public class GithubRepoPageProcessor implements PageProcessor {
    public static final String URL_LIST = "http://neihanshequ.com/.*";
    private Site site = Site.me().setRetryTimes(3).setSleepTime(1000);
    public void process(Page page) {

        //文章页
        Object s0 = page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='header ']/a/img/@src");
        Object s1 = page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='header ']/a/div/span[@class='name']/text()");
        Object s2 = page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='header ']/a/div/span[@class='time timeago']/text()");
        Object s3 = page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='content-wrapper']//h1[@class='title']/p/text()");
        if (s0 != null
                &&s1 != null
                && s2 != null
                && s3 != null) {
            page.putField("头像", s0);
            page.putField("用户名", s1);
            page.putField("发表时间", s2);
            page.putField("发表内容", s3);
        }
        page.addTargetRequests(page.getHtml().links().regex(URL_LIST).all());

    }

    public Site getSite() {
        return site;
    }
}

好,那么这里就要用正则和XPATH提取我们需要的内容了:

先来看下正则表达式的常用字符:

.        任意字符除换行符
\w       字母、数字、下划线、汉字
\d       数字
\b       标注单词的开始、结束位置
^        标注开始位置
$        标注结束位置

*        重复零次或更多次
+        重复一次或更多次
?        重复零次或一次
{n}      重复n次
{n,}     重复n次或更多次
{n,m}    重复n到m次

[0-9]           等同于\d
[a-z]           a-z中的任意一个字母
[aeiou]         aeiou中的任意一个字母
[0-9 a-z A-Z]   等同于\w

|        分支(从左到右依次执行,匹配依次后,后面的不再匹配)

()       分组(表达式分组)

\W    不是字母、数字、下划线、汉字
\S    不是空白符
\D    非数字
\B    不是单词开头、结束的位置
[^x]    除了x以外的任意字符
[^aeiou]  除了aeiou这几个字母以外的任意字符

(?<=exp) 掐头
(?=exp)  去尾

(?<!exp)  禁止前面包含字符
(?!exp)    禁止后面包含字符

接下来使用上面的html文件依次举例:
1、获取所有的数字

\d+

扩展例子:

匹配手机号(匹配13、15、17、18开头的11位手机号):
^1[3578]\d{9}$

匹配QQ号(匹配5-11位的QQ号)
^\d{5,11}$

匹配126邮箱(6-20个字节的用户名)
[a-zA-Z][a-zA-Z0-9]{5,19}@126.com$

匹配IP地址(网上有其他的正则,认为01.01.0.1算是正确的IP,但是我不喜欢,所以写个这样的)
(1\d\d|2[0-4]\d|25[0-4]|^[1-9])\.((1\d\d|2[0-4]\d|25[0-4]|[0-9])\.){2}(1\d\d|2[0-4]\d|25[0-4]|[0-9])

2、获取所有p标签里的内容

正则:
(?<=<p>).*(?=</p>)

XPATH:
精确路径定位:
//div[@class='detail-wrapper']//div[@class='upload-txt  no-mb']//h1/p/text()
简单定位:
//h1[@class='title']/p/text()

3、获取所有的href内容

正则:
(?<=href=").*(?=/")

XPATH:
精确路径定位:
//div[@class='detail-wrapper']//a/@href
简单定位:
//a[@class='image share_url']/@href

分析GithubRepoPageProcessor里面的内容:

//匹配http://neihanshequ.com为前缀的所有网址
public static final String URL_LIST = "http://neihanshequ.com/.*";

//获取当前html页面的所有class名称为detail-wrapper的div下的所有class名称为header下的a标签里面的img标签中的src地址
Object s0 =page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='header ']/a/img/@src")

//获取上述前缀的a标签下的div下的class名为name的span标签里面的内容
Object s1 =page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='header ']/a/div/span[@class='name']/text()")

//获取class名为time timeago的span标签里的内容
Object s2 =page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='header ']/a/div/span[@class='time timeago']/text()")

//获取p标签下的内容
Object s3 =page.getHtml().xpath("//div[@class='detail-wrapper']//div[@class='content-wrapper']//h1[@class='title']/p/text()")

然后把获取到的内容输出到控制台:
page.putField("头像", s0);
            page.putField("用户名", s1);
            page.putField("发表时间", s2);
            page.putField("发表内容", s3);

创建MainApp写入main方法并调用运行

public class MainApp {
    public static void main(String[] args) {
        System.out.println("开始爬取...");
        Spider.create(new GithubRepoPageProcessor()).addUrl("http://neihanshequ.com").thread(5).run();
    }
}

最终效果:


WX20170720-151802.png


作者:独箸
链接:http://www.jianshu.com/p/3d9e5bb9f7b0
來源:简书
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
  • 1
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值