大数据项目实战——基于某招聘网站进行数据采集及数据分析(三)

2023-11-05

大数据项目实战

第三章 数据采集



学习目标

掌握 HDFS API 的基本使用
熟悉 HttpClent 爬虫的使用方法


一、分析与准备

本篇主要对要采集的数据结构进行分析以及创建编写数据采集程序的环境,为最终编写数据采集程序做准备。

1、分析网页结构

在爬取网站数据前要先通过分析网站的源码结构制定爬虫程序的编写方式,以便能获取准确的数据。
使用 Google 浏览器进入开发者模式,切换到 Network 这一项,在浏览器的地址栏中输入要爬取数据网站的 URL,在职位搜索栏中输入想要分析的值为进行检索,这时候可以看到服务器返回的内容,因为内容较多,不太容易找到职位信息数据,所以通过设置过滤,过滤掉不需要的信息。
因为该网站的值为信息并不在 HTML 源代码里,而是保存在 JSON 文件例,因此在过滤后的一栏中选择 XHR(XML Http Request) 过滤规则,这样就可以只看到 Ajax 请求中的 JSON 文件了,我们将要获取的值为信息数据也在这个 JSON 文件中。如图所示。

在这里插入图片描述
单击 positionAjax.json 这一条信息,在弹出的窗口选择 Preview 选项,通过逐级展开 JSON 文件中的数据,在 content --》positionResult --》result 下查看大数据相关的值为信息。如图所示。
在这里插入图片描述

2、数据采集环境准备

本篇编写数据采集程序祝以后啊通过 Eclipse 开发工具完成(当然笨猫猫觉得使用 IDEA 开发工具完成也是可以的哦),实现网络数据的采集。
1)打开 Eclipse 工具,单击 File->new->Other,进入 Select a wizard 界面,选择要创建工程的类别,这里选择的是 Maven Project,即创建一个Maven工程。
在这里插入图片描述
在这里插入图片描述
2)创建 Maven Project,单击 Next 按钮,进入新建项目类别的选择界面,勾选 Create a simple project 复选框,创建 一个简单的 Maven 工程。
在这里插入图片描述
3)单击 Next 按钮,进入 Maven 工程的配置界面,即指定 Group Id 为 com.itcast.jobcase,指定 Artifact Id 为 jobcase-reptile,并在 Packaging 下拉选择框中选择打包方式为 jar 。如图所示。
在这里插入图片描述
4)单击 Finish 按钮,完成 Maven 工程的配置,创建好的 Maven 工程 jobcase-reptile
在这里插入图片描述
5)双击 jobcase-reptile 工程,选中 src/main/java 文件夹,右键单击 New->Package 创建 Package 包,并命名包为 com.position.reptile。
在这里插入图片描述
6)单击 Finish 按钮,完成 Package 包的创建,创建好的 Package 包如图所示。
在这里插入图片描述
7)在上图,双击 pom.xml 文件,添加编写爬虫程序所需要的 HttpClient 和 JDK 1.8 依赖。pom.xml 文件添加的内容,具体如下。

<dependencies>
  	<dependency>
  		<groupId>org.apache.httpcomponents</groupId>
  		<artifactId>httpclient</artifactId>
  		<version>4.5.4</version>
  	</dependency>
  	<dependency>
  		<groupId>jdk.tools</groupId>
  		<artifactId>jdk.tools</artifactId>
  		<version>1.8</version>
  		<scope>system</scope>
  		<systemPath>${JAVA_HOME}/lib/tools.jar</systemPath>
  	</dependency>
  	<dependency>
  		<groupId>org.apache.hadoop</groupId>
  		<artifactId>hadoop-common</artifactId>
  		<version>2.7.4</version>
  	</dependency>
  	<dependency>
  		<groupId>org.apache.hadoop</groupId>
  		<artifactId>hadoop-client</artifactId>
  		<version>2.7.4</version>
  	</dependency>
  </dependencies>

在这里插入图片描述

