PLD - Problem List of Dalaos 发布

@Llf0703  December 1, 2018

项目地址:https://github.com/Llf0703/pld
网页地址:https://pro.llf0703.com/pld/

上午徐妈找我说让我找下大佬在bzoj的刷题清单来照着刷,应该有很大帮助。不过我想如果没有一个时间顺序的话也没法向大佬一样有成长的过程,所以下午就现学了py并写了爬虫,然后先爬了wxh大佬的,毕竟

比赛第三,友谊第二,______第一

具体的使用方法去看README.md吧,我这里主要讲下爬虫及整个项目的原理。

bzoj.py

import urllib.request
import re
import time


def get_html(url): #得到整个网页源代码
    headers = ('User-Agent', 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/45.0.2454.101 Safari/537.36')
    opener = urllib.request.build_opener()
    opener.addheaders = [headers]
    page = opener.open(url)
    html = page.read()
    html = html.decode('utf-8')
    return html


reglist = []

tmp = 1

user=input("请输入用户名:")

url = 'https://www.lydsy.com/JudgeOnline/status.php?user_id='+user #初始的url

html,last_html="",""

while tmp==1:
    last_html=html #上一个页面的源代码,如果完全一样就说明已经到最后一页了(BZOJ就是这样)
    html = get_html(url) //得到源代码
    reg = r'problem.php\?id=([0-9]{1,4})' #正则表达式,匹配题号
    c_reg = re.compile(reg) #将表达式编译
    reglist += c_reg.findall(html) #把当前页所有题号加到总的列表里
    nxt = r'Previous Page</a>\]&nbsp;&nbsp;\[<a href=(.+?)>Next' #匹配下一页的相对链接
    c_nxt = re.compile(nxt)
    nxt_url = c_nxt.findall(html)
    for i in nxt_url:
        url="https://www.lydsy.com/JudgeOnline/"+i #得到下一页url
    if (html==last_html):
        break
    time.sleep(0.5) #停歇0.5s防止被禁IP

rslist = []

for i in range(len(reglist)): #倒序去重输出
    a=reglist.pop()
    if a not in rslist:
        rslist.append(a)

file = open(user+'.txt','w')

for result in rslist:
    file.write(result+'\n')

file.close()

其实整个过程唯一的难点就是翻页,其他就是标准的爬虫。还有BZOJ有反爬虫机制,所以需要一个useragent来伪装浏览器。

然后得到txt以后用process.cpp处理


#include<bits/stdc++.h>

using namespace std;

int main()
{
    freopen("wxh.txt","r",stdin);
    freopen("pro.txt","w",stdout);
    string s;
    while (getline(cin,s))
    {
        string offi="https://www.lydsy.com/JudgeOnline/problem.php?id="+s;
        string bzojch="https://bzoj.llf0703.com/p/"+s+".html";
        string dbzoj="https://darkbzoj.cf/problem/"+s;
        cout<<"<tr>\n";
        cout<<"<td>"<<s<<"</td>\n";
        cout<<"<td><a target=\"_blank\" style=\"color:black;\" href=\""<<offi<<"\">链接</a></td>\n";
        cout<<"<td><a target=\"_blank\" style=\"color:black;\" href=\""<<bzojch<<"\">链接</a></td>\n";
        cout<<"<td><a target=\"_blank\" style=\"color:black;\" href=\""<<dbzoj<<"\">链接</a></td>\n";
        cout<<"</tr>\n";
    }
    return 0;
}

其实只是把它转换成表格的一部分,然后粘贴进去即可。

以上。


添加新评论

  1. cpp文本处理?为何不直接用py?
    %%%

    Reply
    1. @duanyll

      因为我太菜了,py很不熟练,cpp多方便啊

      Reply