Java 将知乎问题下所有的回答保存到本地
Java将知乎问题下所有的回答保存到本地
使用jdk提供的相关api可以获取到网页中的内容,而知乎存放问题回答的地方又是可以通过url的方式被他人直接访问到的。
https://www.zhihu.com/api/v4/questions/xxxxxxxx/answers?include=data%5B%2A%5D.is_normal%2Cadmin_closed_comment%2Creward_info%2Cis_collapsed%2Cannotation_action%2Cannotation_detail%2Ccollapse_reason%2Cis_sticky%2Ccollapsed_by%2Csuggest_edit%2Ccomment_count%2Ccan_comment%2Ccontent%2Ceditable_content%2Cattachment%2Cvoteup_count%2Creshipment_settings%2Ccomment_permission%2Ccreated_time%2Cupdated_time%2Creview_info%2Crelevant_info%2Cquestion%2Cexcerpt%2Cis_labeled%2Cpaid_info%2Cpaid_info_content%2Crelationship.is_authorized%2Cis_author%2Cvoting%2Cis_thanked%2Cis_nothelp%2Cis_recognized%3Bdata%5B%2A%5D.mark_infos%5B%2A%5D.url%3Bdata%5B%2A%5D.author.follower_count%2Cvip_info%2Cbadge%5B%2A%5D.topics%3Bdata%5B%2A%5D.settings.table_of_content.enabled&limit=5&offset=5&platform=desktop&sort_by=default
上面是知乎存放一个问题的所有回答的json信息的url,其中的xxxxxxxx代表的是一个知乎问题的id,这就意味着,只要知道了一个知乎问题的id,那么就可以得到这个问题下的所有回答,并可以通过io将这些信息保存到本地。
一个知乎问题的id可以通过访问这个知乎问题的网页得知。
这是在浏览器中打开一个知乎问题后的网页地址,其中位于question之后,answer之前的那一串数字即是这个问题的id。
将这个id拼接到上面的问题回答json信息的url中,通过浏览器进行访问,可以看到如下界面:
此时知道了知乎问题回答json信息的结构,并且已经掌握了能够将知乎问题回答下载到本地所需要的所有条件,这样就能够动手将这个功能实现出来了。
本人实现了一个使用java图形化界面,根据知乎问题网址获取并将该问题下所有回答保存到本地,并拥有多线程功能的程序。下面是该程序的运行效果。
运行效果:
代码:
以下是该程序的部分代码,如果您想要该程序的完整代码请私信我发给您:
Main.java
package pers;import pers.utils.ConstantUtil;
import java.util.regex.Pattern;
import javax.swing.*;
import java.awt.*;public class Main {public static void main(String[] args) throws Exception {// 图形化界面Dimension dimension = Toolkit.getDefaultToolkit().getScreenSize();int screenWidth = (int)dimension.getWidth();int screenHeight = (int)dimension.getHeight();JFrame window = new JFrame();window.setLayout(null);window.setBounds((screenWidth - ConstantUtil.windowWidth) >> 1,(screenHeight - ConstantUtil.windowHeight) >> 1,ConstantUtil.windowWidth,ConstantUtil.windowHeight);window.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);Font font = new Font("黑体", Font.PLAIN, 30);JTextField field = new JTextField();field.setFont(font);final int fieldWidth = 600, fieldHeight = 80;field.setBounds((window.getWidth() - fieldWidth) >> 1, ((window.getHeight() - fieldHeight) >> 1) - 100, fieldWidth, fieldHeight);JButton button = new JButton("开始");button.setFont(font);button.setBounds(field.getX(), field.getY() + field.getHeight() + 100 ,600, 60);// 20584141button.addActionListener(e -> {// 点击按钮后获取输入的网址String answerId = field.getText();// 对输入内容进行处理以获得问题idif (Pattern.matches(ConstantUtil.URL_REG, answerId)) {if (answerId.charAt(answerId.lastIndexOf('/') - 1) == 'r') {String answerId1 = answerId.substring(0, answerId.lastIndexOf('/') - 7),answerId2 = answerId1.substring(answerId1.lastIndexOf('/') + 1);// 创建线程并执行获取操作new Thread(() -> new Crawler(answerId2)).start();}else {String newAnswerId = answerId.substring(answerId.lastIndexOf('/') + 1);// 创建线程并执行获取操作new Thread(() -> new Crawler(newAnswerId)).start();}}else {// 创建线程并执行获取操作new Thread(() -> new Crawler(answerId)).start();}});window.add(field);window.add(button);window.setVisible(true);// new Thread(() -> new Crawler(answerId)).start();}
}
Crawler.java
package pers;import pers.entity.Answer;
import pers.entity.Overall;
import pers.entity.Paging;
import pers.utils.ConstantUtil;
import pers.utils.FileUtil;
import pers.utils.HttpUtil;public class Crawler {public Crawler(String id) {String text = HttpUtil.sendGet(ConstantUtil.answerURL(id), "utf-8");Overall overall = ConstantUtil.gson.fromJson(text, Overall.class);Paging startPaging = overall.getPaging();while (!startPaging.is_start()) {text = HttpUtil.sendGet(startPaging.getPrevious(), "utf-8");overall = ConstantUtil.gson.fromJson(text, Overall.class);startPaging = overall.getPaging();}// 写入问题String question = overall.getData().get(0).getQuestion().getTitle(),specialQuestion = question.replaceAll(ConstantUtil.REG_EX, question).substring(0, 20) + ".txt";FileUtil.createFile(specialQuestion, true);FileUtil.writeFile(specialQuestion, question + "\n\n");System.out.println("start");int i = 1, j = 1;while (!startPaging.is_end()) {try {Thread.sleep(151 + ConstantUtil.random(29, 52));} catch (InterruptedException e) {e.printStackTrace();}for (Answer answer : overall.getData()) {FileUtil.writeFile(specialQuestion, answer.getAuthor().getName() + "\n");FileUtil.writeFile(specialQuestion, answer.getContent() + "\n\n");System.out.println(answer.getExcerpt());i++;}j++;text = HttpUtil.sendGet(startPaging.getNext(), "utf-8");overall = ConstantUtil.gson.fromJson(text, Overall.class);startPaging = overall.getPaging();}System.out.println("共" + i + "条回答 " + j + "页");System.out.println("end");}
}
欢迎提出意见和建议,感谢支持。
Java 将知乎问题下所有的回答保存到本地相关推荐
- Java开发Twitter爬虫抓取图片和视频并保存到本地
零.目标 使用Java开发爬虫,爬取Twitter状态下评论中的图片和视频,并将其保存到本地. 一.调研爬虫框架 Twitter4J: https://github.com/Twitter4J/Twi ...
- R语言使用caret包构建GBM模型:在模型最优参数已知的情况下,拟合整个训练集,而无需进行任何重采样或参数调优
R语言使用caret包构建GBM模型:在模型最优参数已知的情况下,拟合整个训练集,而无需进行任何重采样或参数调优 目录 R语言使用caret包构建GBM模型:在模型最优参数已知的情况下,拟合整个训练集 ...
- Java删除指定文件夹下的文件和目录
Java删除指定文件夹下的文件和目录 import java.io.File;public class TestFile {public static void main(String[] args) ...
- 下拉加载 实现 java_[Java教程]iscroll5实现一个下拉刷新上拉加载的效果
[Java教程]iscroll5实现一个下拉刷新上拉加载的效果 0 2016-08-24 15:00:08 直接上代码!!! * { margin: 0; padding: 0; } ul, li { ...
- 《Java 进阶之路》 下--推荐书籍
真正想提升自己,我感觉最主要的是先把 JVM.并发.网络这三块知识点学会.学通,这三块是基础,后面所有的框架.中间件等相关的都是基于这三块知识点之上的.学完这三块知识点,可以快速的掌握其它的知识,新框 ...
- Java IO: 其他字符流(下)
转载自 Java IO: 其他字符流(下) 作者: Jakob Jenkov 译者: 李璟(jlee381344197@gmail.com) 本小节会简要概括Java IO中的PushbackRe ...
- ❤️ 爆肝一个月!JAVA零基础入门总结(下)❤️
程序.进程.线程 程序(program) 是为完成特定任务.用某种语言编写的一组指令的集合.即指一段静态的代码,静态对象. 进程(process) 是程序的一次执行过程,或是正在运行的一个程序.是一个 ...
- java文章上一篇下一篇_每个人都必须阅读的10篇Java文章
java文章上一篇下一篇 一个月前,我们发布了每个人都必须阅读的10篇SQL文章列表. 我们相信jOOQ博客上的文章列表将为我们的读者带来非凡的价值. jOOQ博客是一个专注于Java和SQL的博客, ...
- java windows so文件_windows下编译使用NDK,调用SO文件 | 学步园
下载后把压缩包解压出来,例如:D:\ndk,目录下的ndk-build.cmd就是用来编译的批处理命令. 这里以D:\ndk\samples\hello-jni为例,打开D:\ndk\samples\ ...
最新文章
- Java连接Oracle数据库开发银行管理系统【一、需求篇】
- 记一个自己项目上线的全过程
- 《大话数据结构》第9章 排序 9.8 归并排序(下)
- MYSQL-用户操作
- QT QTreeWidget 行切换时改变背景色
- Usage of field SENDABLE in BOL entity
- C++之invalid initialization of non-const reference of type ‘int’ from an rvalue of type ‘int’
- Selenium备忘手册 [转]
- Swarm的进化和大规模应用
- 基于VMware Workstation创建虚拟机,以Ubuntu16.04为例
- drool 7.x 属性 : lock-on-active
- php解析压缩包csv文件,php解析csv文件
- php ci的session和php session,php及codeigniter使用session-cookie的方法(详解)
- 云在脚下 三大云存储方案对比与选型指导
- 教你在Windows自带的微软拼音输入法中用上小鹤双拼方案
- git 学习指南 学习资料笔记
- java 通用事件回调类(观察者队列)
- 通信领域的专有名词释义
- 已解决Excel无法打开文件test.xIsx“,因为文件格式或文件扩展名无效。请确定文件未损坏,并且文件扩展名与文件的格式匹配。
- 300ETF期权适合进行短线交易吗?
热门文章
- 读《汽车构造透视图典》
- Ubuntu 安装MySQL,修改root密码
- mtb11_Dashboard(collapse, hide filters)_DATETRUNC_Donut_各种chart_Custom Shapes Size_action_layout
- 终止进程执行----杀死进程
- 计算机教师的人生格言,教师人生格言座右铭(精选60句)
- 怎样使用css让矩形出现圆角,CSS中设置元素的圆角矩形
- 在知识付费系统搭建上面遇到的坑
- 全国计算机等级考试专用辅导教程,全国计算机等级考试专用辅导教程:三级数据库技术...
- hadoop生态圈之hive面试(一)
- 深度学习笔试100题