8)选中 jobcase-reptile 工程,右键单击选择 Maven->Update Project 更新工程。至此,就完成了 Maven 工程的搭建。

二、采集网页数据

1.创建响应结果 JavaBean 类

本项目才采集的网页数据为 HTTP 请求过程中的响应结果数据,通过创建的 HttpClient 响应结果对象作为数据存储的载体,对响应结果中的状态码和数据内容进行封装。
在 com.position.reptile 包下,创建名为 HttpClientResp.java 文件的 JavaBean 类。

package com.position.reptile;
import java.io.Serializable;


public class HttpClientResp implements Serializable{
	private static final long serialVersionUID = -8664139869153319066L;
	//相应状态码
	private int code;
	private String content;
	
	//定义无参的构造方法
	public HttpClientResp() {
		
	}
	
	//定义有参的构造方法
	public HttpClientResp(String content) {
		this.content = content;
	}

	public HttpClientResp(int code) {
		this.code = code;
	}
	
	public HttpClientResp(int code, String content) {
		this.code = code;
		this.content = content;
	}

	//定义属性的get/set方法
	public int getCode() {
		return code;
	}

	public void setCode(int code) {
		this.code = code;
	}

	public String getContent() {
		return content;
	}

	public void setContent(String content) {
		this.content = content;
	}
	
	//重写toString方法
	@Override
	public String toString() {
		return "HttpClientResp [code=" + code + ", content=" + content + "]";
	}
	
}

2.封装 HTTP 请求的工具类

在 com.position.reptile 包下,创建一个命名为 HttpClientUtils.java 文件的工具类,用于实现 HTTP 请求的方法。

1)定义三个全局变量

在类中定义三个全局变量,便于在类中的方法统一访问,下面是这三个常量的概述。

ENCODING:表示定义发送请求的编码格式
CONNECT_TIMEOUT:表示设置建立连接超时时间
SOCKET_TIMEOUT:表示设置请求获取数据的超时时间
为了有效地防止程序阻塞,可以在程序中设置 CONNECT_TIMEOUT 和 SOCKET_TIMEOUT 两项参数,通过在类中定义常量的方式定义参数的内容。

文件HttpClientUtils.java

//编码格式,发送编码格式统一用UTF-8
private static final String ENCODING = "UTF-8";

//设置连接超时时间,单位毫秒
private static final int CONNECT_TIMEOUT = 100000;

//请求获取数据的超时时间(即响应时间),单位毫秒
private static final int SOCKET_TIMEOUT = 100000;

2)编写 packageHeader() 方法

在工具类中定义 packageHeader() 方法用于封装 HTTP 请求头的参数,如 Cookie、User-Agent 等信息,该方法中包含两个参数,分别为 params 和 httpMethod。

文件HttpClientUtils.java

public static void packageHeader(Map<String,String>params,
		HttpRequestBase httpMethod) {
			//封装请求头
			if(params != null) {
				/*
				 * 通过entrySet()方法从params中返回所有键值对的集合,并保存在entrySet中
				 * 通过foreach()方法每次取出一个键值对保存在一个entry中
				 * */
				Set<Entry<String,String>>entrySet = params.entrySet();
				for(Entry<String,String>entry : entrySet) {
					//通过entry分别获取键-值,将键-值参数设置到请求头HttpRequestBase对象中
					httpMethod.setHeader(entry.getKey(),entry.getValue());
				}
		}
}

params 参数的数据类型为 Map<String,String>,主要用于封装请求头中的参数,其中, Map 的 Key 表示请求头参数的名称,Value 代表请求头参数的内容。例如,在请求头中参加 Cookie,那么 Map 的 Key 则为 Cookie,Value则为 Cookie 的具体内容。
httpMethod 参数为 HttpRequstBase 类型,HttpRequestBase 是一个抽象类,用于调用子类 HttpPost 实现类。

3)编写 packageParam() 方法

设置 HTTP 请求头向服务器发送请求,通过设置请求参数来指定获取哪些类型的数据内容,具体需要哪些参数以及这些参数的作用,会在后续的代码中进行讲解。在工具类中定义 packageParam() 方法用于封装 HTTP 请求参数,该方法中包含两个参数,分别为 params 和 httpMethod 。

文件HttpClientUtils.java

public static void packageParam(Map<String,String>params,
		HttpEntityEnclosingRequestBase httpMethod) 
		throws UnsupportedEncodingException{
			//封装请求对象
			if(params != null) {
				/*
				 * NameValuePair是简单名称值对节点类型 多用于Java想url发送Post请求。在发送post请求时用该list来存放参数
				 */
				List<NameValuePair>nvps = new ArrayList<NameValuePair>();
				/*
				 * 通过entrySet()方法从params中返回所有键值对的集合,
				 * 并保存在entrySet中,通过foreach方法每次取出一个键值对保存在一个entry中
				 */
				Set<Entry<String,String>>entrySet = params.entrySet();
				for(Entry<String,String>entry : entrySet) {
					//分别提取entry中的key和value放入nvps数组中。
					nvps.add(new BasicNameValuePair(entry.getKey(),
							entry.getValue()));
				}
				//设置到请求的http对象中,这里的ENCODING为之前创建的编码常量
				httpMethod.setEntity(new UrlEncodedFormEntity(nvps,ENCODING));
		}
}

上述代码中,params 参数为 Map<String,String> 类型,用于封装请求中的参数名称及参数值, httpMethod 参数为 HttpEntityRequestBase 类型,是一个抽象类,其实现类包括 HttpPost、HttpPatch、HttpPut,是 HttpRequesBase 的子类,将设置的请求持仓数封装在 HttpEntityEnclosingRequestBase 对象。

4)编写 HttpClient() 方法

前两步已经创建了封装请求头和请求参数的方法,按照 HTTP 请求的流程在服务器收到 HTTP 响应内容,该方法中包含三个参数,分别为 httpResponse、httpClient 和 httpMethod,该方法包含返回值,返回值类型为之前定义的实体类 HttpClientResp,其中内容包括响应代码和响应内容。

public static HttpClientResp
	getHttpClientResult(CloseableHttpResponse httpResponse,
	CloseableHttpClient httpClient,HttpRequestBase httpMethod) 
	throws Exception{
		//通过请求参数httpMethod执行Http请求
		httpResponse = httpClient.execute(httpMethod);
		//获取HTTP的响应结果
		if(httpResponse != null && httpResponse.getStatusLine() != null) {
			String content = "";
			if(httpResponse.getEntity() != null) {
				//将响应结果转为String类型,并设置编码格式
				content = EntityUtils.toString(httpResponse.getEntity(),ENCODING);
			}
			
			/*
			 * 返回HTTPClientResp实体类的对象,这两个参数
			 * 分别 代表实体类中的code属性和content属性,
			 * 分别代表响应代码和响应内容
			 */
			return new HttpClientResp(httpResponse.getStatusLine().getStatusCode(),content);
		}
		//如果没有接收到响应内容则返回响应的错误信息
		return new HttpClientResp(HttpStatus.SC_INTERNAL_SERVER_ERROR);
}

在上述代码中,创建的 getHttpClientResult() 方法包含三个参数: httpResponse 参数为 CloseableHttpResponse 类型,用于在服务器接收并解释请求消息之后以 HTTP 响应消息进行响应,我们将要获取的响应内容就是通过该参数获取:httpClient 参数为 CloseableHttpClient 类型,用于表示 HTTP 请求执行的基础对象:httpMethod 参数为 HttpRequestBase 类型,用于实现 HttpPost。

5)编写 doPost() 方法

在前面创建了请求头、请求参数以及获取响应内容的方法。接下来将讲解荣国 HttpClient Post 方式提交请求头和请求参数,从服务端返回状态码和 JSON 数据内容。
注意:选取请求方法要与爬取网站规定的请求方法一致。
在这里插入图片描述

public static HttpClientResp doPost(String url,
		Map<String,String>headers,
		Map<String,String>params) throws Exception{
			//创建httpClient对象
			CloseableHttpClient httpClient = HttpClients.createDefault();
			//创建httpPost对象
			HttpPost httpPost = new HttpPost(url);
			
			/*
			 * setConnectTimeout:设置连接超时时间,单位毫秒。 setConnectionRequestTimeout:设置从connect
			 * Manager(连接池) 获取Connection 超时时间,单位毫秒。这个属性是新加的属性,因为目前版本是可以共享连接池的。
			 * setSocketTimeout:请求获取数据的超时时间(即响应时间),单位毫秒。 如果访问一个接口,多少时间内无法返回数据,就直接放弃次调用。
			 */
			
			
			//封装请求配置项
			RequestConfig requestConfig = RequestConfig.custom()
					.setConnectTimeout(CONNECT_TIMEOUT)
					.setSocketTimeout(CONNECT_TIMEOUT)
					.build();
			//设置post请求配置项
			httpPost.setConfig(requestConfig);
			//通过创建的packageHeader()方法设置请求头
			packageHeader(headers,httpPost);
			//通过创建的packageParam()方法设置请求参数
			packageParam(params,httpPost);
			//创建httpResponse对象获取响应内容
			CloseableHttpResponse httpResponse = null;
			try {
				//执行请求并响应结果
				return getHttpClientResult(httpResponse,httpClient,httpPost);
			}finally {
				//释放资源
				release(httpResponse,httpClient);
		}
}

上述代码中的 doPost() 方法,定义的返回值类型为实体类 HttpClientResp 对象,方法中包含三个参数。三个参数如下。

url:进行数据采集的网站链接
headers:请求头数据
params:请求参数数据
在 doPost() 方法中调用已创建的 getHttpClientResult() 方法获取响应结果数据并作为方法的返回值。

在释放资源一行代码会报错,因为释放资源方法需要通过自行创建后去调用,下面梁编写释放资源代码。

6)编写 release() 方法

HttpClient 在使用过程中要注意资源释放和超时处理的问题,如果线程资源无法释放,会导致线程一直在等待,最终可导致内存或线程被大量占用。这里创建了一个释放资源的方法 release() 主要用于释放 httpclient(HTTP 请求)对象资源和 httpResponse(HTTP 响应)对象资源。

private static void release(CloseableHttpResponse httpResponse, 
			CloseableHttpClient httpClient) 
			throws IOException{
				// TODO Auto-generated method stub
				// 释放资源
				if(httpResponse != null) {
					httpResponse.close();
				}
				if(httpClient != null) {
					httpClient.close();
			}
}

至此, HttpClient 的所有工具类准备完毕,后续直接在实现网页数据采集的主类中调用这些方法即可,通过编写存储数据的工具类,实现瓯江采集的网页数据存储到 HDFS 上。

3.封装存储在 HDFS 的工具类

通过前两节的操作可以成功采集招聘网站的数据,为了便于后续对数据预处理和分析,需要将数据采集程序获取的数据存储到本地或者集群中的 HDFS 上,下面演示如何将爬取的数据存放到 HDFS 上。

1)添加 Hadoop 的依赖

<dependency>
  		<groupId>org.apache.hadoop</groupId>
  		<artifactId>hadoop-common</artifactId>
  		<version>2.7.4</version>
  	</dependency>
  	<dependency>
  		<groupId>org.apache.hadoop</groupId>
  		<artifactId>hadoop-client</artifactId>
  		<version>2.7.4</version>
 </dependency>

之前添加过了,可以不用再次添加。

2)编写 createFileBySysTime() 方法。

在 com.position.reptile 包下,创建名为 HttpClientHdfsUtils.java 文件工具类,实现将数据写入 HDFS 的方法 createFileBySysTime() ,该方法包括三个参数:url (表示 Hadoop 地址)、fileName(表示存储数据的文件名称)和 data(表示数据内容)。

文件HttpClientHdfsUtils.java

public class HttpClientHdfsUtils {
	public static void createFileBySysTime(String url,String fileName,String data) {
		//指定操作HDFS的用户
		System.setProperty("HADOOP_USER_NAME", "root");
		Path path = null;
		//读取系统时间
		Calendar calendar = Calendar.getInstance();
		Date time = calendar.getTime();
		//格式化系统时间为年月日的形式
		SimpleDateFormat format = new SimpleDateFormat("yyyyMMdd");
		//获取系统当前时间并将其转换为string类型,fileName即存储数据的文件夹名称
		String filePath = format.format(time);
		//构造Configuration对相关,配置Hadoop参数
		Configuration conf = new Configuration();
		//实例化URI引入uri
		URI uri = URI.create(url);
		//实例化FileSystem对象,处理文件和目录相关的事务
		FileSystem  fileSystem;
		try {
			//获取文件系统对象
			fileSystem = FileSystem.get(uri,conf);
			//定义文件路径
			path = new Path("/JobData/"+filePath);
			//判断路径是否为空
			if(!fileSystem.exists(path)) {
				//创建目录
				fileSystem.mkdirs(path);
			}
			//在指定目录下创建文件
			FSDataOutputStream fsDataOutputStream = fileSystem.create(
					new Path(path.toString()+"/"+fileName));
			//向文件中写入数据
			IOUtils.copyBytes(new ByteArrayInputStream(data.getBytes()),
					fsDataOutputStream, conf,true);
			//关闭连接释放资源
			fileSystem.close();
		}catch(IOException e) {
			e.printStackTrace();
		}
	}
}

上述代码中,指定在 Hadoop 集群的 HDFS 上创建 /JobData 目录,用于存储当天爬取的数据,数据将文件的形式存储在由当前系统日期的“年月日”组成目录下。

4.实现网页数据采集

1)获取网站的请求头内容

在这里插入图片描述
上图中,将 Request Headers 一项中的参数以<Key,Value>形式写入到 Map 集合中作为数据采集程序的请求头,目的是模拟浏览器登录,防止爬虫失败。

2)创建 Map 集合 headers

在 com.position.reptile 包下,创建名为 HttpClientData.java 文件的主类,用于实现数据采集功能,在该类中创建 main() 方法,在 main() 方法中创建 Map 集合 headers ,将请求头参数放入集合中。

文件 HttpClientData.java

//设置请求头
		Map<String,String> headers = new HashMap<String,String>();
		headers.put("Cookie","");
		headers.put("Connection","keep-alive");
		headers.put("Accept-Language", "zh-CN,zh;q=0.9");
		headers.put("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/99.0.4844.84 Safari/537.36");
		headers.put("content-type", "application/x-www-form-urlencoded; charset=UTF-8");
		headers.put("Referer", "https://www.lagou.com/jobs/list_%E5%A4%A7%E6%95%B0%E6%8D%AE/p-city_0?&cl=false&fromSearch=true&labelWords=&suginput=");
		headers.put("Origin", "https://www.lagou.com");
		headers.put("x-requested-with", "XMLHttpRequest");
		headers.put("x-anit-forge-token", "None");
		headers.put("Cache-Control", "no-cache");
		headers.put("x-anit-forge-code", "0");
		headers.put("Host", "www.lagou.com");

注意:Cookie 后面要有参数,这里因为太长了我设置了空字符,在开发者工具找到 Cookie参数后,其后面的参数要写进去。

3)创建 Map 集合 params

在 HttpClientData 类的 main() 方法中再创建一个 Map 集合 params,将请求参数放入集合中,本项目主要使用三个参数类指定获取获得数据类型,这三个参数包括: kd(职位类型),city (城市)和 pn(页数)。其中,pn 参数需要在每次 HTTP 请求中发生递增变化,用于爬取不同页面中的数据,因此向集合 params 中添加 pn 参数的操作应放在循环中进行。请求头和请求参数设置完毕后,通过 HttpClient 的 post 请求实现数据的获取,因为需要获取不同页面的数据,每个页面的 pn 参数都会发生变化(请求参数发生变化),因此获取数据的方法要放在实现的 for 循环中,通过变化的参数获取数据,将数据保存到 HDFS 上。

文件 HttpClientData.java

Map<String,String>params = new HashMap<String,String>();
		params.put("kd", "大数据");
		params.put("city", "全国");
		
		for(int i = 1; i < 31; i++) {
			params.put("pn", String.valueOf(i));
			HttpClientResp result = HttpClientUtils.doPost("https://www.lagou.com/jobs/positionAjax.json?needAddtionalResult=false&first=true&px=default", headers, params);
			HttpClientHdfsUtils.createFileBySysTime("hdfs://hadoop001:8020", "page"+i, result.toString());
			Thread.sleep(1*500);
		}

5.运行结果

在虚拟机上执行以下命令,有图中结果。

hdfs dfs -ls /JobData/。。。。。。

在这里插入图片描述
点击其中一个page,下载查看内容。
在这里插入图片描述
有如下内容即为爬取成功。
在这里插入图片描述


总结

本篇主要简介网络数据采集程序的变下。通过本篇的学习,读者可以掌握通过 HttpClient 框架进行爬虫的技巧,熟悉编写爬虫程序的操作流程。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

大数据项目实战——基于某招聘网站进行数据采集及数据分析(三) 的相关文章

随机推荐

  • 无法连接至Synaptics定点装置驱动程序,联想thinkpad最完美解决办法

    话说今天手欠 把红点和触摸板都关上了 闲着没事清理注册表信息 这下好了 我的红点的注册表就被清了 刚百度过遇到各种各样的回答 有新建注册表的 有直接运行SynTPEnh exe程序的 还有建议去重装驱动的 对于ThinkPad来说 别的没用
  • 【ubuntu软件】atom笔记软件----下载、配置、使用

    最近平台切换到了ubuntu环境 很多软件都不能用了 今天看下atom这个笔记软件的下载 配置及其使用 一 为什么选择atom atom是免费的 这个及其重要 其次atom是跨平台的 二 下载 1 官网下载 下载地址 https atom
  • vscode快捷键:折叠、展开代码

    vscode代码编辑器折叠所有区域的代码快捷键 1 折叠所有区域代码的快捷键 ctrl k ctrl 0 先按下ctrl和K 再按下ctrl和0 注意这个是零 不是欧 2 展开所有折叠区域代码的快捷键 ctrl k ctrl J 先按下ct
  • Python 之 lambda 函数完整详解 & 巧妙运用

    文章目录 一 前言 二 lambda 语法 三 lambda 特性 四 lambda 常见用法 五 lambda 用法之高阶函数 一 前言 lambda 函数在 Python 编程语言中使用频率非常高 使用起来非常灵活 巧妙 那么 什么是l
  • php token 存储,PHP 实现Token无状态登录验证,无需服务端存储,降低服务器压力...

    早之前大家常用的登录方式是客户端传输账号密码 后台通过比对后成功了 客户端存储在cookie中 每次刷新页面或请求服务端 服务端都需要从数据库中调取对比信息 对于服务端来说 对比登录状态是服务端请求最频繁的动作 所以如果每次都调用数据库请求
  • java参数传递(局部变量)

    基本数据类型 传递的是值的副本 修改副本不会对原值造成影响 也就是值传递 Byte Short Integer Long Float Double Boolean Character 引用数据类型 除开基本数据类型的所有数据类型 传递的是对
  • centos8 安装notepadqq

    yum install epel release yum install snapd systemctl enable now snapd socket snap install notepad plus plus yum install
  • 【附源码】计算机毕业设计SSM汽车维修服务系统

    项目运行 环境配置 Jdk1 8 Tomcat7 0 Mysql HBuilderX Webstorm也行 Eclispe IntelliJ IDEA Eclispe MyEclispe Sts都支持 项目技术 SSM mybatis Ma
  • FTP使用教程

    FTP使用教程 目录 一 FTP简介 二 FTP搭建 三 FTP使用 一 FTP简介 FTP中文为文件传输协议 简称为文传协议 它也是一个应用程序 不同的操作系统有不同的FTP应用程序 这些应用程序都遵守同一种协议以传输文件 FTP主要的功
  • KD树

    KD树 1 概述 KD树是一种查询索引结构 广泛应用于数据库索引中 从概念的角度讲 它是一种高纬数据的快速查询结构 本文首先介绍1维数据的索引查询 然后介绍2维KD树的创建和查询 2 1维数据的查询 假设在数据库的表格T中存储了学生的语文成
  • 数据挖掘概述

    1 数据挖掘定义 数据挖掘是从大量的 不完全的 有噪声的 模糊的 随机的应用数据中 提取出潜在且有用的信息的过程 2 数据分析的过程 1 确定知识发现的过程 2 数据采集 数据质量决定挖掘的上限 而算法仅仅是逼近这个上限 3 数据搜索 将数
  • 怎么做好中层管理

    随着工作经验和年限不断增加 经过努力相信很多IT技术人员和我一样从一个开发角色转变为技术管理或者部门管理角色 一方面需要做技术解决方案架构开发上工作 带领团队攻关技术难题 同时也会面临一些团队管理和团队业绩增长需要不断去提高和突破 虽然不必
  • 基于MATLAB的遗传算法优化混合流水车间调度问题

    基于MATLAB的遗传算法优化混合流水车间调度问题 混合流水车间调度问题是在车间生产中常见的一个优化问题 旨在通过合理安排作业顺序和机器分配 最大限度地提高生产效率和降低生产成本 本文将介绍如何使用MATLAB编写遗传算法来解决混合流水车间
  • Ubuntu ssh root 登录不了解决办法

    Ubuntu在安装的时候 设置了sudo的密码 但是这并不是root用户的密码 导致即使修改了 etc ssh sshd config 文件 运行root用户登录 还是会出现Permission denied 真是坑啊 差点没把我气到吐血
  • 发送html邮件时遇到的奇怪的乱码问题

    解析文件字符流 作为内容发送邮件到客户端 解析的代码如下 BufferedReader reader new BufferedReader new FileReader file 发现windows系统下发送的邮件时是正常的 在linux下
  • NETPLIER : 一款基于概率的网络协议逆向工具(一)理论

    本文系原创 转载请说明出处 信安科研人 关注微信公众号 信安科研人 获取更多网络安全学术技术资讯 今日介绍一篇发表在2021 NDSS会议上的一项有关协议逆向的工作 文章目录 1 网络协议逆向工程简介 1 1 协议逆向工程的主流技术 案例
  • 【计算机网络】第一章知识点汇总

    第一章学习重点 2 5 因特网的组成 通信方式与交换方式 4 4 时延 计算 4 5 时延带宽积 计算 5 2 协议的划分与层次 5 3 五层协议的体系结构 OSI与TCP IP的比较 1 计算机网络在信息时代的作用 三网融合中的 三网 指
  • Hadoop-HBase 单机部署

    一 系统版本 Linux系统 wdOS 1 0 x86 64 iso 关于wdOS说明 1 安装简单 快速 去掉了安装过程中不必要的烦锁操作和不必要的选择 2 可选安装集成web环境 如lamp lnmp lnamp 并可相互自由切换使用
  • 设计模式之适配器模式(Adapter)

    1 定义 适配器模式 Adapter 指的是将一个类的接口转换成另一个可以兼容的接口 比如我们日常生活中的转换头 古早时期使用的电池万能充 就相当于程序中使用的适配器模式 2 适配器模式的种类 2 1 类适配器模式 类适配器模式通过多重继承
  • 大数据项目实战——基于某招聘网站进行数据采集及数据分析(三)

    大数据项目实战 第三章 数据采集 文章目录 大数据项目实战 学习目标 一 分析与准备 1 分析网页结构 2 数据采集环境准备 二 采集网页数据 1 创建响应结果 JavaBean 类 2 封装 HTTP 请求的工具类 1 定义三个全局变量