<?xml version="1.0" encoding="utf-8"?>
<feed xmlns="http://www.w3.org/2005/Atom">
  <title>风晓博客</title>
  
  <subtitle>只有飘零的风，知道你所欲所求</subtitle>
  <link href="/atom.xml" rel="self"/>
  
  <link href="http://www.windknew.com/"/>
  <updated>2020-11-04T08:57:19.909Z</updated>
  <id>http://www.windknew.com/</id>
  
  <author>
    <name>风晓</name>
    
  </author>
  
  <generator uri="http://hexo.io/">Hexo</generator>
  
  <entry>
    <title>XenServer服务搭建（8.2）</title>
    <link href="http://www.windknew.com/Xenserver%E6%9C%8D%E5%8A%A1%E6%90%AD%E5%BB%BA/"/>
    <id>http://www.windknew.com/Xenserver服务搭建/</id>
    <published>2020-11-04T09:52:56.000Z</published>
    <updated>2020-11-04T08:57:19.909Z</updated>
    
    <content type="html"><![CDATA[<hr><h2 id="XenServer"><a href="#XenServer" class="headerlink" title="XenServer"></a>XenServer</h2><hr><h3 id="XenServer简介"><a href="#XenServer简介" class="headerlink" title="XenServer简介"></a>XenServer简介</h3><p>Citrix Xenserver，思杰基于Xen的虚拟化服务器。Citrix XenServer是一种全面而易于管理的<a href="https://baike.baidu.com/item/服务器虚拟化/2639077" target="_blank" rel="noopener">服务器虚拟化</a>平台，基于强大的 Xen Hypervisor 程序之上。Xen技术被广泛看作是业界最快速、最安全的<a href="https://baike.baidu.com/item/虚拟化软件/3765902" target="_blank" rel="noopener">虚拟化软件</a>。XenServer 是为了高效地管理 Windows(R) 和 Linux(R)<a href="https://baike.baidu.com/item/虚拟服务器/5799459" target="_blank" rel="noopener">虚拟服务器</a>而设计的，可提供经济高效的服务器整合和<a href="https://baike.baidu.com/item/业务连续性/5034951" target="_blank" rel="noopener">业务连续性</a>。</p><h3 id="准备工作"><a href="#准备工作" class="headerlink" title="准备工作"></a>准备工作</h3><ol><li><p>在XenServer官网下载<a href="https://xenserver.org/open-source-virtualization-download.html" target="_blank" rel="noopener">ISO文件</a>，需要注册账号；</p></li><li><p>利用镜像制作软件做启动盘,我这里用的是<a href="https://cn.ultraiso.net/uiso9_cn.exe" target="_blank" rel="noopener">UltraISO</a>,关于镜像的写入，链接里都有相关教程</p></li><li><p>安装<strong>XenServer</strong>的服务器CPU必须支持虚拟化，Intel (VT-X) 或者AMD (AMD-V)</p></li><li><p>服务器选择u盘启动</p></li></ol><h3 id="安装步骤"><a href="#安装步骤" class="headerlink" title="安装步骤"></a>安装步骤</h3><p>  一、选择键盘类型：US。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271934291935826.png" alt="img"></p><p>二、这个是欢迎界面，选择“OK”即可。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271934596613818.png" alt="img"></p><p>三、这个是使用协议，我们必须得接受，否则就不能继续安装了！</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271935349431006.png" alt="img"></p><p>四、这个是警告，告诉你XenServer所需要的硬件条件，我们选择“OK”即可。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271936087869666.png" alt="img"></p><p>六、这个是存储设备选择界面，第一个是本地磁盘—sda;第二个是自动精简配置—thin provisioning ，主要是针对XenDesktop MCS，如果想详细了解，可以上查查。我们这里就直接选择本地。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271936441939582.png" alt="img"></p><p>七、这个是安装方式选择界面，一共有三种：本地、HTTP/FTP、NFS，我们这里直接用本地，一般在公司都会用ftp或nfs通过网络安装。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271937149114032.png" alt="img"></p><p>八，提示我们，要不要追加安装补丁包，我们不用就直接选择“NO”。</p><p><img src="https://gitee.com/yhndbd/img/raw/master/271937456307481.png" alt="img"></p><p>九、光盘验证，这里提示让我们选择要不要验证我们的安装光盘有没有错，第一为忽略，即直接跳过，第二个为验证安装源，我们的选择跳过即可。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271938149747917.png" alt="img"></p><p>十、这里要我们输入root的密码，一般在企业中，我们的密码最好复杂些并且要记下来。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271938490995791.png" alt="img"></p><p>十一、这里为XenServer主机的网络设置，有DHCP自动获取和静态IP两种，具体情况要看个人的安装网络环境。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271939265995335.png" alt="img"></p><p>十二、这里为配置XenServer主机的主机名与DNS。DNS 就是公司的DNS服务器，不懂就问网管了。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271940110687215.png" alt="img"></p><p>十三、区时选择，我们选择亚洲—“Asia”。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271940353804755.png" alt="img"></p><p>十四、具体时区，我们直接使用上海—“Shanghai”即可。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271941104115485.png" alt="img"></p><p>十五、这个是设置NTP，主要是与校准时钟有关，特别是在服务器集群时，我们所有的服务器时间必须得一致，否则很容易出现一些很奇怪的问题。当然，你也可以都选择第二个，本地时间，这个的话，就不必设置ntpserver了，不过它为在安装结束后让你手动设置时间的。NTPServer可以到<a href="http://www.ntp.org/" target="_blank" rel="noopener">http://www.ntp.org/</a> 这里看看如何设置。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271941401151878.png" alt="img"></p><p>十六、安装界面</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271942067551273.png" alt="img"></p><p>十七、安装过程</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271942420521690.png" alt="img"></p><p>安装完毕后，它会提示让你重启，重新启动后即可完成XenServer8.2的安装。</p><p>一，IP地址的配置，XenServer 安装好之后，就是这个界面了。可以配置IP 地址，DNS等。</p><p><img src="https://images0.cnblogs.com/blog2015/101934/201504/271943192861547.jpg" alt="img"></p><h3 id="安装过程中遇到的问题"><a href="#安装过程中遇到的问题" class="headerlink" title="安装过程中遇到的问题"></a>安装过程中遇到的问题</h3><p><strong>1.  进行时第二步中出现，this host does not appear to have ang network interfaces </strong></p><p> 解决方案：Xenserver版本问题，更换新的Xenserver版本。（刚开始用的7.0，后来换的8.2  没有出现此问题）</p><p><strong>2.安装完之后出现界面不能加载，如下图问题</strong></p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201103171353241.png" alt="image-20201103171353241"></p><p>解决方案：rm -rf /etc/modules-load.d/，删除之后即可正常启动，具体原因是由于内核加载文件版本较旧，删除之后会更新内核加载文件</p><h2 id="XenCenter"><a href="#XenCenter" class="headerlink" title="XenCenter"></a>XenCenter</h2><h3 id="XenCenter-简介"><a href="#XenCenter-简介" class="headerlink" title="XenCenter 简介"></a>XenCenter 简介</h3><p>​    XenCenter是用来管理和维护XenServer主机的，创建、管理、删除虚拟机等几乎所有的操作都在XenCenter中完成</p><p>   简单来说XenCenter就是XenServer的管理工具</p><h3 id="XenCenter-安装"><a href="#XenCenter-安装" class="headerlink" title="XenCenter 安装"></a>XenCenter 安装</h3><ol><li>浏览器输入XenServer的Ip，得到以下Web页面</li></ol><p>   <img src="https://gitee.com/yhndbd/img/raw/master/image-20201103173403257.png" alt="image-20201103173403257"></p><ol start="2"><li>页面说明</li></ol><p>   <img src="https://gitee.com/yhndbd/img/raw/master/image-20201103175048374.png" alt="image-20201103173824818"></p><ol start="3"><li>点击Xencenter的下载链接进去下载然后进行安装</li></ol><h3 id="XenCenter安装过程中出现的问题及解决方法"><a href="#XenCenter安装过程中出现的问题及解决方法" class="headerlink" title="XenCenter安装过程中出现的问题及解决方法"></a>XenCenter安装过程中出现的问题及解决方法</h3><ol><li><p>windows的.Net版本过低，安装不了，如下图</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201103173824818.png" alt="image-20201103175048374"></p><p>解决方案：更新windows版本或更新.Net</p></li></ol><ol start="2"><li>XenCenter的版本要与XenServer版本对应，低版本的XenCenter不能连接高版本的XenServer主机。</li></ol><h2 id="利用XenCenter搭建虚拟机"><a href="#利用XenCenter搭建虚拟机" class="headerlink" title="利用XenCenter搭建虚拟机"></a>利用XenCenter搭建虚拟机</h2><h4 id="安装说明"><a href="#安装说明" class="headerlink" title="安装说明"></a>安装说明</h4><p>在XenServer安装虚拟机，和传统的操作系统安装不同的是，需要把镜像文件单独放在别的机器上可以以文件共享的方式也可以以NFS的方式，也可以在本地进行iso目录的挂载，然后去装虚拟机，本次使用的也是最后这种方式。</p><h4 id="安装步骤-1"><a href="#安装步骤-1" class="headerlink" title="安装步骤"></a>安装步骤</h4><ol><li><p>创建一个myiso文件夹来存放iso文件，mkdir  /myiso</p></li><li><p>执行<strong>xe sr-create name-label=iso type=iso device-config:location=/iso device-config:legacy_mode= true content-type=iso </strong> 命令 建立iso档型式的储存库(SR - Storage Repositories)，新增成功，上传那些iso文件档至主机的/iso即可。在XenCenter会出现一个项目    （如果没有出现对应的ISO光盘，在存储位置点击重新扫描即可。）</p></li><li><p>新建vm选择要安装的vm类型版本</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104154856611.png" alt="image-20201104154725972"></p></li><li><p>设置vm名称</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104154725972.png" alt="image-20201104154856611"></p></li><li><p>选择安装介质，选择我们之前上传到/myiso目录下的镜像</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104154951345.png" alt="image-20201104154951345"></p></li><li><p>选择主服务器</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104155041913.png" alt="image-20201104155041913"></p></li><li><p>配置服务器的cpu以及内存</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104155458408.png" alt="image-20201104155126246"></p></li><li><p>配置硬盘大小最大不能超过2T</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104155319201.png" alt="image-20201104155319201"></p></li><li><p>配置网络接口</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104155642039.png" alt="image-20201104155458408"></p></li><li><p>然后点击完成即可安装好了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104160857333.png" alt="image-20201104155642039"></p></li><li><p>然后进入正常的ubuntu安装界面，进行安装</p><h4 id="安装过程中出现的问题"><a href="#安装过程中出现的问题" class="headerlink" title="安装过程中出现的问题"></a>安装过程中出现的问题</h4></li><li><p>根目录大小，可以在重新挂载，默认200Gb，具体如图</p><p><img src="https://gitee.com/yhndbd/img/raw/master/image-20201104155126246.png" alt="image-20201104160857333"></p><p><strong>（如果安装时没有挂载可以，安装完成之后，用命令进行挂载）</strong></p></li></ol><ol start="2"><li><p>安装过程中，最后有个OPSSH安装，勾上，省的去手动安装</p></li><li><p>安装过程中，有个IP设置，默认是DHCP、也可以手动改为静态IP，（安装完可在/etc/netplan下的配置文件中更改）</p><p>Subnet  ： 192.168.3.0/24 </p><p>address： 192.168.3.32</p><p>gateway： 192.168.3.1</p><p>nameserver： 8.8.8.8</p></li></ol><h3 id="最后"><a href="#最后" class="headerlink" title="最后"></a>最后</h3><p>由于要进行多台安装，一台一台安装比较麻烦，可以进行vm复制进行快速安装</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;hr&gt;
&lt;h2 id=&quot;XenServer&quot;&gt;&lt;a href=&quot;#XenServer&quot; class=&quot;headerlink&quot; title=&quot;XenServer&quot;&gt;&lt;/a&gt;XenServer&lt;/h2&gt;&lt;hr&gt;
&lt;h3 id=&quot;XenServer简介&quot;&gt;&lt;a href=&quot;#XenS
      
    
    </summary>
    
      <category term="运维" scheme="http://www.windknew.com/blog/categories/%E8%BF%90%E7%BB%B4/"/>
    
    
      <category term="服务器" scheme="http://www.windknew.com/blog/tags/%E6%9C%8D%E5%8A%A1%E5%99%A8/"/>
    
      <category term="运维" scheme="http://www.windknew.com/blog/tags/%E8%BF%90%E7%BB%B4/"/>
    
  </entry>
  
  <entry>
    <title>零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（二）</title>
    <link href="http://www.windknew.com/%E9%9B%B6%E5%9F%BA%E7%A1%80%E5%AE%8C%E6%88%90%E7%8F%8D%E7%88%B1%E7%BD%91%E9%A1%B9%E7%9B%AE%20Java+MySQL+echarts%20%20%20%20%20%EF%BC%88ZhenaiSpider+ZhenaiWeb%EF%BC%89%EF%BC%88%E4%BA%8C%EF%BC%89/"/>
    <id>http://www.windknew.com/零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（二）/</id>
    <published>2020-11-04T09:52:56.000Z</published>
    <updated>2020-11-04T09:07:55.222Z</updated>
    
    <content type="html"><![CDATA[<p>如期而至，继续我们的项目，上次我们配置好了我们的环境  今天呢，我们开始创建我们的项目。</p><p>首先 ，启动Eclipse dian点file 创建yi’g一个新的maven项目</p><p><img src="https://img-blog.csdn.net/20180716164142179?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>注意创建的时候，要钩选这个，而且默认的创建项目的位置是你当初设置的位置，如果你想更改，点击browse 即可更改，在这里呢我选择默认的路径，ran’然后点击next</p><p><img src="https://img-blog.csdn.net/20180716164518727?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动">、</p><p>这里的groupid和artifactId被统称为“坐标”是为了保证项目唯一性而提出的，如果你要把你项目弄到maven本地仓库去，你想要找到你的项目就必须根据这两个id去查找。<br>　　groupId一般分为多个段，这里我只说两段，第一段为域，第二段为公司名称。域又分为org、com、cn等等许多，其中org为非营利组织，com为商业组织。举个apache公司的tomcat项目例子：这个项目的groupId是org.apache，它的域是org（因为tomcat是非营利项目），公司名称是apache，artigactId是tomcat。<br>　　比如我创建一个项目，我一般会将groupId设置为cn.lyh，cn表示域为中国，lyh是我个人姓名缩写，artifactId设置为ZhenaiSpider，表示你这个项目的名称是ZhenaiSpider，依照这个设置，你的包结构最好是cn.lyh.ZhenaiSpider打头的，如果有个包叫single，它的全路径就是cn.lyh.ZhenaiSpider.single</p><p>设置完成之后我们的maven项目就算搭建好了 ，接下来我们会看到一个pom.xml 文件，打开之后是这样的</p><p><img src="https://img-blog.csdn.net/20180716170256828?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>我们需要去<a href="http://mvnrepository.com/" target="_blank" rel="noopener">http://mvnrepository.com/</a> 这个网站去找我们所需要的依赖 我们不会一次性导入所有依赖 只有在需要的时候才会去导入，</p><p>接下来呢 我们要用到的技术是HTTP 协议+爬虫(jsoup - HTML) 当然了  为了提高效率我们用的是多线程去爬取数据（关于Java的多线程 可参考其他帖子，这里就不一一赘述了）</p><p><strong>关于Http协议：</strong></p><p> HTTP协议其实就是用来定义Web客户端如何从Web服务器请求Web页面，以及服务器如何把Web页面传送给客户端。HTTP协议采用了请求/响应模型。客户端向服务器发送一个请求报文，请求报文包含请求的方法、URL、协议版本、请求头部和请求数据。服务器以一个状态行作为响应，响应的内容包括协议的版本、成功或者错误代码、服务器信息、响应头部和响应数据。</p><p><strong>简单的来说</strong> 在浏览器地址栏键入URL，点击链接之后会经历以下流程</p><p>1、浏览器向 DNS 服务器请求解析该 URL 中的域名所对应的 IP 地址;</p><p>2、解析出 IP 地址后，根据该 IP 地址和默认端口 80，和服务器建立<a href="http://www.jianshu.com/p/ef892323e68f" target="_blank" rel="noopener">TCP连接</a>;</p><p>3、浏览器发出读取文件(URL 中域名后面部分对应的文件)的HTTP 请求，该请求报文作为 <a href="http://www.jianshu.com/p/ef892323e68f" target="_blank" rel="noopener">TCP 三次握手</a>的第三个报文的数据发送给服务器;</p><p>4、服务器对浏览器请求作出响应，并把对应的 html 文本发送给浏览器;</p><p>5、释放 <a href="http://www.jianshu.com/p/ef892323e68f" target="_blank" rel="noopener">TCP连接</a>;</p><p>6、浏览器将该 html 文本并显示内容; 　</p><h1 id="Jsoup-："><a href="#Jsoup-：" class="headerlink" title="Jsoup　："></a><strong>Jsoup　：</strong></h1><p>所谓的爬虫，简单的来说 一个网页 ，就是一个文本文件，所谓的爬虫就是一个利用解析器，把我们所需要的信息从网页中拿出来 并把这些信息保存到本地 或者写到数据库里。而jsoup就是Java的 一个强大的Html解析器，它可直接解析某个URL地址、HTML文本内容。它提供了一套非常省力的API，可通过DOM，CSS以及类似于jQuery的操作方法来取出和操作数据。而我们可以去打开浏览器，而在我们的项目中要用到jsoup  我们需要去找依赖并下载下来，打开网站搜索jsoup</p><p><img src="https://img-blog.csdn.net/20180716174857905?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>第一个就是 然后我用的是最新的1.11.3 </p><p><img src="https://img-blog.csdn.net/20180716175020981?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>点击你所需要的版本 </p><p><img src="https://img-blog.csdn.net/20180716175311979?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180716175915369?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><h1 id="分析url："><a href="#分析url：" class="headerlink" title="分析url："></a><strong>分析url：</strong></h1><p> 通过分析，其实我们可以发现，每个网站的url 都是有规律的 ，如图</p><p><img src="https://img-blog.csdn.net/20180716183414703?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后我们用 Java去模拟 去请求</p><p><img src="https://img-blog.csdn.net/2018071619105428?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>请求完成之后，剩下的工作就是通过返回的字符串来进行对文本的解析</p><p>这时候我们就要通过强大的jsoup去进行解析</p><p>首先我们要知道 在浏览器中 我们是可以看到网页的源码的，在浏览器中按f12 即可进入  或者直接鼠标右键 会出来查看源代码，但推荐用前者</p><p><img src="https://img-blog.csdn.net/20180716192525382?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>例如：</p><p><img src="https://img-blog.csdn.net/20180716192644885?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>我们要通过网页的源代码去拿wo’m我么所需要的数据，比如性别，是否结过婚，年龄，是否购车，是否有房，学历情况，收入等等一系列信息</p><p><img src="https://img-blog.csdn.net/20180716193811554?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>我们从网页源码中可以发现 id 是放在这儿的  ，然后我们 用 select 方法 拿出 ID 然后在用.text() 方法拿到值  这样我们就 获取到了这个用户的id ，利用此方法我们可以拿到这个页面的任何信息</p><p>下面这个截图只是个参考 大家要去自己分析看看 是不是这样，试试自己是否能够分析出来想要的结果</p><p>这样我们的的爬虫基本上就结束了，下次我将会wei为大家分享 如何将获取到的的数据保存到Mysql 数据库中 然后为大家介绍制做报表的神器Echarts 本次分享就先到这儿，若文中有什么不足的地方希望大家可以在评论区进行指点。大家可以加关注，继续看我下次的分享哦</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;p&gt;如期而至，继续我们的项目，上次我们配置好了我们的环境  今天呢，我们开始创建我们的项目。&lt;/p&gt;
&lt;p&gt;首先 ，启动Eclipse dian点file 创建yi’g一个新的maven项目&lt;/p&gt;
&lt;p&gt;&lt;img src=&quot;https://img-blog.csdn.net/
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="教程" scheme="http://www.windknew.com/blog/tags/%E6%95%99%E7%A8%8B/"/>
    
  </entry>
  
  <entry>
    <title>零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（三）</title>
    <link href="http://www.windknew.com/%E9%9B%B6%E5%9F%BA%E7%A1%80%E5%AE%8C%E6%88%90%E7%8F%8D%E7%88%B1%E7%BD%91%E9%A1%B9%E7%9B%AE%20Java+MySQL+echarts%20%20%20%20%20%EF%BC%88ZhenaiSpider+ZhenaiWeb%EF%BC%89%EF%BC%88%E4%B8%89%EF%BC%89/"/>
    <id>http://www.windknew.com/零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（三）/</id>
    <published>2020-11-04T09:52:56.000Z</published>
    <updated>2020-11-04T09:15:00.190Z</updated>
    
    <content type="html"><![CDATA[<p>继续我们的项目， 上次之后我们基本上完成了数据的获取（即爬虫），接下来呢就是如何去保存这些数据，有两种方式，一种呢是以文本形式保存到本地，第二种是就是保存到数据库，而我们呢选择后者。</p><h1 id="Mysql"><a href="#Mysql" class="headerlink" title="Mysql"></a><strong>Mysql</strong></h1><p>1，第一当然还是先下载了，进入网站即可选择相应的版本<a href="https://dev.mysql.com/downloads/file/?id=476696" target="_blank" rel="noopener">https://dev.mysql.com/downloads/file/?id=476696</a></p><p>2.我们这里是5.7.22,打开网址，翻到最下面，点击如下，直接下载就好</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717103129351" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，解压，进行初始化数据库</p><p>在bin目录下，执行以下的命令来初始化数据库（cmd下）：</p><p>D:\b\mysql-5.7.21-winx64\bin&gt;mysqld –initialize，</p><p>获取初始化以后的用户名root,和密码：</p><p>然后你会发现解压的目录下，多了一个叫data的文件夹</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717103509819" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>打开之后，有一个后缀为err的文件，用notepade++ 打开  或者记事本也可以</p><p>，<img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717103709671" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>在这个文件的最后，每个人的不一样 但localhost：  后面的就是你的密码</p><p>4，接下来呢，测试启动mysql  </p><p>在解压目录下的bin目录下 输入以下指令mysqld –console</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104033568" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104048648" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>如果显示如图信息，就证明你安装成功了。切记不要关闭这个窗口。</p><p>5，登陆</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104220705" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>密码就是刚才那个文件夹里的那个，但你会发现在这个密码下什么都做不了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104311575" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>修改密码：输入以下指令即可修改密码，如下1234就是我所修改之后的密码，</p><p>mysql&gt; set password=password(‘1234’);</p><p>显示以下信息就代表修改成功了</p><p>Query OK, 0 rows affected, 1 warning (0.00 sec)</p><p>修改完成之后，我们再执行 show tables  jiu’就会发现可以执行了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104602984" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>显示的这些信息都是你所包含的表</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104651619" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>6，方便起见，我们将mysql 安装成windows服务，在bin目录下，执行如下指令即可完成安装</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104808813" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>接下来呢我们配置环境变量，这样我们就可以在cmd中启动mysql了</p><p>在path 下添加到mysql的bin，如下图</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717105038715" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后打开cmd 输入  net start mysql  即可启动mysql(要注意在执行之前我们要关掉之前测试启动mysql的那个窗口)</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717105203308" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>当然了 停止mysql 的命令是 net stop mysql</p><p>7，再登陆</p><p>-u用户名 -p</p><p>对于本机来说：</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717105600496" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>你可以设置远程登陆，即在别人的机器上也可以登录你的数据库，具体设置方法如下</p><p>1.先查看一下你的用户列表</p><p><img src="https://img-blog.csdn.net/2018071710581066?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>你会发现  在root 那栏 只有localhost  即代表只有本机才可以登陆，接下来呢将localhosthuan换成% 这样就可以实现远程登陆了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717110031377" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>到这里呢我们的mysql 基本上就设置好了</p><p>接下来呢我们去xia项目中添加mysql的依赖</p><dependency><br><br>​      <groupid>mysql</groupid><br><br>​      <artifactid>mysql-connector-java</artifactid><br><br>​      <version>5.1.46</version><br><br>​    </dependency><p>关于mysql的语句，我们在这里简单地说几个</p><p>1.创建数据库，后面的 character set utf8  是设置 数据库的编码方式 为utf8 （一般都会是utf8 ）</p><p><img src="https://img-blog.csdn.net/2018071711063926?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>2，进入这个数据库</p><p><img src="https://img-blog.csdn.net/2018071711081921?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，创建一个表</p><p><img src="https://img-blog.csdn.net/20180717111106521?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，查看数据库下的表</p><p><img src="https://img-blog.csdn.net/20180717111135388?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>这时会发现 我们刚才创建的表就出现了</p><p>4，向表中写数据</p><p><img src="https://img-blog.csdn.net/20180717111230105?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>基本操作就这些 其他操作，如删除表，删除字段等等 可自行百度查阅</p><p>接下来呢，我们用java语句去操作数据库，即jdbc，关于jdbc 给大家一个lian链接 感觉写的挺不错，这里就不赘述了</p><p><a href="https://www.cnblogs.com/wuyuegb2312/p/3872607.html" target="_blank" rel="noopener">https://www.cnblogs.com/wuyuegb2312/p/3872607.html</a></p><p>这里我们使用DButils操作数据库。使用 c3p0做连接池，之所以使用连接池是因为每次操作数据库，都重新创建一个连接。Connection 使用连接池：保证连接的重用，回收连接。</p><p>接下来呢，我么要做的就是要添加，c3p0的依赖，</p><p><a href="https://mvnrepository.com/" target="_blank" rel="noopener">https://mvnrepository.com/</a> 然后搜索c3p0 找到相应的依赖，然后拷贝到我们的pom.xml 文件夹下 即可自动下载依赖</p><p>​    <dependency></dependency></p><p>​      <groupid>com.mchange</groupid></p><p>​      <artifactid>c3p0</artifactid></p><p>​      <version>0.9.5.2</version></p><p>​    </p><p>然后添加c3p0的配置文件 c3p0p-config.xml</p><p>&lt;?xml version=<em>“1.0”</em> encoding=<em>“UTF-8”</em>?&gt;</p><p><c3p0-config></c3p0-config></p>  <!-- 默认的配置 --><p>  <default-config></default-config></p><p>&lt;propertyname=<em>“jdbcUrl”</em>&gt;jdbc:mysql:///hyxy?characterEncoding=UTF8&amp;useUnicode=true&amp;useSSL=false</p><p>​    &lt;property name=<em>“driverClass”</em>&gt;com.mysql.jdbc.Driver</p><p>​    &lt;property name=<em>“user”</em>&gt;root</p><p>​    &lt;property name=<em>“password”</em>&gt;1234</p><p>​    <!--连接数据库的超时时间 --></p><p>​    &lt;property name=<em>“checkoutTimeout”</em>&gt;3000</p><p>​    <!--里面默认的初始化连接个数 --></p><p>​    &lt;property name=<em>“initialPoolSize”</em>&gt;3</p><p>​    <!-- 最多有多少连接 --></p><p>​    &lt;property name=<em>“maxPoolSize”</em>&gt;10</p><p>​    &lt;property name=<em>“minPoolSize”</em>&gt;3</p><p>​    <!--一次批量处理，最多可以执行多少SQL语句,默认是50,50~200是一个合理的范围 --></p><p>​    &lt;property name=<em>“maxStatements”</em>&gt;200</p><p>  </p><p></p><h2 id="创建一个连接池，通过读取上面的配置文件"><a href="#创建一个连接池，通过读取上面的配置文件" class="headerlink" title="创建一个连接池，通过读取上面的配置文件"></a>创建一个连接池，通过读取上面的配置文件</h2><p>package cn.hyxy.zhenai.util;<br>import javax.sql.DataSource;<br>import com.mchange.v2.c3p0.ComboPooledDataSource;<br>public class DSUtils {<br>   //1:声明dataSour e<br>   private static DataSource DATASOURCE;<br>   //2:开发一个静态的代码块，只执行一次<br>   static {<br>     DATASOURCE = new ComboPooledDataSource();<br>   }<br>   //3:获取Da<br>   public static DataSource getDataSource() {<br>     return DATASOURCE;<br>   }<br>}</p><h2 id="使用dbutils"><a href="#使用dbutils" class="headerlink" title="使用dbutils"></a>使用dbutils</h2><p>导入dbutils的依赖</p><dependency><p>​      <groupid>commons-dbutils</groupid></p><p>​      <artifactid>commons-dbutils</artifactid></p><p>​      <version>1.7</version></p><p>​    </p></dependency><br><strong>然后呢我们就要根据我们所获取数据的结构，制做mysql的表</strong><p></p><p><img src="https://img-blog.csdn.net/20180717113408420?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><strong>我们来设计我们的表格</strong></p><p>输入指令 ，来创建这个表格</p><p>CREATE TABLE dogs(</p><p>  id BIGINT,</p><p>  NAME VARCHAR(50),</p><p>  age INT,</p><p>  workaddr VARCHAR(20),</p><p>  height INT,</p><p>  salary VARCHAR(30),</p><p>  homeaddr VARCHAR(30),</p><p>  married VARCHAR(10),</p><p>  grade VARCHAR(10),</p><p>  worker VARCHAR(20),</p><p>  house VARCHAR(10),</p><p>  car VARCHAR(10),</p><p>  sex VARCHAR(10)</p><p>);</p><p>然后我们利用程序 将爬取的数据写入到数据库，为了更可观的查看我们爬取的数据，我们可以利用数据库管理和开发工具</p><p>例如navicat premium</p><p>将数据写入到数据库中，在spider 中写一个方法 ，传入我们所获取的信息，利用这个方法将我们传进的信息，写入到数据库中</p><p>   public void insert(String sql, String id, String name,String sex, String age, String workaddr, String height, String salary,<br>       String homeaddr, String married, String grade, String worker, String house, String car) throws Exception {<br>     QueryRunner run = new QueryRunner(DSUtils.getDataSource());<br>     run.update(sql, id, name,sex, age, workaddr, height, salary, homeaddr, married, grade, worker, house, car);<br>   }</p><p>这样呢我们就成功将我们获取的信息写入到我们的数据库了 然后将spider 跑起来 其获取信息</p><p><img src="https://img-blog.csdn.net/20180717115454166?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>我们的爬虫到这儿 就完成了，下次我们就要利用这些数据做成报表，使信息更可观的表现如下图</p><p><img src="https://img-blog.csdn.net/20180717115737652?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115811176?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115838418?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115910128?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115929933?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>诸如此类，大家可自行设计不同的报表类型，明天再和大家继续分享，文中若有不足，欢迎大家的指正。</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;p&gt;继续我们的项目， 上次之后我们基本上完成了数据的获取（即爬虫），接下来呢就是如何去保存这些数据，有两种方式，一种呢是以文本形式保存到本地，第二种是就是保存到数据库，而我们呢选择后者。&lt;/p&gt;
&lt;h1 id=&quot;Mysql&quot;&gt;&lt;a href=&quot;#Mysql&quot; class=&quot;he
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="教程" scheme="http://www.windknew.com/blog/tags/%E6%95%99%E7%A8%8B/"/>
    
  </entry>
  
  <entry>
    <title>零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（一）</title>
    <link href="http://www.windknew.com/%E9%9B%B6%E5%9F%BA%E7%A1%80%E5%AE%8C%E6%88%90%E7%8F%8D%E7%88%B1%E7%BD%91%E9%A1%B9%E7%9B%AE%20Java+MySQL+echarts%20%20%20%20%20%EF%BC%88ZhenaiSpider+ZhenaiWeb%EF%BC%89%EF%BC%88%E4%B8%80%EF%BC%89/"/>
    <id>http://www.windknew.com/零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（一）/</id>
    <published>2020-11-04T09:52:56.000Z</published>
    <updated>2020-11-04T09:08:02.932Z</updated>
    
    <content type="html"><![CDATA[<p><strong>这个项目呢 主要分为两个部分 爬虫（Spider）和Web两方面(web主要是进行数据分析做出报表是数据更可观)</strong></p><p><strong>一、  进行jdk安装及环境变量的配置</strong></p><p>由于是基于java的项目 所以先进行jdk的相关安装及配置：</p><p>1，本次使用的是jdk1.8（当然了 也可以使用其他的版本）</p><p><a href="http://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html" target="_blank" rel="noopener">http://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html</a></p><p>进入这个地址即可进行相应的下载</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716133314886" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>2，下载完成之后进行解压，解压到一个没有中文和空格路径的目录下</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716133723280" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，配置环境变量</p><p>   打开我的电脑 右键属性找到高级设置，右下角有环境变量打开即可进行设置， </p><p>   在系统变量 点击新建 然后输入变量名以及变量值</p><p>   变量名： JAVA_HOME</p><p>​    变量值 ：JDK的解压目录</p><p>   例如<img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716134951265" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后找到系统变量中的path 双击打开 然后右侧栏点击新建 然后再点击浏览找到jdk目录下的bin目录</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716135408906" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>如图这样 就已经完成了</p><p>然后点击确定  应用 即可</p><p>然后验证是否安装成功按住win+r  然后输入cmd 进入命令行 输入java -version 如果如图显示 就证明你就已经配置成功了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716135938480" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><h2 id="二-、下载IDE-集成开发环境）-（这里我用的是Eclipse"><a href="#二-、下载IDE-集成开发环境）-（这里我用的是Eclipse" class="headerlink" title="二 、下载IDE(集成开发环境） （这里我用的是Eclipse)"></a><strong>二 、下载IDE(集成开发环境）</strong> （这里我用的是Eclipse)</h2><p>1，下载Eclipse</p><p>进入官网即可下载<a href="http://www.eclipse.org/downloads/" target="_blank" rel="noopener">http://www.eclipse.org/downloads/</a></p><p>我这里下载的是Mars 版本  但要注意的是 要下载ee 不要下载se</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716140523392" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后解压并启动</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716140633590" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>这个是让你选择工作空间 ，选择以后你的所有的项目都会保存在这个文件夹下</p><p>2，打开以后进行基本的配置</p><p>在菜单栏上有个Windows  点开 然后点击preference 输入work 点击workspqce 将编码方式设置为UTF-8</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716141142956" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>进行到这里以后我们就可以写出一个基本的Java程序了 但我们的spider是基于maven的所以我们还要进行配置maven依赖工具</p><p><strong>三、 创建maven 依赖工具</strong> </p><p>1，下载 解压<a href="http://mirrors.shu.edu.cn/apache/maven/maven-3/3.5.4/binaries/apache-maven-3.5.4-bin.zip" target="_blank" rel="noopener">http://mirrors.shu.edu.cn/apache/maven/maven-3/3.5.4/binaries/apache-maven-3.5.4-bin.zip</a></p><p>点击 即可进入官网下载</p><p><img src="https://img-blog.csdn.net/20180716141625633?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>2，配置环境变量 和上面类似</p><p>M2_HOME = 解压目录</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716141856436" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>在path下新建然后浏览 找到解压目录下的bin</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716142003348" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后打开命令行进行验证看是否成功  输入mvn -v 若显示如下 则成功</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180716142210136" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>2，配置maven</p><p>Mave会从中心仓库下载所需要的依赖包，放到本地（由于服务器在国外 下载过程可能会较慢）</p><p>找到解压目录下的config 文件夹 打开 然后打开里面的settings.xml文件，然后将它放到你的c盘user文件夹下的你的用户名的.m2的文件夹下  例如C:/user/wangjian/.m2/settings.xml （若没有.m2 文件夹 请创建 此时要用命令行来创建，打开cmd 然后输入mkdir .m2 然后文件夹就创建好了）</p><p>然后用notepad++ 打开这个settings.xml文件 并修改参数  如图 （notapade++ 百度即可找到 或者其他工具打开也可以 ）</p><p><img src="https://img-blog.csdn.net/20180716143626979?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>刚开始是这样的 然后修改如下：那个黑字部分 就是下载的依赖所保存的地方 黑字部分是路径  你要自己设置你自己的哦！</p><p><img src="https://img-blog.csdn.net/20180716143336251?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后呢我们就在Eclipse 中集成maven</p><p>还是菜单栏的Windows下的 Preferences 然后如图 输入maven </p><p><img src="https://img-blog.csdn.net/20180716144620153?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>到这里基本上就配置成功了，加关注，明天继续分享哦！</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;p&gt;&lt;strong&gt;这个项目呢 主要分为两个部分 爬虫（Spider）和Web两方面(web主要是进行数据分析做出报表是数据更可观)&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;&lt;strong&gt;一、  进行jdk安装及环境变量的配置&lt;/strong&gt;&lt;/p&gt;
&lt;p&gt;由于是基于java的项目
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="教程" scheme="http://www.windknew.com/blog/tags/%E6%95%99%E7%A8%8B/"/>
    
  </entry>
  
  <entry>
    <title>零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（五）</title>
    <link href="http://www.windknew.com/%E9%9B%B6%E5%9F%BA%E7%A1%80%E5%AE%8C%E6%88%90%E7%8F%8D%E7%88%B1%E7%BD%91%E9%A1%B9%E7%9B%AE%20Java+MySQL+echarts%20%20%20%20%20%EF%BC%88ZhenaiSpider+ZhenaiWeb%EF%BC%89%EF%BC%88%E4%BA%94%EF%BC%89/"/>
    <id>http://www.windknew.com/零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（五）/</id>
    <published>2020-11-04T09:52:56.000Z</published>
    <updated>2020-11-04T09:08:18.736Z</updated>
    
    <content type="html"><![CDATA[<h3 id="全国的单身人士的分布-进行报表分析"><a href="#全国的单身人士的分布-进行报表分析" class="headerlink" title="全国的单身人士的分布 进行报表分析"></a><strong>全国的单身人士的分布 进行报表分析</strong></h3><p>首先要导入地图的js包 我放到了 百度网盘上 大家下载下来之后 解压放到assert文件夹下 即可 </p><p><a href="https://pan.baidu.com/s/1TPB7pzewfg43MXaiw24I8g" target="_blank" rel="noopener">https://pan.baidu.com/s/1TPB7pzewfg43MXaiw24I8g</a></p><p>然后获取数据， 由于全国省份较多 我们可以百度，如图</p><p><img src="https://img-blog.csdn.net/20180718112156382?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后拷贝 到一个新建的txt文件夹下（我在这儿是a.txt） 然后将所有的中文 逗号换成英文的 </p><p>然后在这个目录下打开命令行执行native2ascii a.txt b.txt 然后将 b.txt文件里的内容全选 新建 如下图所示的文件夹</p><p><img src="https://img-blog.csdn.net/20180718112622958?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后如图 写入china = 然后将b里的内容拷贝到等号的后面</p><p>然后获取数据 将数据导入地图 就大功告成了（是不是有点不可思议呢^_^）</p><p>public List&lt;Map&lt;String, Object&gt;&gt; queryChina() {<br>     List&lt;Map&lt;String, Object&gt;&gt; list = new ArrayList&lt;&gt;();<br>     // 读取所有的省信息<br>     Properties prop = new Properties();<br>     try {<br>       prop.load(ZhenaiDao.class.getClassLoader().getResourceAsStream(“zhenai.properties”));<br>       String china = prop.getProperty(“china”);<br>       String[] privs = china.split(“,”);<br>       QueryRunner run = new QueryRunner(ds);<br>       String sql = “select count(1) from dogs where homeaddr like ?”;<br>       for(String priv:privs) {<br>         int cnt = run.query(sql, new ScalarHandler<long>(),priv+”%”).intValue();<br>         Map&lt;String, Object&gt; map = new HashMap&lt;&gt;();<br>         map.put(“name”, priv);<br>         map.put(“value”, cnt);<br>         //放到<br>         list.add(map);<br>       }<br>     } catch (Exception e) {<br>       e.printStackTrace();<br>     }<br>     return list;</long></p><p>&lt;%@ page language=”java” contentType=”text/html; charset=UTF-8”    pageEncoding=”UTF-8”%&gt;&lt;%@ taglib uri=”<a href="http://java.sun.com/jsp/jstl/core&quot;" target="_blank" rel="noopener">http://java.sun.com/jsp/jstl/core&quot;</a> prefix=”c”%&gt;&lt;!DOCTYPE html&gt;<html><head><meta name="generator" content="Hexo 3.9.0"><meta charset="UTF-8"><title>Insert title here</title><link rel="stylesheet" type="text/css" href="<c:url value='/assert/bootstrap/css/bootstrap.css'/>"><script type="text/javascript" src="<c:url value='/assert/jquery-3.2.1.min.js'/>"></script><script type="text/javascript" src="<c:url value='/assert/echarts.min.js'/>"></script><script type="text/javascript" src="<c:url value='/assert/bootstrap/js/bootstrap.min.js'/>"></script><script type="text/javascript" src="<c:url value='/assert/map/js/china.js'/>"></script></head><body>    <div class="container">        <div class="row">            <div class="col-md-12">                <div class="card">                    <div class="card-header bg-primary text-white">                        全国分布图                    </div>                    <div class="card-body">                        <div id="data1" style="height: 600px"></div>                    </div>                </div>            </div>        </div>    </div></body><script type="text/javascript">    var chart = echarts.init(document.getElementById(“data1”));    //声明数据    //初始化地图的选项option    var option = {        backgroundColor : ‘#FFFFFF’,        title : {            text : ‘全国单身人士分布图’,            subtext : ‘数据来自珍爱网’,            x : ‘center’        },        tooltip : {            trigger : ‘item’        },        visualMap : { //用于指定分割值            show : true,            x : ‘left’,            y : ‘top’,            splitList : [ {                start : 701,                end : 5999            }, {                start : 601,                end : 701            }, {                start : 301,                end : 600            }, {                start : 101,                end : 300            }, {                start : 0,                end : 100            }],            color : [ ‘#DC143C’, ‘#DA70D6’, ‘#6495ED’, ‘#00FF7F’, ‘#33CC00’ ]        //这儿用于指定颜色        },        series : [ {            name : ‘单身人士’,            type : ‘map’,//使用地址，显示的结果是地图            mapType : ‘china’, //如果是其他省请引用不同的省js文件，然后输入：山东            roam : true,            data :[],            label : {                show : true,                formatter : function(data) {                    return data.value + “人”;                }            }        } ]    };    chart.setOption(option);</p><pre><code>$.get(&quot;&lt;c:url value=&apos;/china&apos;/&gt;&quot;).done(function(dd){  var ds = eval(&quot;(&quot;+dd+&quot;)&quot;);  var option = {      series : [{        data:ds      }]  };  chart.setOption(option);});</code></pre><p></script><br></html></p><p>效果如图示</p><p><img src="https://img-blog.csdn.net/20180718112949999?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>这样呢我们的项目就大功告成了，我也会将整个项目打包供大家下载参考，关于优化spider的项目代码我也会打包供大家参考</p><p>链接：<a href="https://pan.baidu.com/s/1qFzq7Qa_MEbXbhLHBRokMQ" target="_blank" rel="noopener">https://pan.baidu.com/s/1qFzq7Qa_MEbXbhLHBRokMQ</a> 密码：7efk  (zhenaiweb)</p><p>链接：<a href="https://pan.baidu.com/s/1Ty7m8aV5BArukppMEuIyYg" target="_blank" rel="noopener">https://pan.baidu.com/s/1Ty7m8aV5BArukppMEuIyYg</a> 密码：vysq  （zhenaispider  未优化）</p><p>已优化的 在我的在我的下载资源里有 大家可以去下载参考</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h3 id=&quot;全国的单身人士的分布-进行报表分析&quot;&gt;&lt;a href=&quot;#全国的单身人士的分布-进行报表分析&quot; class=&quot;headerlink&quot; title=&quot;全国的单身人士的分布 进行报表分析&quot;&gt;&lt;/a&gt;&lt;strong&gt;全国的单身人士的分布 进行报表分析&lt;/strong&gt;&lt;
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="教程" scheme="http://www.windknew.com/blog/tags/%E6%95%99%E7%A8%8B/"/>
    
  </entry>
  
  <entry>
    <title>零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（四）</title>
    <link href="http://www.windknew.com/%E9%9B%B6%E5%9F%BA%E7%A1%80%E5%AE%8C%E6%88%90%E7%8F%8D%E7%88%B1%E7%BD%91%E9%A1%B9%E7%9B%AE%20Java+MySQL+echarts%20%20%20%20%20%EF%BC%88ZhenaiSpider+ZhenaiWeb%EF%BC%89%EF%BC%88%E5%9B%9B%EF%BC%89/"/>
    <id>http://www.windknew.com/零基础完成珍爱网项目 Java+MySQL+echarts     （ZhenaiSpider+ZhenaiWeb）（四）/</id>
    <published>2020-11-04T09:52:56.000Z</published>
    <updated>2020-11-04T09:15:43.418Z</updated>
    
    <content type="html"><![CDATA[<p>继续我们的项目， 上次之后我们基本上完成了数据的获取（即爬虫），接下来呢就是如何去保存这些数据，有两种方式，一种呢是以文本形式保存到本地，第二种是就是保存到数据库，而我们呢选择后者。</p><h1 id="Mysql"><a href="#Mysql" class="headerlink" title="Mysql"></a><strong>Mysql</strong></h1><p>1，第一当然还是先下载了，进入网站即可选择相应的版本<a href="https://dev.mysql.com/downloads/file/?id=476696" target="_blank" rel="noopener">https://dev.mysql.com/downloads/file/?id=476696</a></p><p>2.我们这里是5.7.22,打开网址，翻到最下面，点击如下，直接下载就好</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717103129351" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，解压，进行初始化数据库</p><p>在bin目录下，执行以下的命令来初始化数据库（cmd下）：</p><p>D:\b\mysql-5.7.21-winx64\bin&gt;mysqld –initialize，</p><p>获取初始化以后的用户名root,和密码：</p><p>然后你会发现解压的目录下，多了一个叫data的文件夹</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717103509819" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>打开之后，有一个后缀为err的文件，用notepade++ 打开  或者记事本也可以</p><p>，<img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717103709671" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>在这个文件的最后，每个人的不一样 但localhost：  后面的就是你的密码</p><p>4，接下来呢，测试启动mysql  </p><p>在解压目录下的bin目录下 输入以下指令mysqld –console</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104033568" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104048648" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>如果显示如图信息，就证明你安装成功了。切记不要关闭这个窗口。</p><p>5，登陆</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104220705" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>密码就是刚才那个文件夹里的那个，但你会发现在这个密码下什么都做不了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104311575" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>修改密码：输入以下指令即可修改密码，如下1234就是我所修改之后的密码，</p><p>mysql&gt; set password=password(‘1234’);</p><p>显示以下信息就代表修改成功了</p><p>Query OK, 0 rows affected, 1 warning (0.00 sec)</p><p>修改完成之后，我们再执行 show tables  jiu’就会发现可以执行了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104602984" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>显示的这些信息都是你所包含的表</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104651619" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>6，方便起见，我们将mysql 安装成windows服务，在bin目录下，执行如下指令即可完成安装</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717104808813" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>接下来呢我们配置环境变量，这样我们就可以在cmd中启动mysql了</p><p>在path 下添加到mysql的bin，如下图</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717105038715" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>然后打开cmd 输入  net start mysql  即可启动mysql(要注意在执行之前我们要关掉之前测试启动mysql的那个窗口)</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717105203308" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>当然了 停止mysql 的命令是 net stop mysql</p><p>7，再登陆</p><p>-u用户名 -p</p><p>对于本机来说：</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717105600496" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>你可以设置远程登陆，即在别人的机器上也可以登录你的数据库，具体设置方法如下</p><p>1.先查看一下你的用户列表</p><p><img src="https://img-blog.csdn.net/2018071710581066?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>你会发现  在root 那栏 只有localhost  即代表只有本机才可以登陆，接下来呢将localhosthuan换成% 这样就可以实现远程登陆了</p><p><img src="https://gitee.com/yhndbd/img/raw/master/2020/20180717110031377" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>到这里呢我们的mysql 基本上就设置好了</p><p>接下来呢我们去xia项目中添加mysql的依赖</p><dependency><br><br>​      <groupid>mysql</groupid><br><br>​      <artifactid>mysql-connector-java</artifactid><br><br>​      <version>5.1.46</version><br><br>​    </dependency><p>关于mysql的语句，我们在这里简单地说几个</p><p>1.创建数据库，后面的 character set utf8  是设置 数据库的编码方式 为utf8 （一般都会是utf8 ）</p><p><img src="https://img-blog.csdn.net/2018071711063926?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>2，进入这个数据库</p><p><img src="https://img-blog.csdn.net/2018071711081921?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，创建一个表</p><p><img src="https://img-blog.csdn.net/20180717111106521?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>3，查看数据库下的表</p><p><img src="https://img-blog.csdn.net/20180717111135388?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>这时会发现 我们刚才创建的表就出现了</p><p>4，向表中写数据</p><p><img src="https://img-blog.csdn.net/20180717111230105?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>基本操作就这些 其他操作，如删除表，删除字段等等 可自行百度查阅</p><p>接下来呢，我们用java语句去操作数据库，即jdbc，关于jdbc 给大家一个lian链接 感觉写的挺不错，这里就不赘述了</p><p><a href="https://www.cnblogs.com/wuyuegb2312/p/3872607.html" target="_blank" rel="noopener">https://www.cnblogs.com/wuyuegb2312/p/3872607.html</a></p><p>这里我们使用DButils操作数据库。使用 c3p0做连接池，之所以使用连接池是因为每次操作数据库，都重新创建一个连接。Connection 使用连接池：保证连接的重用，回收连接。</p><p>接下来呢，我么要做的就是要添加，c3p0的依赖，</p><p><a href="https://mvnrepository.com/" target="_blank" rel="noopener">https://mvnrepository.com/</a> 然后搜索c3p0 找到相应的依赖，然后拷贝到我们的pom.xml 文件夹下 即可自动下载依赖</p><p>​    <dependency></dependency></p><p>​      <groupid>com.mchange</groupid></p><p>​      <artifactid>c3p0</artifactid></p><p>​      <version>0.9.5.2</version></p><p>​    </p><p>然后添加c3p0的配置文件 c3p0p-config.xml</p><p>&lt;?xml version=<em>“1.0”</em> encoding=<em>“UTF-8”</em>?&gt;</p><p><c3p0-config></c3p0-config></p>  <!-- 默认的配置 --><p>  <default-config></default-config></p><p>&lt;propertyname=<em>“jdbcUrl”</em>&gt;jdbc:mysql:///hyxy?characterEncoding=UTF8&amp;useUnicode=true&amp;useSSL=false</p><p>​    &lt;property name=<em>“driverClass”</em>&gt;com.mysql.jdbc.Driver</p><p>​    &lt;property name=<em>“user”</em>&gt;root</p><p>​    &lt;property name=<em>“password”</em>&gt;1234</p><p>​    <!--连接数据库的超时时间 --></p><p>​    &lt;property name=<em>“checkoutTimeout”</em>&gt;3000</p><p>​    <!--里面默认的初始化连接个数 --></p><p>​    &lt;property name=<em>“initialPoolSize”</em>&gt;3</p><p>​    <!-- 最多有多少连接 --></p><p>​    &lt;property name=<em>“maxPoolSize”</em>&gt;10</p><p>​    &lt;property name=<em>“minPoolSize”</em>&gt;3</p><p>​    <!--一次批量处理，最多可以执行多少SQL语句,默认是50,50~200是一个合理的范围 --></p><p>​    &lt;property name=<em>“maxStatements”</em>&gt;200</p><p>  </p><p></p><h2 id="创建一个连接池，通过读取上面的配置文件"><a href="#创建一个连接池，通过读取上面的配置文件" class="headerlink" title="创建一个连接池，通过读取上面的配置文件"></a>创建一个连接池，通过读取上面的配置文件</h2><p>package cn.hyxy.zhenai.util;<br>import javax.sql.DataSource;<br>import com.mchange.v2.c3p0.ComboPooledDataSource;<br>public class DSUtils {<br>   //1:声明dataSour e<br>   private static DataSource DATASOURCE;<br>   //2:开发一个静态的代码块，只执行一次<br>   static {<br>     DATASOURCE = new ComboPooledDataSource();<br>   }<br>   //3:获取Da<br>   public static DataSource getDataSource() {<br>     return DATASOURCE;<br>   }<br>}</p><h2 id="使用dbutils"><a href="#使用dbutils" class="headerlink" title="使用dbutils"></a>使用dbutils</h2><p>导入dbutils的依赖</p><dependency><p>​      <groupid>commons-dbutils</groupid></p><p>​      <artifactid>commons-dbutils</artifactid></p><p>​      <version>1.7</version></p><p>​    </p></dependency><br><strong>然后呢我们就要根据我们所获取数据的结构，制做mysql的表</strong><p></p><p><img src="https://img-blog.csdn.net/20180717113408420?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><strong>我们来设计我们的表格</strong></p><p>输入指令 ，来创建这个表格</p><p>CREATE TABLE dogs(</p><p>  id BIGINT,</p><p>  NAME VARCHAR(50),</p><p>  age INT,</p><p>  workaddr VARCHAR(20),</p><p>  height INT,</p><p>  salary VARCHAR(30),</p><p>  homeaddr VARCHAR(30),</p><p>  married VARCHAR(10),</p><p>  grade VARCHAR(10),</p><p>  worker VARCHAR(20),</p><p>  house VARCHAR(10),</p><p>  car VARCHAR(10),</p><p>  sex VARCHAR(10)</p><p>);</p><p>然后我们利用程序 将爬取的数据写入到数据库，为了更可观的查看我们爬取的数据，我们可以利用数据库管理和开发工具</p><p>例如navicat premium</p><p>将数据写入到数据库中，在spider 中写一个方法 ，传入我们所获取的信息，利用这个方法将我们传进的信息，写入到数据库中</p><p>   public void insert(String sql, String id, String name,String sex, String age, String workaddr, String height, String salary,<br>       String homeaddr, String married, String grade, String worker, String house, String car) throws Exception {<br>     QueryRunner run = new QueryRunner(DSUtils.getDataSource());<br>     run.update(sql, id, name,sex, age, workaddr, height, salary, homeaddr, married, grade, worker, house, car);<br>   }</p><p>这样呢我们就成功将我们获取的信息写入到我们的数据库了 然后将spider 跑起来 其获取信息</p><p><img src="https://img-blog.csdn.net/20180717115454166?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>我们的爬虫到这儿 就完成了，下次我们就要利用这些数据做成报表，使信息更可观的表现如下图</p><p><img src="https://img-blog.csdn.net/20180717115737652?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115811176?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115838418?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115910128?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p><img src="https://img-blog.csdn.net/20180717115929933?watermark/2/text/aHR0cHM6Ly9ibG9nLmNzZG4ubmV0L2FpZmVpbmloYW8=/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70" alt="img"><img src="data:image/gif;base64,R0lGODlhAQABAPABAP///wAAACH5BAEKAAAALAAAAAABAAEAAAICRAEAOw==" alt="点击并拖拽以移动"></p><p>诸如此类，大家可自行设计不同的报表类型，明天再和大家继续分享，文中若有不足，欢迎大家的指正。</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;p&gt;继续我们的项目， 上次之后我们基本上完成了数据的获取（即爬虫），接下来呢就是如何去保存这些数据，有两种方式，一种呢是以文本形式保存到本地，第二种是就是保存到数据库，而我们呢选择后者。&lt;/p&gt;
&lt;h1 id=&quot;Mysql&quot;&gt;&lt;a href=&quot;#Mysql&quot; class=&quot;he
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="教程" scheme="http://www.windknew.com/blog/tags/%E6%95%99%E7%A8%8B/"/>
    
  </entry>
  
  <entry>
    <title>Hello World</title>
    <link href="http://www.windknew.com/hello-world/"/>
    <id>http://www.windknew.com/hello-world/</id>
    <published>2020-09-09T06:41:13.580Z</published>
    <updated>2020-09-09T06:41:13.580Z</updated>
    
    <content type="html"><![CDATA[<p>Welcome to <a href="https://hexo.io/" target="_blank" rel="noopener">Hexo</a>! This is your very first post. Check <a href="https://hexo.io/docs/" target="_blank" rel="noopener">documentation</a> for more info. If you get any problems when using Hexo, you can find the answer in <a href="https://hexo.io/docs/troubleshooting.html" target="_blank" rel="noopener">troubleshooting</a> or you can ask me on <a href="https://github.com/hexojs/hexo/issues" target="_blank" rel="noopener">GitHub</a>.</p><h2 id="Quick-Start"><a href="#Quick-Start" class="headerlink" title="Quick Start"></a>Quick Start</h2><h3 id="Create-a-new-post"><a href="#Create-a-new-post" class="headerlink" title="Create a new post"></a>Create a new post</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">$ hexo new <span class="string">"My New Post"</span></span><br></pre></td></tr></table></figure><p>More info: <a href="https://hexo.io/docs/writing.html" target="_blank" rel="noopener">Writing</a></p><h3 id="Run-server"><a href="#Run-server" class="headerlink" title="Run server"></a>Run server</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">$ hexo server</span><br></pre></td></tr></table></figure><p>More info: <a href="https://hexo.io/docs/server.html" target="_blank" rel="noopener">Server</a></p><h3 id="Generate-static-files"><a href="#Generate-static-files" class="headerlink" title="Generate static files"></a>Generate static files</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">$ hexo generate</span><br></pre></td></tr></table></figure><p>More info: <a href="https://hexo.io/docs/generating.html" target="_blank" rel="noopener">Generating</a></p><h3 id="Deploy-to-remote-sites"><a href="#Deploy-to-remote-sites" class="headerlink" title="Deploy to remote sites"></a>Deploy to remote sites</h3><figure class="highlight bash"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">$ hexo deploy</span><br></pre></td></tr></table></figure><p>More info: <a href="https://hexo.io/docs/one-command-deployment.html" target="_blank" rel="noopener">Deployment</a></p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;p&gt;Welcome to &lt;a href=&quot;https://hexo.io/&quot; target=&quot;_blank&quot; rel=&quot;noopener&quot;&gt;Hexo&lt;/a&gt;! This is your very first post. Check &lt;a href=&quot;https://hexo.
      
    
    </summary>
    
    
  </entry>
  
  <entry>
    <title>在家学习java第七天（接口和包）</title>
    <link href="http://www.windknew.com/java-8/"/>
    <id>http://www.windknew.com/java-8/</id>
    <published>2020-02-13T09:27:58.000Z</published>
    <updated>2020-02-20T01:31:31.622Z</updated>
    
    <content type="html"><![CDATA[<h1 id="Java-接口"><a href="#Java-接口" class="headerlink" title="Java 接口"></a>Java 接口</h1><p>接口（Interface），在java中，是一个抽象类型，是抽象方法的集合，接口通常以interface来声明，一个类通过继承接口的方式，从而来继承接口的抽象方法</p><p>接口并不是类，编写接口的方式和类很相似，但是他门属于不同的概念，类描述对象的属性和方法接口则包含类要实现的方法</p><p>除非实现接口的类是抽象类，否则该类要定义接口中的所有方法</p><p>接口无法被实例化，但是可以被实现。一个实现接口的类必须实现接口内所描述的所有方法，否则就必须声明为抽象类。另外，在Java中，接口类型可用来声明一个变量，他们可以成为一个空指针，或是被绑定在一个以此接口实现的对象</p><h2 id="接口与类的相似点"><a href="#接口与类的相似点" class="headerlink" title="接口与类的相似点"></a>接口与类的相似点</h2><ul><li>一个接口可以有多个方法。</li><li>接口文件保存在 .java 结尾的文件中，文件名使用接口名。</li><li>接口的字节码文件保存在 .class 结尾的文件中。</li><li>接口相应的字节码文件必须在与包名称相匹配的目录结构中。</li></ul><h2 id="接口与类的区别："><a href="#接口与类的区别：" class="headerlink" title="接口与类的区别："></a>接口与类的区别：</h2><ul><li>接口不能用于实例化对象。</li><li>接口没有构造方法。</li><li>接口中所有的方法必须是抽象方法。</li><li>接口不能包含成员变量，除了 static 和 final 变量。</li><li>接口不是被类继承了，而是要被类实现。</li><li>接口支持多继承。</li></ul><h2 id="接口特性"><a href="#接口特性" class="headerlink" title="接口特性"></a>接口特性</h2><ul><li>接口中每一个方法也是隐式抽象的,接口中的方法会被隐式的指定为 <strong>public abstract</strong>（只能是 public abstract，其他修饰符都会报错）。</li><li>接口中可以含有变量，但是接口中的变量会被隐式的指定为 <strong>public static final</strong> 变量（并且只能是 public，用 private 修饰会报编译错误）。</li><li>接口中的方法是不能在接口中实现的，只能由实现接口的类来实现接口中的方法。</li></ul><h2 id="抽象类和接口的区别"><a href="#抽象类和接口的区别" class="headerlink" title="抽象类和接口的区别"></a>抽象类和接口的区别</h2><ul><li>抽象类中的方法可以有方法体，就是能实现方法的具体功能，但是接口中的方法不行。</li><li>抽象类中的成员变量可以是各种类型的，而接口中的成员变量只能是 <strong>public static final</strong> 类型的。</li><li>接口中不能含有静态代码块以及静态方法(用 static 修饰的方法)，而抽象类是可以有静态代码块和静态方法。</li><li>一个类只能继承一个抽象类，而一个类却可以实现多个接口。</li></ul><p><strong><em>注</em></strong>：JDK 1.8 <strong>以后，接口里可以有静态方法和方法体了。</strong></p><h2 id="接口的声明"><a href="#接口的声明" class="headerlink" title="接口的声明"></a>接口的声明</h2><p>接口的声明语法格式如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">[可见度] interface 接口名称 [extends 其他的接口名] &#123;</span><br><span class="line">        <span class="comment">// 声明变量</span></span><br><span class="line">        <span class="comment">// 抽象方法</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>Interface关键字用来声明一个接口。下面是接口声明的一个简单例子。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> java.lang.*;</span><br><span class="line"><span class="comment">//引入包</span></span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">NameOfInterface</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="comment">//任何类型 final, static 字段</span></span><br><span class="line">   <span class="comment">//抽象方法</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>接口有以下特性：</p><ul><li>接口是隐式抽象的，当声明一个接口的时候，不必使用<strong>abstract</strong>关键字。</li><li>接口中每一个方法也是隐式抽象的，声明时同样不需要<strong>abstract</strong>关键字。</li><li>接口中的方法都是公有的。</li></ul><h4 id="实例"><a href="#实例" class="headerlink" title="实例"></a><strong>实例</strong></h4><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名 : Animal.java */</span></span><br><span class="line"><span class="class"><span class="keyword">interface</span> <span class="title">Animal</span> </span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">travel</span><span class="params">()</span></span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="接口的实现"><a href="#接口的实现" class="headerlink" title="接口的实现"></a>接口的实现</h2><p>当类实现接口的时候，类要实现接口中所有的方法。否则，类必须声明为抽象的类。</p><p>类使用implements关键字实现接口。在类声明中，Implements关键字放在class声明后面。</p><p>实现一个接口的语法，可以使用这个公式：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">...implements 接口名称[, 其他接口名称, 其他接口名称..., ...] ...</span><br></pre></td></tr></table></figure><h4 id="实例-1"><a href="#实例-1" class="headerlink" title="实例"></a>实例</h4><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名 : MammalInt.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">MammalInt</span> <span class="keyword">implements</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Mammal eats"</span>);</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">travel</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Mammal travels"</span>);</span><br><span class="line">   &#125; </span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">noOfLegs</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> <span class="number">0</span>;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String args[])</span></span>&#123;</span><br><span class="line">      MammalInt m = <span class="keyword">new</span> MammalInt();</span><br><span class="line">      m.eat();</span><br><span class="line">      m.travel();</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>结果如下</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200213094430615/20200213105750147.png" alt=""></p><p>重写接口中声明的方法时，需要注意以下规则：</p><ul><li>类在实现接口的方法时，不能抛出强制性异常，只能在接口中，或者继承接口的抽象类中抛出该强制性异常。</li><li>类在重写方法时要保持一致的方法名，并且应该保持相同或者相兼容的返回值类型。</li><li>如果实现接口的类是抽象类，那么就没必要实现该接口的方法。</li></ul><p>在实现接口的时候，也要注意一些规则：</p><ul><li>一个类可以同时实现多个接口。</li><li>一个类只能继承一个类，但是能实现多个接口。</li><li>一个接口能继承另一个接口，这和类之间的继承比较相似。</li></ul><h2 id="接口的继承"><a href="#接口的继承" class="headerlink" title="接口的继承"></a>接口的继承</h2><p>一个接口能继承另一个接口，和类之间的继承方式比较相似。接口的继承使用extends关键字，子接口继承父接口的方法。</p><p>下面的Sports接口被Hockey和Football接口继承：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 文件名: Sports.java</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">Sports</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setHomeTeam</span><span class="params">(String name)</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setVisitingTeam</span><span class="params">(String name)</span></span>;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="comment">// 文件名: Football.java</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">Football</span> <span class="keyword">extends</span> <span class="title">Sports</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">homeTeamScored</span><span class="params">(<span class="keyword">int</span> points)</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">visitingTeamScored</span><span class="params">(<span class="keyword">int</span> points)</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">endOfQuarter</span><span class="params">(<span class="keyword">int</span> quarter)</span></span>;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="comment">// 文件名: Hockey.java</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">Hockey</span> <span class="keyword">extends</span> <span class="title">Sports</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">homeGoalScored</span><span class="params">()</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">visitingGoalScored</span><span class="params">()</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">endOfPeriod</span><span class="params">(<span class="keyword">int</span> period)</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">overtimePeriod</span><span class="params">(<span class="keyword">int</span> ot)</span></span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>Hockey接口自己声明了四个方法，从Sports接口继承了两个方法，这样，实现Hockey接口的类需要实现六个方法。</p><p>相似的，实现Football接口的类需要实现五个方法，其中两个来自于Sports接口。</p><h2 id="接口的多继承"><a href="#接口的多继承" class="headerlink" title="接口的多继承"></a>接口的多继承</h2><p>在Java中，类的多继承是不合法，但接口允许多继承。</p><p>在接口的多继承中extends关键字只需要使用一次，在其后跟着继承接口。 如下所示：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">Hockey</span> <span class="keyword">extends</span> <span class="title">Sports</span>, <span class="title">Event</span></span></span><br></pre></td></tr></table></figure><p>没有任何方法的接口被称为标记接口。标记接口主要用于以下两种目的：</p><ul><li><p>建立一个公共的父接口：</p><p>正如EventListener接口，这是由几十个其他接口扩展的Java API，你可以使用一个标记接口来建立一组接口的父接口。例如：当一个接口继承了EventListener接口，Java虚拟机(JVM)就知道该接口将要被用于一个事件的代理方案。</p></li><li><p>向一个类添加数据类型：</p><p>这种情况是标记接口最初的目的，实现标记接口的类不需要定义任何接口方法(因为标记接口根本就没有方法)，但是该类通过多态性变成一个接口类型。</p></li></ul><p>标记接口定义如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> java.util;</span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">EventListener</span></span>&#123;</span><br><span class="line">    ....</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h1 id="Java-包（package）"><a href="#Java-包（package）" class="headerlink" title="Java 包（package）"></a>Java 包（package）</h1><p>为了更好地组织类，Java 提供了包机制，用于区别类名的命名空间。</p><h2 id="包的作用"><a href="#包的作用" class="headerlink" title="包的作用"></a>包的作用</h2><ul><li>1、把功能相似或相关的类或接口组织在同一个包中，方便类的查找和使用。</li><li>2、如同文件夹一样，包也采用了树形目录的存储方式。同一个包中的类名字是不同的，不同的包中的类的名字是可以相同的，当同时调用两个不同包中相同类名的类时，应该加上包名加以区别。因此，包可以避免名字冲突。</li><li>3、包也限定了访问权限，拥有包访问权限的类才能访问某个包中的类。</li></ul><p>Java 使用包（package）这种机制是为了防止命名冲突，访问控制，提供搜索和定位类（class）、接口、枚举（enumerations）和注释（annotation）等。</p><p>包语句的语法格式为：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> pkg1[．pkg2[．pkg3…]];</span><br></pre></td></tr></table></figure><p>例如,一个Something.java 文件它的内容</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> net.java.util;</span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Something</span></span>&#123;</span><br><span class="line">   ...</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>那么它的路径应该是 <strong>net/java/util/Something.java</strong> 这样保存的。 package(包) 的作用是把不同的 java 程序分类保存，更方便的被其他 java 程序调用。</p><p>一个包（package）可以定义为一组相互联系的类型（类、接口、枚举和注释），为这些类型提供访问保护和命名空间管理的功能。</p><p>以下是一些 Java 中的包：</p><ul><li><strong>java.lang</strong>-打包基础的类</li><li><strong>java.io</strong>-包含输入输出功能的函数</li></ul><p>开发者可以自己把一组类和接口等打包，并定义自己的包。而且在实际开发中这样做是值得提倡的，当你自己完成类的实现之后，将相关的类分组，可以让其他的编程者更容易地确定哪些类、接口、枚举和注释等是相关的。</p><p>由于包创建了新的命名空间（namespace），所以不会跟其他包中的任何名字产生命名冲突。使用包这种机制，更容易实现访问控制，并且让定位相关类更加简单。</p><h2 id="创建包"><a href="#创建包" class="headerlink" title="创建包"></a>创建包</h2><p>创建包的时候，你需要为这个包取一个合适的名字。之后，如果其他的一个源文件包含了这个包提供的类、接口、枚举或者注释类型的时候，都必须将这个包的声明放在这个源文件的开头。</p><p>包声明应该在源文件的第一行，每个源文件只能有一个包声明，这个文件中的每个类型都应用于它。</p><p>如果一个源文件中没有使用包声明，那么其中的类，函数，枚举，注释等将被放在一个无名的包（unnamed package）中。</p><h3 id="例子"><a href="#例子" class="headerlink" title="例子"></a>例子</h3><p>让我们来看一个例子，这个例子创建了一个叫做animals的包。通常使用小写的字母来命名避免与类、接口名字的冲突。</p><p>在 animals 包中加入一个接口（interface）：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名: Animal.java */</span></span><br><span class="line"><span class="keyword">package</span> animals;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">interface</span> <span class="title">Animal</span> </span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">travel</span><span class="params">()</span></span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>接下来，在同一个包中加入该接口的实现：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> animals;</span><br><span class="line"> </span><br><span class="line"><span class="comment">/* 文件名 : MammalInt.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">MammalInt</span> <span class="keyword">implements</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Mammal eats"</span>);</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">travel</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Mammal travels"</span>);</span><br><span class="line">   &#125; </span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">noOfLegs</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> <span class="number">0</span>;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String args[])</span></span>&#123;</span><br><span class="line">      MammalInt m = <span class="keyword">new</span> MammalInt();</span><br><span class="line">      m.eat();</span><br><span class="line">      m.travel();</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>然后，编译这两个文件，并把他们放在一个叫做animals的子目录中。 用下面的命令来运行：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">$ mkdir animals</span><br><span class="line">$ cp Animal.class  MammalInt.class animals</span><br><span class="line">$ java animals/MammalInt</span><br><span class="line">Mammal eats</span><br><span class="line">Mammal travel</span><br></pre></td></tr></table></figure><h2 id="import-关键字"><a href="#import-关键字" class="headerlink" title="import 关键字"></a>import 关键字</h2><p>为了能够使用某一个包的成员，我们需要在 Java 程序中明确导入该包。使用 “import” 语句可完成此功能。</p><p>在 java 源文件中 import 语句应位于 package 语句之后，所有类的定义之前，可以没有，也可以有多条，其语法格式为：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> package1[.package2…].(classname|*);</span><br></pre></td></tr></table></figure><p>如果在一个包中，一个类想要使用本包中的另一个类，那么该包名可以省略。</p><h3 id="例子-1"><a href="#例子-1" class="headerlink" title="例子"></a>例子</h3><p>下面的 payroll 包已经包含了 Employee 类，接下来向 payroll 包中添加一个 Boss 类。Boss 类引用 Employee 类的时候可以不用使用 payroll 前缀，Boss 类的实例如下。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">package</span> payroll;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Boss</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">payEmployee</span><span class="params">(Employee e)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      e.mailCheck();</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>如果 Boss 类不在 payroll 包中又会怎样？Boss 类必须使用下面几种方法之一来引用其他包中的类。</p><p>使用类全名描述，例如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">payroll.Employee</span><br></pre></td></tr></table></figure><p>用 <strong>import</strong> 关键字引入，使用通配符 “*”</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> payroll.*;</span><br></pre></td></tr></table></figure><p>使用 <strong>import</strong> 关键字引入 Employee 类:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">import</span> payroll.Employee;</span><br></pre></td></tr></table></figure><p><strong>类文件中可以包含任意数量的 import 声明。import 声明必须在包声明之后，类声明之前。</strong></p><h2 id="package-的目录结构"><a href="#package-的目录结构" class="headerlink" title="package 的目录结构"></a>package 的目录结构</h2><p>类放在包中会有两种主要的结果：</p><ul><li>包名成为类名的一部分，正如我们前面讨论的一样。</li><li>包名必须与相应的字节码所在的目录结构相吻合。</li></ul><p>下面是管理你自己 java 中文件的一种简单方式：</p><p>将类、接口等类型的源码放在一个文本中，这个文件的名字就是这个类型的名字，并以.java作为扩展名。例如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">// 文件名 :  Car.java</span></span><br><span class="line"> </span><br><span class="line"><span class="keyword">package</span> vehicle;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Car</span> </span>&#123;</span><br><span class="line">   <span class="comment">// 类实现  </span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>接下来，把源文件放在一个目录中，这个目录要对应类所在包的名字。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">....\vehicle\Car.java</span><br></pre></td></tr></table></figure><p>现在，正确的类名和路径将会是如下样子：</p><ul><li>类名 -&gt; vehicle.Car</li><li>路径名 -&gt; vehicle\Car.java (在 windows 系统中)</li></ul><p>通常，一个公司使用它互联网域名的颠倒形式来作为它的包名.例如：互联网域名是 runoob.com，所有的包名都以 com.runoob 开头。包名中的每一个部分对应一个子目录。</p><p>例如：有一个 <strong>com.runoob.test</strong> 的包，这个包包含一个叫做 Runoob.java 的源文件，那么相应的，应该有如下面的一连串子目录：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">....\com\runoob\test\Runoob.java</span><br></pre></td></tr></table></figure><p>编译的时候，编译器为包中定义的每个类、接口等类型各创建一个不同的输出文件，输出文件的名字就是这个类型的名字，并加上 .class 作为扩展后缀。 例如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">/ 文件名: Runoob.java</span><br><span class="line"> </span><br><span class="line"><span class="keyword">package</span> com.runoob.test;</span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Runoob</span> </span>&#123;</span><br><span class="line">      </span><br><span class="line">&#125;</span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Google</span> </span>&#123;</span><br><span class="line">      </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>现在，我们用-d选项来编译这个文件，如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">$javac -d . Runoob.java</span><br></pre></td></tr></table></figure><p>这样会像下面这样放置编译了的文件：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">.\com\runoob\test\Runoob.class</span><br><span class="line">.\com\runoob\test\Google.class</span><br></pre></td></tr></table></figure><p>可以像下面这样来导入所有 <strong>\com\runoob\test\</strong> 中定义的类、接口等：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">import com.runoob.test.*;</span><br></pre></td></tr></table></figure><p>编译之后的 .class 文件应该和 .java 源文件一样，它们放置的目录应该跟包的名字对应起来。但是，并不要求 .class 文件的路径跟相应的 .java 的路径一样。你可以分开来安排源码和类的目录。</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">&lt;path-one&gt;\sources\com\runoob\test\Runoob.java</span><br><span class="line">&lt;path-two&gt;\classes\com\runoob\test\Google.class</span><br></pre></td></tr></table></figure><p>样，你可以将你的类目录分享给其他的编程人员，而不用透露自己的源码。用这种方法管理源码和类文件可以让编译器和java 虚拟机（JVM）可以找到你程序中使用的所有类型。</p><p>类目录的绝对路径叫做 <strong>class path</strong>。设置在系统变量 <strong>CLASSPATH</strong> 中。编译器和 java 虚拟机通过将 package 名字加到 class path 后来构造 .class 文件的路径。</p><p><path- two="">\classes 是 class path，package 名字是 com.runoob.test,而编译器和 JVM 会在 <path-two>\classes\com\runoob\test 中找 .class 文件。</path-two></path-></p><p>一个 class path 可能会包含好几个路径，多路径应该用分隔符分开。默认情况下，编译器和 JVM 查找当前目录。JAR 文件按包含 Java 平台相关的类，所以他们的目录默认放在了 class path 中。</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;Java-接口&quot;&gt;&lt;a href=&quot;#Java-接口&quot; class=&quot;headerlink&quot; title=&quot;Java 接口&quot;&gt;&lt;/a&gt;Java 接口&lt;/h1&gt;&lt;p&gt;接口（Interface），在java中，是一个抽象类型，是抽象方法的集合，接口通常以interfa
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家学习java第六天（抽象类，封装）</title>
    <link href="http://www.windknew.com/java-6/"/>
    <id>http://www.windknew.com/java-6/</id>
    <published>2020-02-12T09:00:19.000Z</published>
    <updated>2020-02-20T01:19:51.723Z</updated>
    
    <content type="html"><![CDATA[<h1 id="Java-抽象类"><a href="#Java-抽象类" class="headerlink" title="Java 抽象类"></a>Java 抽象类</h1><h2 id="抽象类"><a href="#抽象类" class="headerlink" title="抽象类"></a><strong>抽象类</strong></h2><ul><li><p>在面向对象中，所有的对象都是通过类来描述的，但是并不是所有的类都是用来描绘对象的，如果一个类中没有包含最够的信息来描绘一个具体的对象，这样的类就是抽象类</p></li><li><p>抽象类除了不能实例化对象外，类的其他功能依然存在，成员变量，成员方法和构造方法的访问方式和普通类一样</p></li><li>由于抽象类不能实例化对象，所以抽象类u必须被继承，才能被使用，</li><li>在Java中抽象类表示的是一种继承关系，一个类只能继承一个抽象类，而一个类却可以实现多个接口</li></ul><h2 id="在Java语言中使用abstract-class来定义抽象类，如："><a href="#在Java语言中使用abstract-class来定义抽象类，如：" class="headerlink" title="在Java语言中使用abstract class来定义抽象类，如："></a>在Java语言中使用abstract class来定义抽象类，如：</h2><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">abstract</span> <span class="class"><span class="keyword">class</span> <span class="title">Employee</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="keyword">private</span> String name;</span><br><span class="line">   <span class="keyword">private</span> String address;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">int</span> number;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="title">Employee</span><span class="params">(String name, String address, <span class="keyword">int</span> number)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Constructing an Employee"</span>);</span><br><span class="line">      <span class="keyword">this</span>.name = name;</span><br><span class="line">      <span class="keyword">this</span>.address = address;</span><br><span class="line">      <span class="keyword">this</span>.number = number;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">double</span> <span class="title">computePay</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">     System.out.println(<span class="string">"Inside Employee computePay"</span>);</span><br><span class="line">     <span class="keyword">return</span> <span class="number">0.0</span>;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">mailCheck</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Mailing a check to "</span> + <span class="keyword">this</span>.name</span><br><span class="line">       + <span class="string">" "</span> + <span class="keyword">this</span>.address);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">toString</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> name + <span class="string">" "</span> + address + <span class="string">" "</span> + number;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">getName</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> name;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">getAddress</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> address;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setAddress</span><span class="params">(String newAddress)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      address = newAddress;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">getNumber</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">     <span class="keyword">return</span> number;</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>该类和普通类没什么不同，尽管类是抽象类，但是它仍然有3个成员变量，7个成员方法，和一个构造方法，如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">AbstractDemo</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String [] args)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      <span class="comment">/* 以下是不允许的，会引发错误 */</span></span><br><span class="line">      Employee e = <span class="keyword">new</span> Employee(<span class="string">"George W."</span>, <span class="string">"Houston, TX"</span>, <span class="number">43</span>);</span><br><span class="line"> </span><br><span class="line">      System.out.println(<span class="string">"\n Call mailCheck using Employee reference--"</span>);</span><br><span class="line">      e.mailCheck();</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>当编译时会产生以下错误</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200213094430615/20200213094434145.png" alt=""></p><h2 id="继承抽象类"><a href="#继承抽象类" class="headerlink" title="继承抽象类"></a>继承抽象类</h2><p>我们能通过一般的方法继承Employee类</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名 : Salary.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Salary</span> <span class="keyword">extends</span> <span class="title">Employee</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">double</span> salary; <span class="comment">//Annual salary</span></span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="title">Salary</span><span class="params">(String name, String address, <span class="keyword">int</span> number, <span class="keyword">double</span> salary)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">       <span class="keyword">super</span>(name, address, number);</span><br><span class="line">       setSalary(salary);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">mailCheck</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">       System.out.println(<span class="string">"Within mailCheck of Salary class "</span>);</span><br><span class="line">       System.out.println(<span class="string">"Mailing check to "</span> + getName()+<span class="string">" with salary "</span>+salary);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">double</span> <span class="title">getSalary</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">       <span class="keyword">return</span> salary;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setSalary</span><span class="params">(<span class="keyword">double</span> newSalary)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">       <span class="keyword">if</span>(newSalary &gt;= <span class="number">0.0</span>)</span><br><span class="line">       &#123;</span><br><span class="line">          salary = newSalary;</span><br><span class="line">       &#125;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">double</span> <span class="title">computePay</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Computing salary pay for "</span> + getName());</span><br><span class="line">      <span class="keyword">return</span> salary/<span class="number">52</span>;</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>尽管我们不能实例化一个Employee类的对象，但是如果我们实例化一个Salary类对象，该对象将从Employee类继承7个成员方法，且通过该方法可以设置获取三个成员变量</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br></pre></td><td class="code"><pre><span class="line">* 文件名 : AbstractDemo.java */</span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">AbstractDemo</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String [] args)</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      Salary s = <span class="keyword">new</span> Salary(<span class="string">"Mohd Mohtashim"</span>, <span class="string">"Ambehta, UP"</span>, <span class="number">3</span>, <span class="number">3600.00</span>);</span><br><span class="line">      Employee e = <span class="keyword">new</span> Salary(<span class="string">"John Adams"</span>, <span class="string">"Boston, MA"</span>, <span class="number">2</span>, <span class="number">2400.00</span>);</span><br><span class="line"> </span><br><span class="line">      System.out.println(<span class="string">"Call mailCheck using Salary reference --"</span>);</span><br><span class="line">      s.mailCheck();</span><br><span class="line"> </span><br><span class="line">      System.out.println(<span class="string">"\n Call mailCheck using Employee reference--"</span>);</span><br><span class="line">      e.mailCheck();</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>运行结果如下：</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200213094430615/20200213095040947.png" alt=""></p><h2 id="抽象方法"><a href="#抽象方法" class="headerlink" title="抽象方法"></a>抽象方法</h2><p>如果你想设计这样一个类，该类包含一个特别的成员方法，该方法的具体实现由它的子类确定，那么你可以在父类中声明该方法为抽象方法。</p><p>Abstract 关键字同样可以用来声明抽象方法，抽象方法只包含一个方法名，而没有方法体。</p><p>抽象方法没有定义，方法名后面直接跟一个分号，而不是花括号。如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">abstract</span> <span class="class"><span class="keyword">class</span> <span class="title">Employee</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="keyword">private</span> String name;</span><br><span class="line">   <span class="keyword">private</span> String address;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">int</span> number;</span><br><span class="line">   </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">abstract</span> <span class="keyword">double</span> <span class="title">computePay</span><span class="params">()</span></span>;</span><br><span class="line">   </span><br><span class="line">   <span class="comment">//其余代码</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>声明抽象方法会造成以下两个结果：</p><ul><li>如果一个类包含抽象方法，那么该类必须是抽象类。</li><li>任何子类必须重写父类的抽象方法，或者声明自身为抽象类。</li></ul><p>继承抽象方法的子类必须重写该方法。否则，该子类也必须声明为抽象类。最终，必须有子类实现该抽象方法，否则，从最初的父类到最终的子类都不能用来实例化对象。</p><p>如果Salary类继承了Employee类，那么它必须实现computePay()方法，如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Salary</span> <span class="keyword">extends</span> <span class="title">Employee</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">double</span> salary; <span class="comment">// Annual salary</span></span><br><span class="line">  </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">double</span> <span class="title">computePay</span><span class="params">()</span></span></span><br><span class="line"><span class="function">   </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Computing salary pay for "</span> + getName());</span><br><span class="line">      <span class="keyword">return</span> salary/<span class="number">52</span>;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="comment">//其余代码</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="抽象类总结"><a href="#抽象类总结" class="headerlink" title="抽象类总结"></a>抽象类总结</h2><ul><li>抽象类不能被实例化(初学者很容易犯的错)，如果被实例化，就会报错，编译无法通过。只有抽象类的非抽象子类可以创建对象。</li><li>抽象类中不一定包含抽象方法，但是有抽象方法的类必定是抽象类。</li><li>抽象类中的抽象方法只是声明，不包含方法体，就是不给出方法的具体实现也就是方法的具体功能。</li><li>构造方法，类方法（用 static 修饰的方法）不能声明为抽象方法。</li><li>抽象类的子类必须给出抽象类中的抽象方法的具体实现，除非该子类也是抽象类。</li></ul><h1 id="Java-封装"><a href="#Java-封装" class="headerlink" title="Java 封装"></a>Java 封装</h1><hr><p>在面向对象程式设计方法中，封装（英语：Encapsulation）是指一种将抽象性函式接口的实现细节部分包装、隐藏起来的方法。</p><p>封装可以被认为是一个保护屏障，防止该类的代码和数据被外部类定义的代码随机访问。</p><p>要访问该类的代码和数据，必须通过严格的接口控制。</p><p>封装最主要的功能在于我们能修改自己的实现代码，而不用修改那些调用我们代码的程序片段。</p><p>适当的封装可以让程式码更容易理解与维护，也加强了程式码的安全性。</p><h3 id="封装的优点"><a href="#封装的优点" class="headerlink" title="封装的优点"></a>封装的优点</h3><ul><li>良好的封装能够减少耦合。</li><li>类内部的结构可以自由修改。</li><li>可以对成员变量进行更精确的控制。</li><li>隐藏信息，实现细节。</li></ul><h2 id="实现Java封装的步骤"><a href="#实现Java封装的步骤" class="headerlink" title="实现Java封装的步骤"></a>实现Java封装的步骤</h2><ol><li>修改属性的可见性来限制对属性的访问（一般限制为private），例如：</li></ol><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Person</span> </span>&#123;</span><br><span class="line">    <span class="keyword">private</span> String name;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">int</span> age;</span><br><span class="line">&#125;</span><br><span class="line">这段代码中，将name和age属性设置为私有的，只能本类才能访问，其他类都访问不了，如此就对信息进行了隐藏。</span><br></pre></td></tr></table></figure><ol start="2"><li>对每个值属性提供对外的公共方法访问，也就是创建一对赋取值方法，用于对私有属性的访问，例如</li></ol><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Person</span></span>&#123;</span><br><span class="line">    <span class="keyword">private</span> String name;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">int</span> age;</span><br><span class="line">​</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">getAge</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> age;</span><br><span class="line">    &#125;</span><br><span class="line">​</span><br><span class="line">    <span class="function"><span class="keyword">public</span> String <span class="title">getName</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> name;</span><br><span class="line">    &#125;</span><br><span class="line">​</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setAge</span><span class="params">(<span class="keyword">int</span> age)</span></span>&#123;</span><br><span class="line">      <span class="keyword">this</span>.age = age;</span><br><span class="line">    &#125;</span><br><span class="line">​</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setName</span><span class="params">(String name)</span></span>&#123;</span><br><span class="line">      <span class="keyword">this</span>.name = name;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>采用this关键字是为了解决实例变量（private String name）和局部变量（setName(String name)中的name变量）之间发生的同名的冲突。</strong></p><h2 id="实例"><a href="#实例" class="headerlink" title="实例"></a>实例</h2><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名: EncapTest.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">EncapTest</span></span>&#123;</span><br><span class="line"> </span><br><span class="line">   <span class="keyword">private</span> String name;</span><br><span class="line">   <span class="keyword">private</span> String idNum;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">int</span> age;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">getAge</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> age;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">getName</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> name;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">getIdNum</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">return</span> idNum;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setAge</span><span class="params">( <span class="keyword">int</span> newAge)</span></span>&#123;</span><br><span class="line">      age = newAge;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setName</span><span class="params">(String newName)</span></span>&#123;</span><br><span class="line">      name = newName;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setIdNum</span><span class="params">( String newId)</span></span>&#123;</span><br><span class="line">      idNum = newId;</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上实例中public方法是外部类访问该类成员变量的入口。</p><p>通常情况下，这些方法被称为getter和setter方法。</p><p>因此，任何要访问类中私有成员变量的类都要通过这些getter和setter方法。</p><p>通过如下的例子说明EncapTest类的变量怎样被访问：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">RunEncap</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String args[])</span></span>&#123;</span><br><span class="line">      EncapTest encap = <span class="keyword">new</span> EncapTest();</span><br><span class="line">      encap.setName(<span class="string">"James"</span>);</span><br><span class="line">      encap.setAge(<span class="number">20</span>);</span><br><span class="line">      encap.setIdNum(<span class="string">"12343ms"</span>);</span><br><span class="line"> </span><br><span class="line">      System.out.print(<span class="string">"Name : "</span> + encap.getName()+ </span><br><span class="line">                             <span class="string">" Age : "</span>+ encap.getAge());</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上就是今天学到的java内容，java果然博大精深，怪不得人生苦短，我用python，学了几天java深深体会到了python的精炼</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;Java-抽象类&quot;&gt;&lt;a href=&quot;#Java-抽象类&quot; class=&quot;headerlink&quot; title=&quot;Java 抽象类&quot;&gt;&lt;/a&gt;Java 抽象类&lt;/h1&gt;&lt;h2 id=&quot;抽象类&quot;&gt;&lt;a href=&quot;#抽象类&quot; class=&quot;headerlink&quot; ti
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家学习java第五天（Java面向对象-重写与重载和多态）</title>
    <link href="http://www.windknew.com/java-5/"/>
    <id>http://www.windknew.com/java-5/</id>
    <published>2020-02-11T09:00:19.000Z</published>
    <updated>2020-02-13T02:03:50.166Z</updated>
    
    <content type="html"><![CDATA[<h2 id="重写-Override"><a href="#重写-Override" class="headerlink" title="重写(Override)"></a>重写(Override)</h2><p>重写是子类对父类的允许访问的方法的实现过程进行重新编写, 返回值和形参都不能改变。<strong>即外壳不变，核心重写！</strong></p><p>重写的好处在于子类可以根据需要，定义特定于自己的行为。 也就是说子类能够根据需要实现父类的方法。</p><p>重写方法不能抛出新的检查异常或者比被重写方法申明更加宽泛的异常。例如： 父类的一个方法申明了一个检查异常 IOException，但是在重写这个方法的时候不能抛出 Exception 异常，因为 Exception 是 IOException 的父类，只能抛出 IOException 的子类异常。</p><p>在面向对象原则里，重写意味着可以重写任何现有方法。实例如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">move</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"动物可以移动"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Dog</span> <span class="keyword">extends</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">move</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"狗可以跑和走"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">TestDog</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String args[])</span></span>&#123;</span><br><span class="line">      Animal a = <span class="keyword">new</span> Animal(); <span class="comment">// Animal 对象</span></span><br><span class="line">      Animal b = <span class="keyword">new</span> Dog(); <span class="comment">// Dog 对象</span></span><br><span class="line"> </span><br><span class="line">      a.move();<span class="comment">// 执行 Animal 类的方法</span></span><br><span class="line"> </span><br><span class="line">      b.move();<span class="comment">//执行 Dog 类的方法</span></span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上实例编译运行结果如下：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">动物可以移动</span><br><span class="line">狗可以跑和走</span><br></pre></td></tr></table></figure><p>在上面的例子中可以看到，尽管 b 属于 Animal 类型，但是它运行的是 Dog 类的 move方法。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">move</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"动物可以移动"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Dog</span> <span class="keyword">extends</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">move</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"狗可以跑和走"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">bark</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"狗可以吠叫"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">TestDog</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String args[])</span></span>&#123;</span><br><span class="line">      Animal a = <span class="keyword">new</span> Animal(); <span class="comment">// Animal 对象</span></span><br><span class="line">      Animal b = <span class="keyword">new</span> Dog(); <span class="comment">// Dog 对象</span></span><br><span class="line"> </span><br><span class="line">      a.move();<span class="comment">// 执行 Animal 类的方法</span></span><br><span class="line">      b.move();<span class="comment">//执行 Dog 类的方法</span></span><br><span class="line">      b.bark();</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上实例编译运行结果如下：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line">TestDog.java:30: cannot find symbol</span><br><span class="line">symbol  : method bark()</span><br><span class="line">location: class Animal</span><br><span class="line">                b.bark();</span><br><span class="line">                 ^</span><br></pre></td></tr></table></figure><p>该程序将抛出一个编译错误，因为b的引用类型Animal没有bark方法。</p><h2 id="方法的重写规则"><a href="#方法的重写规则" class="headerlink" title="方法的重写规则"></a>方法的重写规则</h2><ul><li>参数列表必须完全与被重写方法的相同。</li><li>返回类型与被重写方法的返回类型可以不相同，但是必须是父类返回值的派生类（java5 及更早版本返回类型要一样，java7 及更高版本可以不同）。</li><li>访问权限不能比父类中被重写的方法的访问权限更低。例如：如果父类的一个方法被声明为 public，那么在子类中重写该方法就不能声明为 protected。</li><li>父类的成员方法只能被它的子类重写。</li><li>声明为 final 的方法不能被重写。</li><li>声明为 static 的方法不能被重写，但是能够被再次声明。</li><li>子类和父类在同一个包中，那么子类可以重写父类所有方法，除了声明为 private 和 final 的方法。</li><li>子类和父类不在同一个包中，那么子类只能够重写父类的声明为 public 和 protected 的非 final 方法。</li><li>重写的方法能够抛出任何非强制异常，无论被重写的方法是否抛出异常。但是，重写的方法不能抛出新的强制性异常，或者比被重写方法声明的更广泛的强制性异常，反之则可以。</li><li>构造方法不能被重写。</li><li>如果不能继承一个方法，则不能重写这个方法。</li></ul><h2 id="Super-关键字的使用"><a href="#Super-关键字的使用" class="headerlink" title="Super 关键字的使用"></a>Super 关键字的使用</h2><p>当需要在子类中调用父类的被重写方法时，要使用 super 关键</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">move</span><span class="params">()</span></span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"动物可以移动"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Dog</span> <span class="keyword">extends</span> <span class="title">Animal</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">move</span><span class="params">()</span></span>&#123;</span><br><span class="line">      <span class="keyword">super</span>.move(); <span class="comment">// 应用super类的方法</span></span><br><span class="line">      System.out.println(<span class="string">"狗可以跑和走"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">TestDog</span></span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String args[])</span></span>&#123;</span><br><span class="line"> </span><br><span class="line">      Animal b = <span class="keyword">new</span> Dog(); <span class="comment">// Dog 对象</span></span><br><span class="line">      b.move(); <span class="comment">//执行 Dog类的方法</span></span><br><span class="line"> </span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上实例编译运行结果如下：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">动物可以移动</span><br><span class="line">狗可以跑和走</span><br></pre></td></tr></table></figure><h2 id="重载-Overload"><a href="#重载-Overload" class="headerlink" title="重载(Overload)"></a>重载(Overload)</h2><p>重载(overloading) 是在一个类里面，方法名字相同，而参数不同。返回类型可以相同也可以不同。</p><p>每个重载的方法（或者构造函数）都必须有一个独一无二的参数类型列表。</p><p>最常用的地方就是构造器的重载。</p><p><strong>重载规则:</strong></p><ul><li>被重载的方法必须改变参数列表(参数个数或类型不一样)；</li><li>被重载的方法可以改变返回类型；</li><li>被重载的方法可以改变访问修饰符；</li><li>被重载的方法可以声明新的或更广的检查异常；</li><li>方法能够在同一个类中或者在一个子类中被重载。</li><li>无法以返回值类型作为重载函数的区分标准。</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Overloading</span> </span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">test</span><span class="params">()</span></span>&#123;</span><br><span class="line">        System.out.println(<span class="string">"test1"</span>);</span><br><span class="line">        <span class="keyword">return</span> <span class="number">1</span>;</span><br><span class="line">    &#125;</span><br><span class="line"> </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">test</span><span class="params">(<span class="keyword">int</span> a)</span></span>&#123;</span><br><span class="line">        System.out.println(<span class="string">"test2"</span>);</span><br><span class="line">    &#125;   </span><br><span class="line"> </span><br><span class="line">    <span class="comment">//以下两个参数类型顺序不同</span></span><br><span class="line">    <span class="function"><span class="keyword">public</span> String <span class="title">test</span><span class="params">(<span class="keyword">int</span> a,String s)</span></span>&#123;</span><br><span class="line">        System.out.println(<span class="string">"test3"</span>);</span><br><span class="line">        <span class="keyword">return</span> <span class="string">"returntest3"</span>;</span><br><span class="line">    &#125;   </span><br><span class="line"> </span><br><span class="line">    <span class="function"><span class="keyword">public</span> String <span class="title">test</span><span class="params">(String s,<span class="keyword">int</span> a)</span></span>&#123;</span><br><span class="line">        System.out.println(<span class="string">"test4"</span>);</span><br><span class="line">        <span class="keyword">return</span> <span class="string">"returntest4"</span>;</span><br><span class="line">    &#125;   </span><br><span class="line"> </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span></span>&#123;</span><br><span class="line">        Overloading o = <span class="keyword">new</span> Overloading();</span><br><span class="line">        System.out.println(o.test());</span><br><span class="line">        o.test(<span class="number">1</span>);</span><br><span class="line">        System.out.println(o.test(<span class="number">1</span>,<span class="string">"test3"</span>));</span><br><span class="line">        System.out.println(o.test(<span class="string">"test4"</span>,<span class="number">1</span>));</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>结果如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">Compiling Overloading.java.......</span><br><span class="line">-----------OUTPUT-----------</span><br><span class="line">test1</span><br><span class="line"><span class="number">1</span></span><br><span class="line">test2</span><br><span class="line">test3</span><br><span class="line">returntest3</span><br><span class="line">test4</span><br><span class="line">returntest4</span><br><span class="line">[Finished in <span class="number">1.4</span>s]</span><br></pre></td></tr></table></figure><h2 id="重写与重载之间的区别"><a href="#重写与重载之间的区别" class="headerlink" title="重写与重载之间的区别"></a>重写与重载之间的区别</h2><table><thead><tr><th style="text-align:left">区别点</th><th style="text-align:left">重载方法</th><th style="text-align:left">重写方法</th></tr></thead><tbody><tr><td style="text-align:left">参数列表</td><td style="text-align:left">必须修改</td><td style="text-align:left">一定不能修改</td></tr><tr><td style="text-align:left">返回类型</td><td style="text-align:left">可以修改</td><td style="text-align:left">一定不能修改</td></tr><tr><td style="text-align:left">异常</td><td style="text-align:left">可以修改</td><td style="text-align:left">可以减少或删除，一定不能抛出新的或者更广的异常</td></tr><tr><td style="text-align:left">访问</td><td style="text-align:left">可以修改</td><td style="text-align:left">一定不能做更严格的限制（可以降低限制）</td></tr></tbody></table><h2 id="总结"><a href="#总结" class="headerlink" title="总结"></a>总结</h2><p>方法的重写(Overriding)和重载(Overloading)是java多态性的不同表现，重写是父类与子类之间多态性的一种表现，重载可以理解成多态的具体表现形式。</p><ul><li>(1)方法重载是一个类中定义了多个方法名相同,而他们的参数的数量不同或数量相同而类型和次序不同,则称为方法的重载(Overloading)。</li><li>(2)方法重写是在子类存在方法与父类的方法的名字相同,而且参数的个数与类型一样,返回值也一样的方法,就称为重写(Overriding)。</li><li>(3)方法重载是一个类的多态性表现,而方法重写是子类与父类的一种多态性表现。</li></ul><p><img src="https://www.runoob.com/wp-content/uploads/2013/12/overloading-vs-overriding.png" alt=""></p><p><img src="https://www.runoob.com/wp-content/uploads/2013/12/20171102-1.png" alt=""></p><h1 id="多态"><a href="#多态" class="headerlink" title="多态"></a>多态</h1><p>多态是同一个行为具有多个不同表现形式或形态的能力。</p><p>多态就是同一个接口，使用不同的实例而执行不同操作</p><p>比如键盘上的按键，在不同应用有不同的功能</p><h3 id="多态的优点"><a href="#多态的优点" class="headerlink" title="多态的优点"></a>多态的优点</h3><ul><li>消除类型之间的耦合关系</li><li>可替换性</li><li>可扩充性</li><li>接口性</li><li>灵活性</li><li>简化性</li></ul><h3 id="多态存在的三个必要条件"><a href="#多态存在的三个必要条件" class="headerlink" title="多态存在的三个必要条件"></a>多态存在的三个必要条件</h3><ul><li>继承</li><li>重写</li><li>父类引用指向子类对象</li></ul><p>比如：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">Parent p = new Child();</span><br></pre></td></tr></table></figure><p>当使用多态方式调用方法时，首先检查父类中是否有该方法，如果没有，则编译错误；如果有，再去调用子类的同名方法。</p><p>多态的好处：可以使程序有良好的扩展，并可以对所有类的对象进行通用处理。</p><p>如下列多态例子:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Test</span> </span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span> </span>&#123;</span><br><span class="line">      show(<span class="keyword">new</span> Cat());  <span class="comment">// 以 Cat 对象调用 show 方法</span></span><br><span class="line">      show(<span class="keyword">new</span> Dog());  <span class="comment">// 以 Dog 对象调用 show 方法</span></span><br><span class="line">                </span><br><span class="line">      Animal a = <span class="keyword">new</span> Cat();  <span class="comment">// 向上转型  </span></span><br><span class="line">      a.eat();               <span class="comment">// 调用的是 Cat 的 eat</span></span><br><span class="line">      Cat c = (Cat)a;        <span class="comment">// 向下转型  </span></span><br><span class="line">      c.work();        <span class="comment">// 调用的是 Cat 的 work</span></span><br><span class="line">  &#125;  </span><br><span class="line">            </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">show</span><span class="params">(Animal a)</span>  </span>&#123;</span><br><span class="line">      a.eat();  </span><br><span class="line">        <span class="comment">// 类型判断</span></span><br><span class="line">        <span class="keyword">if</span> (a <span class="keyword">instanceof</span> Cat)  &#123;  <span class="comment">// 猫做的事情 </span></span><br><span class="line">            Cat c = (Cat)a;  </span><br><span class="line">            c.work();  </span><br><span class="line">        &#125; <span class="keyword">else</span> <span class="keyword">if</span> (a <span class="keyword">instanceof</span> Dog) &#123; <span class="comment">// 狗做的事情 </span></span><br><span class="line">            Dog c = (Dog)a;  </span><br><span class="line">            c.work();  </span><br><span class="line">        &#125;  </span><br><span class="line">    &#125;  </span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">abstract</span> <span class="class"><span class="keyword">class</span> <span class="title">Animal</span> </span>&#123;  </span><br><span class="line">    <span class="function"><span class="keyword">abstract</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>;  </span><br><span class="line">&#125;  </span><br><span class="line">  </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Cat</span> <span class="keyword">extends</span> <span class="title">Animal</span> </span>&#123;  </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span> </span>&#123;  </span><br><span class="line">        System.out.println(<span class="string">"吃鱼"</span>);  </span><br><span class="line">    &#125;  </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">work</span><span class="params">()</span> </span>&#123;  </span><br><span class="line">        System.out.println(<span class="string">"抓老鼠"</span>);  </span><br><span class="line">    &#125;  </span><br><span class="line">&#125;  </span><br><span class="line">  </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Dog</span> <span class="keyword">extends</span> <span class="title">Animal</span> </span>&#123;  </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span> </span>&#123;  </span><br><span class="line">        System.out.println(<span class="string">"吃骨头"</span>);  </span><br><span class="line">    &#125;  </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">work</span><span class="params">()</span> </span>&#123;  </span><br><span class="line">        System.out.println(<span class="string">"看家"</span>);  </span><br><span class="line">    &#125;  </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>执行以上程序，输出结果为：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br></pre></td><td class="code"><pre><span class="line">吃鱼</span><br><span class="line">抓老鼠</span><br><span class="line">吃骨头</span><br><span class="line">看家</span><br><span class="line">吃鱼</span><br><span class="line">抓老鼠</span><br></pre></td></tr></table></figure><h2 id="虚函数"><a href="#虚函数" class="headerlink" title="虚函数"></a>虚函数</h2><p>虚函数的存在是为了多态。</p><p>Java 中其实没有虚函数的概念，它的普通函数就相当于 C++ 的虚函数，动态绑定是Java的默认行为。如果 Java 中不希望某个函数具有虚函数特性，可以加上 final 关键字变成非虚函数。</p><h3 id="重写"><a href="#重写" class="headerlink" title="重写"></a>重写</h3><p>我们将介绍在 Java 中，当设计类时，被重写的方法的行为怎样影响多态性。</p><p>我们已经讨论了方法的重写，也就是子类能够重写父类的方法。</p><p>当子类对象调用重写的方法时，调用的是子类的方法，而不是父类中被重写的方法。</p><p>要想调用父类中被重写的方法，则必须使用关键字 <strong>super</strong>。如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名 : Employee.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Employee</span> </span>&#123;</span><br><span class="line">   <span class="keyword">private</span> String name;</span><br><span class="line">   <span class="keyword">private</span> String address;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">int</span> number;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="title">Employee</span><span class="params">(String name, String address, <span class="keyword">int</span> number)</span> </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Employee 构造函数"</span>);</span><br><span class="line">      <span class="keyword">this</span>.name = name;</span><br><span class="line">      <span class="keyword">this</span>.address = address;</span><br><span class="line">      <span class="keyword">this</span>.number = number;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">mailCheck</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"邮寄支票给： "</span> + <span class="keyword">this</span>.name</span><br><span class="line">       + <span class="string">" "</span> + <span class="keyword">this</span>.address);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">toString</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> name + <span class="string">" "</span> + address + <span class="string">" "</span> + number;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">getName</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> name;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> String <span class="title">getAddress</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> address;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setAddress</span><span class="params">(String newAddress)</span> </span>&#123;</span><br><span class="line">      address = newAddress;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">int</span> <span class="title">getNumber</span><span class="params">()</span> </span>&#123;</span><br><span class="line">     <span class="keyword">return</span> number;</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>假设下面的类继承Employee类：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名 : Salary.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Salary</span> <span class="keyword">extends</span> <span class="title">Employee</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">double</span> salary; <span class="comment">// 全年工资</span></span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="title">Salary</span><span class="params">(String name, String address, <span class="keyword">int</span> number, <span class="keyword">double</span> salary)</span> </span>&#123;</span><br><span class="line">       <span class="keyword">super</span>(name, address, number);</span><br><span class="line">       setSalary(salary);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">mailCheck</span><span class="params">()</span> </span>&#123;</span><br><span class="line">       System.out.println(<span class="string">"Salary 类的 mailCheck 方法 "</span>);</span><br><span class="line">       System.out.println(<span class="string">"邮寄支票给："</span> + getName()</span><br><span class="line">       + <span class="string">" ，工资为："</span> + salary);</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">double</span> <span class="title">getSalary</span><span class="params">()</span> </span>&#123;</span><br><span class="line">       <span class="keyword">return</span> salary;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setSalary</span><span class="params">(<span class="keyword">double</span> newSalary)</span> </span>&#123;</span><br><span class="line">       <span class="keyword">if</span>(newSalary &gt;= <span class="number">0.0</span>) &#123;</span><br><span class="line">          salary = newSalary;</span><br><span class="line">       &#125;</span><br><span class="line">   &#125;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">double</span> <span class="title">computePay</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"计算工资，付给："</span> + getName());</span><br><span class="line">      <span class="keyword">return</span> salary/<span class="number">52</span>;</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment">/* 文件名 : VirtualDemo.java */</span></span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">VirtualDemo</span> </span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String [] args)</span> </span>&#123;</span><br><span class="line">      Salary s = <span class="keyword">new</span> Salary(<span class="string">"员工 A"</span>, <span class="string">"北京"</span>, <span class="number">3</span>, <span class="number">3600.00</span>);</span><br><span class="line">      Employee e = <span class="keyword">new</span> Salary(<span class="string">"员工 B"</span>, <span class="string">"上海"</span>, <span class="number">2</span>, <span class="number">2400.00</span>);</span><br><span class="line">      System.out.println(<span class="string">"使用 Salary 的引用调用 mailCheck -- "</span>);</span><br><span class="line">      s.mailCheck();</span><br><span class="line">      System.out.println(<span class="string">"\n使用 Employee 的引用调用 mailCheck--"</span>);</span><br><span class="line">      e.mailCheck();</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上实例编译运行结果如下：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">Employee 构造函数</span><br><span class="line">Employee 构造函数</span><br><span class="line">使用 Salary 的引用调用 mailCheck -- </span><br><span class="line">Salary 类的 mailCheck 方法 </span><br><span class="line">邮寄支票给：员工 A ，工资为：3600.0</span><br><span class="line"></span><br><span class="line">使用 Employee 的引用调用 mailCheck--</span><br><span class="line">Salary 类的 mailCheck 方法 </span><br><span class="line">邮寄支票给：员工 B ，工资为：2400.0</span><br></pre></td></tr></table></figure><h3 id="例子解析"><a href="#例子解析" class="headerlink" title="例子解析"></a>例子解析</h3><ul><li>实例中，实例化了两个 Salary 对象：一个使用 Salary 引用 s，另一个使用 Employee 引用 e。</li><li>当调用 s.mailCheck() 时，编译器在编译时会在 Salary 类中找到 mailCheck()，执行过程 JVM 就调用 Salary 类的 mailCheck()。</li><li>因为 e 是 Employee 的引用，所以调用 e 的 mailCheck() 方法时，编译器会去 Employee 类查找 mailCheck() 方法 。</li><li>在编译的时候，编译器使用 Employee 类中的 mailCheck() 方法验证该语句， 但是在运行的时候，Java虚拟机(JVM)调用的是 Salary 类中的 mailCheck() 方法。</li></ul><p>以上整个过程被称为虚拟方法调用，该方法被称为虚拟方法。</p><p>Java中所有的方法都能以这种方式表现，因此，重写的方法能在运行时调用，不管编译的时候源代码中引用变量是什么数据类型。</p><h2 id="态的实现方式"><a href="#态的实现方式" class="headerlink" title="态的实现方式"></a>态的实现方式</h2><h3 id="方式一：重写："><a href="#方式一：重写：" class="headerlink" title="方式一：重写："></a>方式一：重写：</h3><p>就是java重写与重载</p><h3 id="方式二：接口"><a href="#方式二：接口" class="headerlink" title="方式二：接口"></a>方式二：接口</h3><ul><li>生活中的接口最具代表性的就是插座，例如一个三接头的插头都能接在三孔插座中，因为这个是每个国家都有各自规定的接口规则，有可能到国外就不行，那是因为国外自己定义的接口类型。</li><li>java中的接口类似于生活中的接口，就是一些方法特征的集合，但没有方法的实现。具体可以看 <a href="https://www.runoob.com/java/java-interfaces.html" target="_blank" rel="noopener">java接口</a> 这一章节的内容。</li></ul>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h2 id=&quot;重写-Override&quot;&gt;&lt;a href=&quot;#重写-Override&quot; class=&quot;headerlink&quot; title=&quot;重写(Override)&quot;&gt;&lt;/a&gt;重写(Override)&lt;/h2&gt;&lt;p&gt;重写是子类对父类的允许访问的方法的实现过程进行重新编写, 返回值
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家学习java第五天（Java面向对象-继承）</title>
    <link href="http://www.windknew.com/java-4/"/>
    <id>http://www.windknew.com/java-4/</id>
    <published>2020-02-10T09:38:11.000Z</published>
    <updated>2020-02-13T02:03:54.003Z</updated>
    
    <content type="html"><![CDATA[<h1 id="Java继承"><a href="#Java继承" class="headerlink" title="Java继承"></a>Java继承</h1><h2 id="继承的概念"><a href="#继承的概念" class="headerlink" title="继承的概念"></a>继承的概念</h2><p>继承时java面向对象编程技术的一块基石，因为它允许创建分等级层次的类</p><p>继承就是子类继承父类的特征和行为，使得子类对象具有父类的实例域和方法，或子类从父类集成方法，使得子类具有父亲相同的行为</p><h2 id="类的继承格式"><a href="#类的继承格式" class="headerlink" title="类的继承格式"></a>类的继承格式</h2><p>在java中通过extends关键字可以申明一个类是从另一个类继承而来的，一般形式如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> 父类 </span>&#123;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> 子类 <span class="keyword">extends</span> 父类 </span>&#123;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="类的好处"><a href="#类的好处" class="headerlink" title="类的好处"></a>类的好处</h2><p>开发动物类，其中动物分别为企鹅以及老鼠，要求如下：</p><ul><li>企鹅：属性（姓名，id），方法（吃，睡，自我介绍）</li><li>老鼠：属性（姓名，id），方法（吃，睡，自我介绍）</li></ul><p><strong>企鹅类：</strong></p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Penguin</span> </span>&#123; </span><br><span class="line">    <span class="keyword">private</span> String name; </span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">int</span> id; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Penguin</span><span class="params">(String myName, <span class="keyword">int</span>  myid)</span> </span>&#123; </span><br><span class="line">        name = myName; </span><br><span class="line">        id = myid; </span><br><span class="line">    &#125; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>&#123; </span><br><span class="line">        System.out.println(name+<span class="string">"正在吃"</span>); </span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">sleep</span><span class="params">()</span></span>&#123;</span><br><span class="line">        System.out.println(name+<span class="string">"正在睡"</span>);</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">introduction</span><span class="params">()</span> </span>&#123; </span><br><span class="line">        System.out.println(<span class="string">"大家好！我是"</span>         + id + <span class="string">"号"</span> + name + <span class="string">"."</span>); </span><br><span class="line">    &#125; </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>老鼠类：</strong></p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Mouse</span> </span>&#123; </span><br><span class="line">    <span class="keyword">private</span> String name; </span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">int</span> id; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Mouse</span><span class="params">(String myName, <span class="keyword">int</span>  myid)</span> </span>&#123; </span><br><span class="line">        name = myName; </span><br><span class="line">        id = myid; </span><br><span class="line">    &#125; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>&#123; </span><br><span class="line">        System.out.println(name+<span class="string">"正在吃"</span>); </span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">sleep</span><span class="params">()</span></span>&#123;</span><br><span class="line">        System.out.println(name+<span class="string">"正在睡"</span>);</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">introduction</span><span class="params">()</span> </span>&#123; </span><br><span class="line">        System.out.println(<span class="string">"大家好！我是"</span>         + id + <span class="string">"号"</span> + name + <span class="string">"."</span>); </span><br><span class="line">    &#125; </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>从这两段代码可以看出来，代码存在重复了，所以要解决这两段代码的问题，就需要继承，将两段代码中相同的部分提取出来组成 一个父类：</p><p><strong>公共父类</strong></p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Animal</span> </span>&#123; </span><br><span class="line">    <span class="keyword">private</span> String name;  </span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">int</span> id; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Animal</span><span class="params">(String myName, <span class="keyword">int</span> myid)</span> </span>&#123; </span><br><span class="line">        name = myName; </span><br><span class="line">        id = myid;</span><br><span class="line">    &#125; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>&#123; </span><br><span class="line">        System.out.println(name+<span class="string">"正在吃"</span>); </span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">sleep</span><span class="params">()</span></span>&#123;</span><br><span class="line">        System.out.println(name+<span class="string">"正在睡"</span>);</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">introduction</span><span class="params">()</span> </span>&#123; </span><br><span class="line">        System.out.println(<span class="string">"大家好！我是"</span>         + id + <span class="string">"号"</span> + name + <span class="string">"."</span>); </span><br><span class="line">    &#125; </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>这个Animal类就可以作为一个父类，然后企鹅类和老鼠类继承这个类之后，就具有父类当中的属性和方法，子类就不会存在重复的代码，维护性也提高，代码也更加简洁，提高代码的复用性（复用性主要是可以多次使用，不用再多次写同样的代码） 继承之后的代码：</p><p><strong>企鹅类</strong></p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Penguin</span> <span class="keyword">extends</span> <span class="title">Animal</span> </span>&#123; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Penguin</span><span class="params">(String myName, <span class="keyword">int</span> myid)</span> </span>&#123; </span><br><span class="line">        <span class="keyword">super</span>(myName, myid); </span><br><span class="line">    &#125; </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>老鼠类</strong></p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Mouse</span> <span class="keyword">extends</span> <span class="title">Animal</span> </span>&#123; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Mouse</span><span class="params">(String myName, <span class="keyword">int</span> myid)</span> </span>&#123; </span><br><span class="line">        <span class="keyword">super</span>(myName, myid); </span><br><span class="line">    &#125; </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="继承类型"><a href="#继承类型" class="headerlink" title="继承类型"></a>继承类型</h2><p>需要注意的是 Java 不支持多继承，但支持多重继承。</p><p><img src="https://www.runoob.com/wp-content/uploads/2013/12/types_of_inheritance-1.png" alt=""></p><h2 id="继承的特性"><a href="#继承的特性" class="headerlink" title="继承的特性"></a>继承的特性</h2><ul><li>子类拥有父类非 private 的属性、方法。</li><li>子类可以拥有自己的属性和方法，即子类可以对父类进行扩展。</li><li>子类可以用自己的方式实现父类的方法。</li><li>Java 的继承是单继承，但是可以多重继承，单继承就是一个子类只能继承一个父类，多重继承就是，例如 A 类继承 B 类，B 类继承 C 类，所以按照关系就是 C 类是 B 类的父类，B 类是 A 类的父类，这是 Java 继承区别于 C++ 继承的一个特性。</li><li>提高了类之间的耦合性（继承的缺点，耦合度高就会造成代码之间的联系越紧密，代码独立性越差）。</li></ul><p>继承可以使用 extends 和 implements 这两个关键字来实现继承，而且所有的类都是继承于 java.lang.Object，当一个类没有继承的两个关键字，则默认继承object（这个类在 <strong>java.lang</strong> 包中，所以不需要 <strong>import</strong>）祖先类。</p><h3 id="extends关键字"><a href="#extends关键字" class="headerlink" title="extends关键字"></a>extends关键字</h3><p>在 Java 中，类的继承是单一继承，也就是说，一个子类只能拥有一个父类，所以 extends 只能继承一个类。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Animal</span> </span>&#123; </span><br><span class="line">    <span class="keyword">private</span> String name;   </span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">int</span> id; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Animal</span><span class="params">(String myName, String myid)</span> </span>&#123; </span><br><span class="line">        <span class="comment">//初始化属性值</span></span><br><span class="line">    &#125; </span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span> </span>&#123;  <span class="comment">//吃东西方法的具体实现  &#125; </span></span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">sleep</span><span class="params">()</span> </span>&#123; <span class="comment">//睡觉方法的具体实现  &#125; </span></span><br><span class="line">&#125; </span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Penguin</span>  <span class="keyword">extends</span>  <span class="title">Animal</span></span>&#123; </span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h3 id="implements关键字"><a href="#implements关键字" class="headerlink" title="implements关键字"></a>implements关键字</h3><p>使用 implements 关键字可以变相的使java具有多继承的特性，使用范围为类继承接口的情况，可以同时继承多个接口（接口跟接口之间采用逗号分隔）。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">A</span> </span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span></span>;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">sleep</span><span class="params">()</span></span>;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">interface</span> <span class="title">B</span> </span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">show</span><span class="params">()</span></span>;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">C</span> <span class="keyword">implements</span> <span class="title">A</span>,<span class="title">B</span> </span>&#123;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h3 id="super-与-this-关键字"><a href="#super-与-this-关键字" class="headerlink" title="super 与 this 关键字"></a>super 与 this 关键字</h3><p>super关键字：我们可以通过super关键字来实现对父类成员的访问，用来引用当前对象的父类。</p><p>this关键字：指向自己的引用。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Animal</span> </span>&#123;</span><br><span class="line">  <span class="function"><span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span> </span>&#123;</span><br><span class="line">    System.out.println(<span class="string">"animal : eat"</span>);</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">Dog</span> <span class="keyword">extends</span> <span class="title">Animal</span> </span>&#123;</span><br><span class="line">  <span class="function"><span class="keyword">void</span> <span class="title">eat</span><span class="params">()</span> </span>&#123;</span><br><span class="line">    System.out.println(<span class="string">"dog : eat"</span>);</span><br><span class="line">  &#125;</span><br><span class="line">  <span class="function"><span class="keyword">void</span> <span class="title">eatTest</span><span class="params">()</span> </span>&#123;</span><br><span class="line">    <span class="keyword">this</span>.eat();   <span class="comment">// this 调用自己的方法</span></span><br><span class="line">    <span class="keyword">super</span>.eat();  <span class="comment">// super 调用父类方法</span></span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Test</span> </span>&#123;</span><br><span class="line">  <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span> </span>&#123;</span><br><span class="line">    Animal a = <span class="keyword">new</span> Animal();</span><br><span class="line">    a.eat();</span><br><span class="line">    Dog d = <span class="keyword">new</span> Dog();</span><br><span class="line">    d.eatTest();</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>输出结果为：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">animal : eat</span><br><span class="line">dog : eat</span><br><span class="line">animal : eat</span><br></pre></td></tr></table></figure><h3 id="final关键字"><a href="#final关键字" class="headerlink" title="final关键字"></a>final关键字</h3><p>final 关键字声明类可以把类定义为不能继承的，即最终类；或者用于修饰方法，该方法不能被子类重写：</p><ul><li><p>声明类：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">final class 类名 &#123;//类体&#125;</span><br></pre></td></tr></table></figure></li><li><p>声明方法：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">修饰符(public/private/default/protected) final 返回值类型 方法名()&#123;//方法体&#125;</span><br></pre></td></tr></table></figure></li></ul><p><strong>注</strong>:实例变量也可以被定义为 final，被定义为 final 的变量不能被修改。被声明为 final 类的方法自动地声明为 final，但是实例变量并不是 final</p><hr><h2 id="构造器"><a href="#构造器" class="headerlink" title="构造器"></a>构造器</h2><p>子类是不继承父类的构造器（构造方法或者构造函数）的，它只是调用（隐式或显式）。如果父类的构造器带有参数，则必须在子类的构造器中显式地通过 <strong>super</strong> 关键字调用父类的构造器并配以适当的参数列表。</p><p>如果父类构造器没有参数，则在子类的构造器中不需要使用 <strong>super</strong> 关键字调用父类构造器，系统会自动调用父类的无参构造器。</p><h2 id="实例"><a href="#实例" class="headerlink" title="实例"></a>实例</h2><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">SuperClass</span> </span>&#123;</span><br><span class="line">  <span class="keyword">private</span> <span class="keyword">int</span> n;</span><br><span class="line">  SuperClass()&#123;</span><br><span class="line">    System.out.println(<span class="string">"SuperClass()"</span>);</span><br><span class="line">  &#125;</span><br><span class="line">  SuperClass(<span class="keyword">int</span> n) &#123;</span><br><span class="line">    System.out.println(<span class="string">"SuperClass(int n)"</span>);</span><br><span class="line">    <span class="keyword">this</span>.n = n;</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">// SubClass 类继承</span></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">SubClass</span> <span class="keyword">extends</span> <span class="title">SuperClass</span></span>&#123;</span><br><span class="line">  <span class="keyword">private</span> <span class="keyword">int</span> n;</span><br><span class="line">  </span><br><span class="line">  SubClass()&#123; <span class="comment">// 自动调用父类的无参数构造器</span></span><br><span class="line">    System.out.println(<span class="string">"SubClass"</span>);</span><br><span class="line">  &#125;  </span><br><span class="line">  </span><br><span class="line">  <span class="function"><span class="keyword">public</span> <span class="title">SubClass</span><span class="params">(<span class="keyword">int</span> n)</span></span>&#123; </span><br><span class="line">    <span class="keyword">super</span>(<span class="number">300</span>);  <span class="comment">// 调用父类中带有参数的构造器</span></span><br><span class="line">    System.out.println(<span class="string">"SubClass(int n):"</span>+n);</span><br><span class="line">    <span class="keyword">this</span>.n = n;</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="comment">// SubClass2 类继承</span></span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">SubClass2</span> <span class="keyword">extends</span> <span class="title">SuperClass</span></span>&#123;</span><br><span class="line">  <span class="keyword">private</span> <span class="keyword">int</span> n;</span><br><span class="line">  </span><br><span class="line">  SubClass2()&#123;</span><br><span class="line">    <span class="keyword">super</span>(<span class="number">300</span>);  <span class="comment">// 调用父类中带有参数的构造器</span></span><br><span class="line">    System.out.println(<span class="string">"SubClass2"</span>);</span><br><span class="line">  &#125;  </span><br><span class="line">  </span><br><span class="line">  <span class="function"><span class="keyword">public</span> <span class="title">SubClass2</span><span class="params">(<span class="keyword">int</span> n)</span></span>&#123; <span class="comment">// 自动调用父类的无参数构造器</span></span><br><span class="line">    System.out.println(<span class="string">"SubClass2(int n):"</span>+n);</span><br><span class="line">    <span class="keyword">this</span>.n = n;</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">TestSuperSub</span></span>&#123;</span><br><span class="line">  <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span> <span class="params">(String args[])</span></span>&#123;</span><br><span class="line">    System.out.println(<span class="string">"------SubClass 类继承------"</span>);</span><br><span class="line">    SubClass sc1 = <span class="keyword">new</span> SubClass();</span><br><span class="line">    SubClass sc2 = <span class="keyword">new</span> SubClass(<span class="number">100</span>); </span><br><span class="line">    System.out.println(<span class="string">"------SubClass2 类继承------"</span>);</span><br><span class="line">    SubClass2 sc3 = <span class="keyword">new</span> SubClass2();</span><br><span class="line">    SubClass2 sc4 = <span class="keyword">new</span> SubClass2(<span class="number">200</span>); </span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>输出结果为：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line">------SubClass 类继承------</span><br><span class="line">SuperClass()</span><br><span class="line">SubClass</span><br><span class="line">SuperClass(int n)</span><br><span class="line">SubClass(int n):100</span><br><span class="line">------SubClass2 类继承------</span><br><span class="line">SuperClass(int n)</span><br><span class="line">SubClass2</span><br><span class="line">SuperClass()</span><br><span class="line">SubClass2(int n):200</span><br></pre></td></tr></table></figure>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;Java继承&quot;&gt;&lt;a href=&quot;#Java继承&quot; class=&quot;headerlink&quot; title=&quot;Java继承&quot;&gt;&lt;/a&gt;Java继承&lt;/h1&gt;&lt;h2 id=&quot;继承的概念&quot;&gt;&lt;a href=&quot;#继承的概念&quot; class=&quot;headerlink&quot; title=
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="学习" scheme="http://www.windknew.com/blog/tags/%E5%AD%A6%E4%B9%A0/"/>
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家学习lava第四天（修饰符）</title>
    <link href="http://www.windknew.com/java-3/"/>
    <id>http://www.windknew.com/java-3/</id>
    <published>2020-02-09T09:52:56.000Z</published>
    <updated>2020-02-13T02:03:57.402Z</updated>
    
    <content type="html"><![CDATA[<h1 id="Java-修饰符"><a href="#Java-修饰符" class="headerlink" title="Java 修饰符"></a>Java 修饰符</h1><p>Java语言提供了很多修饰符，主要分为一下两类：</p><ul><li>访问修饰符</li><li>非访问修饰符</li></ul><p>修饰符用来定义类，方法或者变量，通常放在语句的最前端，例如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Classname</span></span>&#123;</span><br><span class="line">    <span class="comment">//...</span></span><br><span class="line">&#125;</span><br><span class="line"><span class="keyword">private</span> boollean myFlag;</span><br><span class="line"><span class="keyword">static</span> <span class="keyword">final</span> <span class="keyword">double</span> weeks = <span class="number">9.5</span>;</span><br><span class="line">pritected <span class="keyword">static</span> <span class="keyword">final</span> <span class="keyword">int</span> BOXWIDTH = <span class="number">42</span>;</span><br><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] arguments)</span></span>&#123;</span><br><span class="line">    <span class="comment">//方法体</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h1 id="访问控制修饰符"><a href="#访问控制修饰符" class="headerlink" title="访问控制修饰符"></a>访问控制修饰符</h1><p>Java中，可以使用访问控制符来保护对类，变量，方法和构造方法的访问，Java支持4种不同的访问权限。</p><ul><li><strong>default</strong>(即默认，什么也不写)：在同一包内可见，不使用任何修饰符，适用对象：类、接口、变量、方法。 </li><li><strong>private</strong>：在同一类内可见，使用对象：变量，方法。<strong>注意不能修饰类（外部类）</strong></li><li><strong>public</strong>：都所有类可见。使用对象：类，接口，变量，方法</li><li><strong>protected</strong>：对同一包内的类和所有子类可见，使用对象：变量，方法。<strong>(注意不能修饰类（外部类）)</strong></li></ul><h2 id="访问控制"><a href="#访问控制" class="headerlink" title="访问控制"></a><strong>访问控制</strong></h2><table><thead><tr><th style="text-align:left">修饰符</th><th style="text-align:left">当前类</th><th style="text-align:left">同一包内</th><th style="text-align:left">子孙类(同一包)</th><th style="text-align:left">子孙类(不同包)</th><th style="text-align:left">其他包</th></tr></thead><tbody><tr><td style="text-align:left"><code>public</code></td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">Y</td></tr><tr><td style="text-align:left"><code>protected</code></td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">Y/N（<a href="https://www.runoob.com/java/java-modifier-types.html#protected-desc" target="_blank" rel="noopener">说明</a>）</td><td style="text-align:left">N</td></tr><tr><td style="text-align:left"><code>default</code></td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">Y</td><td style="text-align:left">N</td><td style="text-align:left">N</td></tr><tr><td style="text-align:left"><code>private</code></td><td style="text-align:left">Y</td><td style="text-align:left">N</td><td style="text-align:left">N</td><td style="text-align:left">N</td><td style="text-align:left">N</td></tr></tbody></table><p>默认访问修饰符-不使用任何关键字</p><p>使用默认访问修饰符声明的变量和方法，对同一个包内的类是可见的，接口里的变量都隐式声明为<code>public static final</code>而接口里的方法默认情况下的访问权限是<code>public</code>如下变量和方法的声明可以不使用任何修饰符</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">String version = <span class="string">"1.5.1"</span>;</span><br><span class="line"><span class="function"><span class="keyword">boolean</span> <span class="title">processOrder</span><span class="params">()</span></span>&#123;</span><br><span class="line">    <span class="keyword">return</span> <span class="keyword">true</span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="私有访问修饰符-private"><a href="#私有访问修饰符-private" class="headerlink" title="私有访问修饰符-private"></a><strong>私有访问修饰符-private</strong></h2><p>私有访问修饰符时最严格的访问级别，所以被声明为private的方法，变量和构造方法只能被所属类访问，并且类和接口不能声明为private</p><p>声明为私有访问类型的变量只能通过类中公共的getter方法被外部类访问</p><p>Private访问修饰符的使用主要用来隐藏类的实现细节和保护类的数据，如下：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br></pre></td><td class="code"><pre><span class="line">publuic <span class="class"><span class="keyword">class</span> <span class="title">ligger</span></span>&#123;</span><br><span class="line">    <span class="keyword">private</span> String format;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> String <span class="title">getFormat</span><span class="params">()</span></span>&#123;</span><br><span class="line">        <span class="keyword">return</span> <span class="keyword">this</span>.format;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">setFormat</span><span class="params">(String format)</span></span>&#123;</span><br><span class="line">        <span class="keyword">this</span>.format = format;</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>实例中，Logger类中的format变量为私有变量，所以其他类不能直接得到和设置该变量的值，为了使其他类能够操作该变量，定义了两个public方法：getFormat()（返回format的值）和setFormat(String)（设置format的值）</p><h2 id="公有访问修饰符-public"><a href="#公有访问修饰符-public" class="headerlink" title="公有访问修饰符-public"></a><strong>公有访问修饰符-public</strong></h2><p>被声明为public的类、方法、构造方法和接口能够被任何其他类访问</p><p>如果几个相互访问的public类分布在不同的包中，则需要导入相应的public类所在的包。由于类的继承性，类所有的公有方法和变量都能被其子类继承。</p><p>以下函数使用了公有访问控制：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] arguments)</span> </span>&#123;</span><br><span class="line">   <span class="comment">// ...</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>Java 程序的 main() 方法必须设置成公有的，否则，Java 解释器将不能运行该类。</strong></p><h2 id="受保护的访问修饰符-protected"><a href="#受保护的访问修饰符-protected" class="headerlink" title="受保护的访问修饰符-protected"></a>受保护的访问修饰符-protected</h2><p>protected 需要从以下两个点来分析说明：</p><ul><li><strong>子类与基类在同一包中</strong>：被声明为 protected 的变量、方法和构造器能被同一个包中的任何其他类访问；</li><li><strong>子类与基类不在同一包中</strong>：那么在子类中，子类实例可以访问其从基类继承而来的 protected 方法，而不能访问基类实例的protected方法。</li></ul><p>protected 可以修饰数据成员，构造方法，方法成员，<strong>不能修饰类（内部类除外）</strong>。</p><p>接口及接口的成员变量和成员方法不能声明为 protected。 可以看看下图演示：</p><p><img src="https://www.runoob.com/wp-content/uploads/2013/12/java-protected.gif" alt=""></p><p>子类能访问 protected 修饰符声明的方法和变量，这样就能保护不相关的类使用这些方法和变量。</p><p>下面的父类使用了 protected 访问修饰符，子类重写了父类的 openSpeaker() 方法:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br></pre></td><td class="code"><pre><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">AudioPlayer</span> </span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">protected</span> <span class="keyword">boolean</span> <span class="title">openSpeaker</span><span class="params">(Speaker sp)</span> </span>&#123;</span><br><span class="line">      <span class="comment">// 实现细节</span></span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">StreamingAudioPlayer</span> <span class="keyword">extends</span> <span class="title">AudioPlayer</span> </span>&#123;</span><br><span class="line">   <span class="function"><span class="keyword">protected</span> <span class="keyword">boolean</span> <span class="title">openSpeaker</span><span class="params">(Speaker sp)</span> </span>&#123;</span><br><span class="line">      <span class="comment">// 实现细节</span></span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>如果把 openSpeaker() 方法声明为 private，那么除了 AudioPlayer 之外的类将不能访问该方法。</p><p>如果把 openSpeaker() 声明为 public，那么所有的类都能够访问该方法。</p><p>如果我们只想让该方法对其所在类的子类可见，则将该方法声明为 protected。</p><h2 id="访问控制和继承"><a href="#访问控制和继承" class="headerlink" title="访问控制和继承"></a>访问控制和继承</h2><p>请注意以下方法继承的规则：</p><ul><li>父类中声明为 public 的方法在子类中也必须为 public。</li><li>父类中声明为 protected 的方法在子类中要么声明为 protected，要么声明为 public，不能声明为 private。</li><li>父类中声明为 private 的方法，不能够被继承。</li></ul><h2 id="非访问修饰符"><a href="#非访问修饰符" class="headerlink" title="非访问修饰符"></a>非访问修饰符</h2><p>为了实现一些其他的功能，Java 也提供了许多非访问修饰符。</p><p>static 修饰符，用来修饰类方法和类变量。</p><p>final 修饰符，用来修饰类、方法和变量，final 修饰的类不能够被继承，修饰的方法不能被继承类重新定义，修饰的变量为常量，是不可修改的。</p><p>abstract 修饰符，用来创建抽象类和抽象方法。</p><p>synchronized 和 volatile 修饰符，主要用于线程的编程。</p><h3 id="static-修饰符"><a href="#static-修饰符" class="headerlink" title="static 修饰符"></a>static 修饰符</h3><ul><li><p><strong>静态变量：</strong></p><p>static 关键字用来声明独立于对象的静态变量，无论一个类实例化多少对象，它的静态变量只有一份拷贝。 静态变量也被称为类变量。局部变量不能被声明为 static 变量。</p></li><li><p><strong>静态方法：</strong></p><p>static 关键字用来声明独立于对象的静态方法。静态方法不能使用类的非静态变量。静态方法从参数列表得到数据，然后计算这些数据。</p></li></ul><p>对类变量和方法的访问可以直接使用 <strong>classname.variablename</strong> 和 <strong>classname.methodname</strong> 的方式访问。</p><p>如下例所示，static修饰符用来创建类方法和类变量。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">InstanceCounter</span> </span>&#123;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">static</span> <span class="keyword">int</span> numInstances = <span class="number">0</span>;</span><br><span class="line">   <span class="function"><span class="keyword">protected</span> <span class="keyword">static</span> <span class="keyword">int</span> <span class="title">getCount</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      <span class="keyword">return</span> numInstances;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">private</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">addInstance</span><span class="params">()</span> </span>&#123;</span><br><span class="line">      numInstances++;</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   InstanceCounter() &#123;</span><br><span class="line">      InstanceCounter.addInstance();</span><br><span class="line">   &#125;</span><br><span class="line"> </span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] arguments)</span> </span>&#123;</span><br><span class="line">      System.out.println(<span class="string">"Starting with "</span> +</span><br><span class="line">      InstanceCounter.getCount() + <span class="string">" instances"</span>);</span><br><span class="line">      <span class="keyword">for</span> (<span class="keyword">int</span> i = <span class="number">0</span>; i &lt; <span class="number">500</span>; ++i)&#123;</span><br><span class="line">         <span class="keyword">new</span> InstanceCounter();</span><br><span class="line">          &#125;</span><br><span class="line">      System.out.println(<span class="string">"Created "</span> +</span><br><span class="line">      InstanceCounter.getCount() + <span class="string">" instances"</span>);</span><br><span class="line">   &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>以上实例运行编辑结果如下:</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">Starting with <span class="number">0</span> instances</span><br><span class="line">Created <span class="number">500</span> instances</span><br></pre></td></tr></table></figure><h2 id="final-修饰符"><a href="#final-修饰符" class="headerlink" title="final 修饰符"></a><strong>final 修饰符</strong></h2><p><strong>final 变量：</strong></p><p>final 表示”最后的、最终的”含义，变量一旦赋值后，不能被重新赋值。被 final 修饰的实例变量必须显式指定初始值。</p><p>final 修饰符通常和 static 修饰符一起使用来创建类常量。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Test</span></span>&#123;</span><br><span class="line">  <span class="keyword">final</span> <span class="keyword">int</span> value = <span class="number">10</span>;</span><br><span class="line">  <span class="comment">// 下面是声明常量的实例</span></span><br><span class="line">  <span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">final</span> <span class="keyword">int</span> BOXWIDTH = <span class="number">6</span>;</span><br><span class="line">  <span class="keyword">static</span> <span class="keyword">final</span> String TITLE = <span class="string">"Manager"</span>;</span><br><span class="line"> </span><br><span class="line">  <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">changeValue</span><span class="params">()</span></span>&#123;</span><br><span class="line">     value = <span class="number">12</span>; <span class="comment">//将输出一个错误</span></span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>final 方法</strong></p><p>父类中的 final 方法可以被子类继承，但是不能被子类重写。</p><p>声明 final 方法的主要目的是防止该方法的内容被修改。</p><p>如下所示，使用 final 修饰符声明方法。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Test</span></span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">final</span> <span class="keyword">void</span> <span class="title">changeName</span><span class="params">()</span></span>&#123;</span><br><span class="line">       <span class="comment">// 方法体</span></span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>final 类</strong></p><p>final 类不能被继承，没有类能够继承 final 类的任何特性。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">final</span> <span class="class"><span class="keyword">class</span> <span class="title">Test</span> </span>&#123;</span><br><span class="line">   <span class="comment">// 类体</span></span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="abstract-修饰符"><a href="#abstract-修饰符" class="headerlink" title="abstract 修饰符"></a>abstract 修饰符</h2><h3 id="抽象类："><a href="#抽象类：" class="headerlink" title="抽象类："></a><strong>抽象类：</strong></h3><p>抽象类不能用来实例化对象，声明抽象类的唯一目的是为了将来对该类进行扩充。</p><p>一个类不能同时被 abstract 和 final 修饰。如果一个类包含抽象方法，那么该类一定要声明为抽象类，否则将出现编译错误。</p><p>抽象类可以包含抽象方法和非抽象方法。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">abstract</span> <span class="class"><span class="keyword">class</span> <span class="title">Caravan</span></span>&#123;</span><br><span class="line">   <span class="keyword">private</span> <span class="keyword">double</span> price;</span><br><span class="line">   <span class="keyword">private</span> String model;</span><br><span class="line">   <span class="keyword">private</span> String year;</span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">abstract</span> <span class="keyword">void</span> <span class="title">goFast</span><span class="params">()</span></span>; <span class="comment">//抽象方法</span></span><br><span class="line">   <span class="function"><span class="keyword">public</span> <span class="keyword">abstract</span> <span class="keyword">void</span> <span class="title">changeColor</span><span class="params">()</span></span>;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><strong>抽象方法</strong></p><p>抽象方法是一种没有任何实现的方法，该方法的的具体实现由子类提供。</p><p>抽象方法不能被声明成 final 和 static。</p><p>任何继承抽象类的子类必须实现父类的所有抽象方法，除非该子类也是抽象类。</p><p>如果一个类包含若干个抽象方法，那么该类必须声明为抽象类。抽象类可以不包含抽象方法。</p><p>抽象方法的声明以分号结尾，例如：<strong>public abstract sample();</strong>。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">abstract</span> <span class="class"><span class="keyword">class</span> <span class="title">SuperClass</span></span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">abstract</span> <span class="keyword">void</span> <span class="title">m</span><span class="params">()</span></span>; <span class="comment">//抽象方法</span></span><br><span class="line">&#125;</span><br><span class="line"> </span><br><span class="line"><span class="class"><span class="keyword">class</span> <span class="title">SubClass</span> <span class="keyword">extends</span> <span class="title">SuperClass</span></span>&#123;</span><br><span class="line">     <span class="comment">//实现抽象方法</span></span><br><span class="line">      <span class="function"><span class="keyword">void</span> <span class="title">m</span><span class="params">()</span></span>&#123;</span><br><span class="line">          .........</span><br><span class="line">      &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="synchronized-修饰符"><a href="#synchronized-修饰符" class="headerlink" title="synchronized 修饰符"></a>synchronized 修饰符</h2><p>synchronized 关键字声明的方法同一时间只能被一个线程访问。synchronized 修饰符可以应用于四个访问修饰</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">synchronized</span> <span class="keyword">void</span> <span class="title">showDetails</span><span class="params">()</span></span>&#123;</span><br><span class="line">.......</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="transient-修饰符"><a href="#transient-修饰符" class="headerlink" title="transient 修饰符"></a>transient 修饰符</h2><p>序列化的对象包含被 transient 修饰的实例变量时，java 虚拟机(JVM)跳过该特定的变量。</p><p>该修饰符包含在定义变量的语句中，用来预处理类和变量的数据类型。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="keyword">transient</span> <span class="keyword">int</span> limit = <span class="number">55</span>;   <span class="comment">// 不会持久化</span></span><br><span class="line"><span class="keyword">public</span> <span class="keyword">int</span> b; <span class="comment">// 持久化</span></span><br></pre></td></tr></table></figure><h2 id="volatile-修饰符"><a href="#volatile-修饰符" class="headerlink" title="volatile 修饰符"></a>volatile 修饰符</h2><p>volatile 修饰的成员变量在每次被线程访问时，都强制从共享内存中重新读取该成员变量的值。而且，当成员变量发生变化时，会强制线程将变化值回写到共享内存。这样在任何时刻，两个不同的线程总是看到某个成员变量的同一个值。</p><p>一个 volatile 对象引用可能是 null。</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">MyRunnable</span> <span class="keyword">implements</span> <span class="title">Runnable</span></span></span><br><span class="line"><span class="class"></span>&#123;</span><br><span class="line">    <span class="keyword">private</span> <span class="keyword">volatile</span> <span class="keyword">boolean</span> active;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">run</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        active = <span class="keyword">true</span>;</span><br><span class="line">        <span class="keyword">while</span> (active) <span class="comment">// 第一行</span></span><br><span class="line">        &#123;</span><br><span class="line">            <span class="comment">// 代码</span></span><br><span class="line">        &#125;</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">void</span> <span class="title">stop</span><span class="params">()</span></span></span><br><span class="line"><span class="function">    </span>&#123;</span><br><span class="line">        active = <span class="keyword">false</span>; <span class="comment">// 第二行</span></span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>通常情况下，在一个线程调用 run() 方法（在 Runnable 开启的线程），在另一个线程调用 stop() 方法。 如果 <strong>第一行</strong> 中缓冲区的 active 值被使用，那么在 <strong>第二行</strong> 的 active 值为 false 时循环不会停止。</p><p>但是以上代码中我们使用了 volatile 修饰 active，所以该循环会停止</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;Java-修饰符&quot;&gt;&lt;a href=&quot;#Java-修饰符&quot; class=&quot;headerlink&quot; title=&quot;Java 修饰符&quot;&gt;&lt;/a&gt;Java 修饰符&lt;/h1&gt;&lt;p&gt;Java语言提供了很多修饰符，主要分为一下两类：&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;访问修饰符&lt;/l
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="学习" scheme="http://www.windknew.com/blog/tags/%E5%AD%A6%E4%B9%A0/"/>
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家学习lava第三天（类和对象）</title>
    <link href="http://www.windknew.com/java-2/"/>
    <id>http://www.windknew.com/java-2/</id>
    <published>2020-02-08T09:54:48.000Z</published>
    <updated>2020-02-13T02:04:00.436Z</updated>
    
    <content type="html"><![CDATA[<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>在家无聊学习java第三天</p><h1 id="内容"><a href="#内容" class="headerlink" title="内容"></a>内容</h1><h2 id="java对象和类"><a href="#java对象和类" class="headerlink" title="java对象和类"></a>java对象和类</h2><ul><li>类：类是一个模板，它描述一类对象的行为和状态</li><li>对象： 对象是类的一个实例，有状态和行为，比如，一条狗是一个对象，他的状态有：颜色，名字，品种，行为有：摇尾巴，叫，吃等</li></ul><p>对比现实对象和软件对象，他们之间十分相似，软件对象也有状态和行为，软件对象的状态就是属性，行为就是具体的方法，在软件开发中，方法操作对象内部的状态，队形的相互调用也是通过方法来实现</p><h2 id="Java中的类"><a href="#Java中的类" class="headerlink" title="Java中的类"></a>Java中的类</h2><p>如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Dog</span></span>&#123;</span><br><span class="line">  String breed;</span><br><span class="line">  <span class="keyword">int</span> age;</span><br><span class="line">  String color;</span><br><span class="line">  <span class="function"><span class="keyword">void</span> <span class="title">barking</span><span class="params">()</span></span>&#123;</span><br><span class="line">  &#125;</span><br><span class="line"> </span><br><span class="line">  <span class="function"><span class="keyword">void</span> <span class="title">hungry</span><span class="params">()</span></span>&#123;</span><br><span class="line">  &#125;</span><br><span class="line"> </span><br><span class="line">  <span class="function"><span class="keyword">void</span> <span class="title">sleeping</span><span class="params">()</span></span>&#123;</span><br><span class="line">  &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>一个类可以包含以下类型变量：</p><ul><li><strong>局部变量</strong>：在方法、构造方法或者语句块中定义的变量被称为局部变量。变量声明和初始化都是在方法中，方法结束后，变量就会自动销毁。</li><li><strong>成员变量</strong>：成员变量是定义在类中，方法体之外的变量。这种变量在创建对象的时候实例化。成员变量可以被类中方法、构造方法和特定类的语句块访问。</li><li><strong>类变量</strong>：类变量也声明在类中，方法体之外，但必须声明为static类型。</li></ul><p>一个类可以拥有多个方法，在上面的例子中：barking()、hungry()和sleeping()都是Dog类的方法。</p><h2 id="构造方法"><a href="#构造方法" class="headerlink" title="构造方法"></a>构造方法</h2><p>每个类都有构造方法，如果没有显式地为类定义构造方法。java编译器将会为该类提供一个默认构造方法，在创建一个对象的时候，至少要调用一个构造方法，构造方法的名称必须与类同名，一个类可以有多个构造方法如：</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br></pre></td><td class="code"><pre><span class="line">public class Puppy&#123;</span><br><span class="line">    public Puppy()&#123;    </span><br><span class="line">    &#125;</span><br><span class="line">    public Puppy(String name)&#123;</span><br><span class="line">    // 这个构造器仅有一个参数：name </span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="创建对象"><a href="#创建对象" class="headerlink" title="创建对象"></a>创建对象</h2><p>对象是根据类创建的。在java中，使用关键字来创建一个新的对象。创建对象需要以下三步：</p><ul><li><strong>声明</strong>：声明一个对象，包括对象名称和对象类型。</li><li><strong>实例化：</strong> 使用关键字new来创建一个对象</li><li><strong>初始化</strong> ：使用new创建对象时，会调用构造方法初始化对象</li></ul><p>如：</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Puppy</span></span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="title">Puppy</span><span class="params">(String name)</span></span>&#123;</span><br><span class="line">    <span class="comment">//这个构造器仅有一个参数：name</span></span><br><span class="line">    System.out.println(<span class="string">"小狗的名字是："</span>+name);</span><br><span class="line">    &#125;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span></span>&#123;</span><br><span class="line">        <span class="comment">// 下面语句将创建一个Puppy对象</span></span><br><span class="line">        Puppy myPuppy = <span class="keyword">new</span> Puppy(<span class="string">"tommy"</span>);</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;前言&lt;/h1&gt;&lt;p&gt;在家无聊学习java第三天&lt;/p&gt;
&lt;h1 id=&quot;内容&quot;&gt;&lt;a href=&quot;#内容&quot; class=&quot;headerlink&quot; title=&quot;
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="学习" scheme="http://www.windknew.com/blog/tags/%E5%AD%A6%E4%B9%A0/"/>
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家学习java第二天（常量和变量）</title>
    <link href="http://www.windknew.com/java-1/"/>
    <id>http://www.windknew.com/java-1/</id>
    <published>2020-02-07T09:25:25.000Z</published>
    <updated>2020-02-13T02:04:03.300Z</updated>
    
    <content type="html"><![CDATA[<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>在家无聊学习java第二天</p><h1 id="内容"><a href="#内容" class="headerlink" title="内容"></a>内容</h1><h2 id="常量"><a href="#常量" class="headerlink" title="常量"></a>常量</h2><ul><li>字符串常量</li><li>整数常量</li><li>浮点数常量</li><li>字符常量</li><li>布尔常量</li><li>空常量：null</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">TwodayDemo1</span></span>&#123;</span><br><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span></span>&#123;</span><br><span class="line">    <span class="comment">//字符串常量</span></span><br><span class="line">    System.out.println(<span class="string">"ABC"</span>);</span><br><span class="line">    System.out.println(<span class="string">""</span>);</span><br><span class="line">    System.out.println(<span class="string">"XYZ"</span>);</span><br><span class="line">    </span><br><span class="line">    <span class="comment">//整数常量</span></span><br><span class="line">    System.out.println(<span class="number">30</span>);</span><br><span class="line">    System.out.println(-<span class="number">30</span>);</span><br><span class="line">    </span><br><span class="line">    <span class="comment">//浮点数常量（小数）</span></span><br><span class="line">    System.out.println(<span class="number">3.14</span>);</span><br><span class="line">    System.out.println(-<span class="number">2.5</span>);</span><br><span class="line">    </span><br><span class="line">    <span class="comment">//字符常量</span></span><br><span class="line">    System.out.println(<span class="string">'A'</span>);</span><br><span class="line">    System.out.println(<span class="string">'6'</span>);</span><br><span class="line">    <span class="comment">//System.out.println('');  两个单引号中间必须有且仅有一个字符，没有就会报错 </span></span><br><span class="line">    <span class="comment">//System.out.println('AB')    有两个字符也不行</span></span><br><span class="line">        </span><br><span class="line">        <span class="comment">//布尔常量</span></span><br><span class="line">        System.out.println(<span class="keyword">true</span>);</span><br><span class="line">        System.out.println(<span class="keyword">false</span>);</span><br><span class="line">        </span><br><span class="line">        <span class="comment">//空常量，不能直接用来打印输出</span></span><br><span class="line">        <span class="comment">// System.out.println(null);  会报错</span></span><br><span class="line">&#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><h2 id="数据类型"><a href="#数据类型" class="headerlink" title="数据类型"></a>数据类型</h2><p>java的数据类型分为两大类：</p><ul><li>基本数据类型</li><li>引用数据类型</li></ul><h3 id="基本数据类型"><a href="#基本数据类型" class="headerlink" title="基本数据类型"></a>基本数据类型</h3><p>四类八种基本数据类型</p><table><thead><tr><th style="text-align:left">数据类型</th><th>关键字</th><th>内存占用</th><th>取值范围</th></tr></thead><tbody><tr><td style="text-align:left">字节型</td><td>byte</td><td>1个字节</td><td>-128~127</td></tr><tr><td style="text-align:left">短整型</td><td>short</td><td>2个字节</td><td>-32768~32767</td></tr><tr><td style="text-align:left">整形</td><td>int（默认）</td><td>4个字节</td><td>-2^31^~2^31^-1</td></tr><tr><td style="text-align:left">长整型</td><td>long</td><td>8个字节</td><td>-2^63^~2^63^-1</td></tr><tr><td style="text-align:left">单精度浮点数</td><td>float</td><td>4个字节</td><td>1.4013E-45~3.4028E+38</td></tr><tr><td style="text-align:left">双精度浮点数</td><td>double（默认）</td><td>8个字节</td><td>4.9E-324~1.7977E+308</td></tr><tr><td style="text-align:left">字符型</td><td>char</td><td>2个字节</td><td>0-65535</td></tr><tr><td style="text-align:left">布尔类型</td><td>boolean</td><td>1个字节</td><td>true  false</td></tr></tbody></table><p>【<strong>SP</strong>】 </p><ul><li><p>java中的默认类型，整形是int，浮点型是double</p></li><li><p>字符串不是基本类型而是引用类型</p></li><li><p>浮点型可能只是一个近似值，并非精确的值</p></li><li><p>数据范围与字节数并不一定相关，如float数据范围比long更加广泛，单float是4字节而long是8字节</p></li><li><p>如果使用float需加后缀F，若使用long后缀需加L，推荐使用大写字母后缀</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">System.out.println(100);//是int型</span><br><span class="line">System.out.println(100L);//是long型</span><br><span class="line">System.out.println(100.2);//是double型</span><br><span class="line">System.out.println(100F);//是float型</span><br></pre></td></tr></table></figure></li></ul><h2 id="变量的定义"><a href="#变量的定义" class="headerlink" title="变量的定义"></a>变量的定义</h2><p>变量定义有以下两种方式</p><ol><li><p>创建一个变量并且使用的格式</p><ul><li><strong>数据类型 变量名称</strong> //创建一个变量</li><li><strong>变量名称 = 数据值</strong>  //赋值</li></ul></li><li><p>一步到位</p><ul><li><p><strong>数据类型  变量名称 = 数据值</strong>；//在创建变量同时，立刻放入指定的数据值</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"> <span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">Day02</span></span>&#123;</span><br><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span></span>&#123;</span><br></pre></td></tr></table></figure></li></ul><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br></pre></td><td class="code"><pre><span class="line">   </span><br><span class="line"> //方式一</span><br><span class="line">int num1;</span><br><span class="line">num1 =10;</span><br><span class="line">   System.out.println(num1);</span><br><span class="line">    //方式二</span><br><span class="line">    int num2 = 25;</span><br><span class="line">    System.out.println(num2);</span><br><span class="line">    System.out.println(&quot;--------------&quot;);</span><br><span class="line">    byte num3 = 30; //注意右侧数值不能超过左侧数据类型的数据范围</span><br><span class="line">    System.out.println(num3);</span><br><span class="line">    //byte num4 = 400;// 右侧超出了byte的取值范围，错误！！</span><br><span class="line">    short num5 = 50;</span><br><span class="line"> System.out.println(num5);</span><br><span class="line">   </span><br><span class="line">    long num6 = 3000000L;</span><br><span class="line"> System.out.println(num6);</span><br><span class="line">   </span><br><span class="line">    float num7 = 2.5F;</span><br><span class="line"> System.out.println(num7);</span><br><span class="line">   </span><br><span class="line">    double  num8 = 1.2;</span><br><span class="line"> System.out.println(num8);</span><br><span class="line">   </span><br><span class="line">    char zifu1 = &apos;A&apos;;</span><br><span class="line"> System.out.println(zifu1);</span><br><span class="line">   </span><br><span class="line">    zifu1 = &apos;中&apos;;</span><br><span class="line"> System.out.println(zifu1);</span><br><span class="line">   </span><br><span class="line">    boolean var1 = true;</span><br><span class="line"> System.out.println(var1);</span><br><span class="line">   </span><br><span class="line">    var1 = false;</span><br><span class="line"> System.out.println(var1);</span><br><span class="line"></span><br><span class="line">&#125;</span><br><span class="line">   &#125;</span><br></pre></td></tr></table></figure>  <figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line"></span><br><span class="line">**TIPS**</span><br><span class="line"></span><br><span class="line">* 变量之间不能重复</span><br><span class="line">* 对于float和long后缀不能丢掉</span><br><span class="line">* 如果用type和long注意取值范围</span><br><span class="line">* 没有进行赋值的变量，不能直接使用，一定要复制之后才能进行使用（如打印输出操作）</span><br><span class="line">* 变量不要超出变量的定义域</span><br><span class="line"></span><br><span class="line"># 数据类型转换</span><br><span class="line"></span><br><span class="line">1. 自动转换</span><br><span class="line"></span><br><span class="line">   一个int类型变量和一个byte类型变量进行加法运算，结果是什么类型？</span><br><span class="line"></span><br><span class="line">   ```java</span><br><span class="line">   int i =1;</span><br><span class="line">   byte b = 2;</span><br></pre></td></tr></table></figure><p>运算结果，变量的类型将是int类型，这就是出现了数据类型的自动类型转换现象</p><p><strong>自动转换(隐式)</strong>：将取值范围小的类型自动提升为取值范围大的类型</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="keyword">void</span> <span class="title">main</span><span class="params">(String[] args)</span> </span>&#123;</span><br><span class="line">    <span class="keyword">int</span> i =<span class="number">1</span>;</span><br><span class="line">    <span class="keyword">byte</span> =<span class="number">2</span>;</span><br><span class="line">    <span class="comment">//byte x = b+i //报错</span></span><br><span class="line">    <span class="comment">//int 类型和byte；类型运算，结果是int</span></span><br><span class="line">    <span class="keyword">int</span> j = b+i;</span><br><span class="line">    System.out.println(j);</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p>规则：数据范围从小到大</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">long</span> num1 = <span class="number">100</span>;<span class="comment">//左边是long，右边是int，从int--long是从小到大，自当发生数据类型转换</span></span><br><span class="line"><span class="keyword">double</span> num2 = <span class="number">2.5F</span>;</span><br><span class="line"><span class="keyword">float</span> num3  =<span class="number">30L</span>;</span><br></pre></td></tr></table></figure><p><strong>强制类型转换</strong></p><p>代码需要进行特殊的格式处理，不能自动完成</p><p>范围小的类型 范围小的变量名 = （范围小的类型）原本范围大的数据</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">int</span> num = (<span class="keyword">int</span>) <span class="number">100L</span>;</span><br><span class="line"><span class="comment">//左边是int类型，右边是long类型，不一样</span></span><br><span class="line"><span class="comment">//long --&gt; int ，不是从小到大，不能发生自动化类型转换</span></span><br><span class="line"><span class="comment">//范围小的类型 范围小的变量名 = （范围小的类型）原本范围大的数据</span></span><br></pre></td></tr></table></figure><p><strong>Tips</strong></p><ol><li><p>强制类型转换一般不使用，因为有可能发生精度损失，数据溢出</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">int</span> num  =(<span class="keyword">int</span>) <span class="number">6000000000L</span>;</span><br><span class="line">输出num为<span class="number">17</span>亿数据溢出</span><br></pre></td></tr></table></figure></li><li><p>byte/short/char三种类型都可以发生数学运算</p></li><li><p>byte/short/char三种类型在运算的时候，都会被首先提升为int类型然后再计算</p></li><li><p>boolean  不能发生数据类型转换</p></li></ol></li></ol><h1 id="运算符"><a href="#运算符" class="headerlink" title="运算符"></a>运算符</h1><h2 id="一元运算符"><a href="#一元运算符" class="headerlink" title="一元运算符"></a>一元运算符</h2><ul><li>取反 ！</li><li>自增 ++</li><li>自减 –</li></ul><h2 id="二元运算符"><a href="#二元运算符" class="headerlink" title="二元运算符"></a>二元运算符</h2><ul><li>+</li><li>-</li><li>*</li><li>/</li><li>=</li></ul><h2 id="三元运算符"><a href="#三元运算符" class="headerlink" title="三元运算符"></a>三元运算符</h2><p>数据类型 变量名称 = 条件判断 ？ 表达式A：表达式B;</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">int</span> a;</span><br><span class="line"><span class="keyword">int</span> b;</span><br><span class="line"><span class="keyword">int</span> max = a &gt; b ? a : b;</span><br></pre></td></tr></table></figure><p><strong>Tips</strong></p><ul><li>必须同时保证表达式A和表达式B都符合左侧数据类型的要求</li><li>三元运算符的结果必须被使用</li></ul><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">int</span> result = <span class="number">3</span> &gt; <span class="number">4</span> ? <span class="number">2.5</span> : <span class="number">10</span> ;  <span class="comment">//错误 数据类型不一致</span></span><br><span class="line">System.out.println(a &gt; b ? a : b);<span class="comment">//正确写法</span></span><br><span class="line">a &gt; b ? a : b  <span class="comment">//错误写法，没有进行使用</span></span><br></pre></td></tr></table></figure>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;前言&lt;/h1&gt;&lt;p&gt;在家无聊学习java第二天&lt;/p&gt;
&lt;h1 id=&quot;内容&quot;&gt;&lt;a href=&quot;#内容&quot; class=&quot;headerlink&quot; title=&quot;
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="学习" scheme="http://www.windknew.com/blog/tags/%E5%AD%A6%E4%B9%A0/"/>
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>在家java学习第一天（java认识和环境搭建）</title>
    <link href="http://www.windknew.com/java/"/>
    <id>http://www.windknew.com/java/</id>
    <published>2020-02-06T08:41:42.000Z</published>
    <updated>2020-02-13T02:03:41.173Z</updated>
    
    <content type="html"><![CDATA[<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a><strong>前言</strong></h1><p>​    下学期要学习java，闲来无事，开始了自学之旅，用于记录学习java的全过程，当是学习笔记吧</p><h1 id="什么是java，以及java发展史"><a href="#什么是java，以及java发展史" class="headerlink" title="什么是java，以及java发展史"></a><strong>什么是java，以及java发展史</strong></h1><h2 id="什么是java语言"><a href="#什么是java语言" class="headerlink" title="什么是java语言"></a><strong>什么是java语言</strong></h2><p>Java语言是美国Sun公司（Stanford University Network）斯坦福大学网络公司，在1995年推出的高级编程语言，所谓编程语言，是计算机的语言，人门可以使用编程语言对计算机下达命令，让计算机完成人门需要的功能</p><p>Java语言之父James Gosling就是这家公司非常nb的程序员，关于java之父的详细了解，可以看看以下这篇文章</p><p>​       <a href="http://www.elecfans.com/d/633774.html" target="_blank" rel="noopener">java之父及java诞生</a></p><p><img src="http://q4uie93wz.bkt.clouddn.com/java/20200206045310571.png" alt=""></p><p>​                                              java语言之父 James Gosling</p><h2 id="Java发展史"><a href="#Java发展史" class="headerlink" title="Java发展史"></a>Java发展史</h2><ul><li>1995年Sun公司发布java1.0版本</li><li>1997年发布java1.1版本</li><li>1998年发布java1.2版本</li><li>2000年发布java1.3版本</li><li>2002年发布java1.4版本</li><li>2004年发布java5版本（因为和1.4变化太大，更新力度太大，所以用大版版本号来表示）</li><li>2006年发布java6版本</li><li>2009年Oracle甲骨文公司收购Sun公司，并于2011年发布java7版本</li><li>2014年发布java8版本</li><li>2017年9月发布java9版本</li><li>2018年3月发布java10版本</li></ul><h2 id="Java的应用"><a href="#Java的应用" class="headerlink" title="Java的应用"></a>Java的应用</h2><p>Java语言经过多年的发展已经形成了一个较为健全的语言生态，在Web开发、大数据开发、Android开发等领域均有广泛的应用，而且凭借稳定的性能表现和较强的扩展性，目前Java语言依然是大型互联网平台较为常见的解决方案，采用Java语言进行大型后端系统的开发会在很大程度上降低开发风险。JAVA的一次编译，到处运行，你知道多少？](<a href="https://blog.csdn.net/wangyongxia921/article/details/28117155" target="_blank" rel="noopener">https://blog.csdn.net/wangyongxia921/article/details/28117155</a>)</p><h2 id="Java环境的搭建"><a href="#Java环境的搭建" class="headerlink" title="Java环境的搭建"></a>Java环境的搭建</h2><ul><li><strong>JVM</strong> (java Virtual Machine):java虚拟机，简称JVM，是运行所有java程序的假想计算机，是java程序的运行环境，是java最具吸引力的特性之一，我们编写的JVM之上</li><li><strong>跨平台</strong>：任何软件的运行，都必须要运行在操作系统之上，而我们用Java编写的软件可以运行在任何的操作系统上，这个特性称为java语言的跨平台特性，该特性是由JVM实现的，我们编写的程序运行在JVM上，而JVM运行在操作系统上（这就是著名的‘一次编写，到处运行’）可以看看这篇文章<a href="https://blog.csdn.net/wangyongxia921/article/details/28117155" target="_blank" rel="noopener">JAVA的一次编译，到处运行，你知道多少？</a></li></ul><p>​           <img src="http://q4uie93wz.bkt.clouddn.com/java/20200206052004691.png" alt=""></p><h3 id="JRE和JDK"><a href="#JRE和JDK" class="headerlink" title="JRE和JDK"></a><strong>JRE和JDK</strong></h3><ul><li><strong>JRE</strong> (java Runtime Environment) :是java程序的运行时环境，包含JVM和运行时所需要的核心类库</li><li><strong>JDK</strong> (java Development Kit):是java程序开发工具包，包含JRE和开发人员使用的工具</li></ul><p>我们想要运行一个已有的java程序，那么只需要安装JRE即可</p><p>我们想要开发一个全新的java程序，那么必须安装JDK</p><p>JDK，JRE，JVM关系图</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200206172646684/20200206052700258.png" alt=""></p><p>下载安装<a href="https://www.oracle.com/technetwork/java/javase/archive-139210.html" target="_blank" rel="noopener">JDK</a></p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200206172646684/20200206053424799.png" alt=""></p><p>可以选择不同的版本号,(我无论什么都喜欢下载最新的我下载的是最新的)</p><p>选择相应的java版本，点进去</p><p><img src="C:\Users\lyh\AppData\Roaming\Typora\typora-user-images\1580981715514.png" alt="1580981715514"></p><p>选择相应系统的jdk点击下载</p><p>下载成功之后点击安装</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200206172646684/20200206054114831.png" alt=""></p><p><strong>注意这个路径问题</strong></p><h2 id="添加环境变量"><a href="#添加环境变量" class="headerlink" title="添加环境变量"></a>添加环境变量</h2><p>将我们的jdk安装的bin目录添加到环境变量path里</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200206172646684/20200206054828671.png" alt=""></p><p>然后打开cmd测试</p><p><img src="C:\Users\lyh\AppData\Roaming\Typora\typora-user-images\1580982637728.png" alt="1580982637728"></p><p>这样就说明，jdk环境变量配好了</p><h2 id="Hello-World"><a href="#Hello-World" class="headerlink" title="Hello World"></a>Hello World</h2><p>新建一个文本文档，命名为HelloWorld.java</p><figure class="highlight java"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br></pre></td><td class="code"><pre><span class="line"><span class="keyword">public</span> <span class="class"><span class="keyword">class</span> <span class="title">HelloWorld</span></span>&#123;</span><br><span class="line">    <span class="function"><span class="keyword">public</span> <span class="keyword">static</span> <span class="title">main</span><span class="params">(String[] args)</span></span>&#123;</span><br><span class="line">        System.out.println(<span class="string">"Hello,World"</span>);</span><br><span class="line">    &#125;</span><br><span class="line">&#125;</span><br></pre></td></tr></table></figure><p><img src="C:\Users\lyh\AppData\Roaming\Typora\typora-user-images\1580983459688.png" alt="1580983459688"></p><p>执行javac 编译HelloWorld.java执行后什么都不出现，同目录下会出现.class的字节码文件</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200206172646684/20200206060318866.png" alt=""></p><p>然后java  HelloWorld 就能成功执行该文件</p><p><img src="C:\Users\lyh\AppData\Roaming\Typora\typora-user-images\1580984557635.png" alt="1580984557635"></p><p><strong>注意用的是java HelloWorld，java后面一个空格，加不加后缀的文件名</strong></p><p>今天就学了这么多，明天再学变量什么的，</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;&lt;strong&gt;前言&lt;/strong&gt;&lt;/h1&gt;&lt;p&gt;​    下学期要学习java，闲来无事，开始了自学之旅，用于记录学习java的全过程，当是学习笔记吧&lt;/
      
    
    </summary>
    
      <category term="java" scheme="http://www.windknew.com/blog/categories/java/"/>
    
    
      <category term="学习" scheme="http://www.windknew.com/blog/tags/%E5%AD%A6%E4%B9%A0/"/>
    
      <category term="java" scheme="http://www.windknew.com/blog/tags/java/"/>
    
  </entry>
  
  <entry>
    <title>文泉课堂爬虫源码</title>
    <link href="http://www.windknew.com/wenquanketang-spider/"/>
    <id>http://www.windknew.com/wenquanketang-spider/</id>
    <published>2020-02-05T02:21:59.000Z</published>
    <updated>2020-09-09T09:06:21.736Z</updated>
    
    <content type="html"><![CDATA[<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>今天打开发现文泉课堂需要登陆才能进行访问，一登陆，发现，昨天的502，明显好多了今天附上所有源码，供大家学习和参考</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br><span class="line">49</span><br><span class="line">50</span><br><span class="line">51</span><br><span class="line">52</span><br><span class="line">53</span><br><span class="line">54</span><br><span class="line">55</span><br><span class="line">56</span><br><span class="line">57</span><br><span class="line">58</span><br><span class="line">59</span><br><span class="line">60</span><br><span class="line">61</span><br><span class="line">62</span><br><span class="line">63</span><br><span class="line">64</span><br><span class="line">65</span><br><span class="line">66</span><br><span class="line">67</span><br><span class="line">68</span><br><span class="line">69</span><br><span class="line">70</span><br><span class="line">71</span><br><span class="line">72</span><br><span class="line">73</span><br><span class="line">74</span><br><span class="line">75</span><br><span class="line">76</span><br><span class="line">77</span><br><span class="line">78</span><br><span class="line">79</span><br><span class="line">80</span><br><span class="line">81</span><br><span class="line">82</span><br><span class="line">83</span><br><span class="line">84</span><br><span class="line">85</span><br><span class="line">86</span><br><span class="line">87</span><br><span class="line">88</span><br><span class="line">89</span><br><span class="line">90</span><br><span class="line">91</span><br><span class="line">92</span><br><span class="line">93</span><br><span class="line">94</span><br><span class="line">95</span><br><span class="line">96</span><br><span class="line">97</span><br><span class="line">98</span><br><span class="line">99</span><br><span class="line">100</span><br><span class="line">101</span><br><span class="line">102</span><br><span class="line">103</span><br><span class="line">104</span><br><span class="line">105</span><br><span class="line">106</span><br><span class="line">107</span><br><span class="line">108</span><br><span class="line">109</span><br><span class="line">110</span><br><span class="line">111</span><br><span class="line">112</span><br><span class="line">113</span><br><span class="line">114</span><br><span class="line">115</span><br><span class="line">116</span><br><span class="line">117</span><br><span class="line">118</span><br><span class="line">119</span><br><span class="line">120</span><br><span class="line">121</span><br><span class="line">122</span><br><span class="line">123</span><br><span class="line">124</span><br><span class="line">125</span><br><span class="line">126</span><br><span class="line">127</span><br><span class="line">128</span><br><span class="line">129</span><br><span class="line">130</span><br><span class="line">131</span><br><span class="line">132</span><br><span class="line">133</span><br><span class="line">134</span><br><span class="line">135</span><br><span class="line">136</span><br><span class="line">137</span><br><span class="line">138</span><br><span class="line">139</span><br><span class="line">140</span><br><span class="line">141</span><br><span class="line">142</span><br><span class="line">143</span><br><span class="line">144</span><br><span class="line">145</span><br><span class="line">146</span><br><span class="line">147</span><br><span class="line">148</span><br><span class="line">149</span><br><span class="line">150</span><br><span class="line">151</span><br><span class="line">152</span><br><span class="line">153</span><br><span class="line">154</span><br><span class="line">155</span><br><span class="line">156</span><br><span class="line">157</span><br><span class="line">158</span><br><span class="line">159</span><br><span class="line">160</span><br></pre></td><td class="code"><pre><span class="line">#!/usr/bin/env python</span><br><span class="line"># -*- coding:utf-8 -*-</span><br><span class="line"># Author:风晓</span><br><span class="line">import requests</span><br><span class="line">import time</span><br><span class="line">from pathlib import Path</span><br><span class="line">import os</span><br><span class="line">import jwt</span><br><span class="line">import json</span><br><span class="line">from tqdm import trange</span><br><span class="line">data =&#123;&#125;</span><br><span class="line">headers =&#123;</span><br><span class="line">    &apos;user-agent&apos;: &apos;Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36&apos;,</span><br><span class="line">  &#125;</span><br><span class="line">JWT_SECRET = &apos;g0NnWdSE8qEjdMD8a1aq12qEYphwErKctvfd3IktWHWiOBpVsgkecur38aBRPn2w&apos;</span><br><span class="line"># SESS = httpx.Client()</span><br><span class="line">URL = &apos;https://lib-nuanxin.wqxuetang.com&apos;</span><br><span class="line"># SESS.get(URL)</span><br><span class="line">&apos;&apos;&apos; jwt key for bookid &apos;&apos;&apos;</span><br><span class="line"># url = &quot;https://lib-nuanxin.wqxuetang.com/v1/read/k?bid=%s&quot; % bookid</span><br><span class="line">def gen_jwt_key(bookid,cooike):</span><br><span class="line">  url = f&apos;&#123;URL&#125;/v1/read/k?bid=&#123;bookid&#125;&apos;</span><br><span class="line">  print(url)</span><br><span class="line">  # r = self.session.get(url, timeout=5)</span><br><span class="line"></span><br><span class="line">  # r = SESS.get(url, timeout=5)</span><br><span class="line">  # j = json.loads(r.text)</span><br><span class="line">  head = &#123;</span><br><span class="line">    &apos;Accept&apos;: &apos;text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8&apos;,</span><br><span class="line">    &apos;Accept-Encoding&apos;: &apos;gzip, deflate, sdch&apos;,</span><br><span class="line">    &apos;Accept-Language&apos;: &apos;zh-CN,zh;q=0.8&apos;,</span><br><span class="line">    &apos;Connection&apos;: &apos;keep-alive&apos;,</span><br><span class="line">    &apos;Cookie&apos;: cooike,</span><br><span class="line">    &apos;Host&apos;: &apos;lib-nuanxin.wqxuetang.com&apos;,</span><br><span class="line">    &apos;Upgrade-Insecure-Requests&apos;: &apos;1&apos;,</span><br><span class="line">    &apos;User-Agent&apos;: &apos;Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/49.0.2623.112 Safari/537.36&apos;,</span><br><span class="line">  &#125;</span><br><span class="line">  try:</span><br><span class="line">    resp = requests.get(url,headers = head)</span><br><span class="line">    resp.raise_for_status()</span><br><span class="line">  except Exception as exc:</span><br><span class="line">    print(exc)</span><br><span class="line"></span><br><span class="line">  try:</span><br><span class="line">    jdata = resp.json()</span><br><span class="line">  except Exception as exc:</span><br><span class="line">    jdata = &#123;&#125;</span><br><span class="line"></span><br><span class="line">  res = jdata.get(&apos;data&apos;)</span><br><span class="line">  if res is None:</span><br><span class="line">    raise Exception(&apos;returned None, something is not right...&apos;)</span><br><span class="line"></span><br><span class="line">  return res</span><br><span class="line">def gen_jwt_token(bookid, page,cooike):</span><br><span class="line">  &apos;&apos;&apos; gen jwt token &apos;&apos;&apos;</span><br><span class="line">  cur_time = time.time()</span><br><span class="line">  jwtkey = gen_jwt_key(bookid,cooike)</span><br><span class="line">  print(jwtkey)</span><br><span class="line">  jwttoken = jwt.encode(</span><br><span class="line">    &#123;</span><br><span class="line">      &quot;p&quot;: page,</span><br><span class="line">      &quot;t&quot;: int(cur_time) * 1000,</span><br><span class="line">      &quot;b&quot;: str(bookid),</span><br><span class="line">      &quot;w&quot;: 1000,</span><br><span class="line">      &quot;k&quot;: json.dumps(jwtkey),</span><br><span class="line">      &quot;iat&quot;: int(cur_time),</span><br><span class="line">    &#125;,</span><br><span class="line">    JWT_SECRET,</span><br><span class="line">    algorithm=&apos;HS256&apos;,</span><br><span class="line">  ).decode(&apos;ascii&apos;)</span><br><span class="line">  print(jwttoken)</span><br><span class="line">  return jwttoken</span><br><span class="line">def bookinfo(bookid,cooike):</span><br><span class="line">  &apos;&apos;&apos; bookinfo &apos;&apos;&apos;</span><br><span class="line">  # url = f&quot;https://lib-nuanxin.wqxuetang.com/v1/read/initread?bid=&#123;self.bookid&#125;&quot;  # noqa</span><br><span class="line">  url = f&apos;&#123;URL&#125;/v1/read/initread?bid=&#123;bookid&#125;&apos;</span><br><span class="line">  # r = self.session.get(url)</span><br><span class="line">  head = &#123;</span><br><span class="line">    &apos;Accept&apos;: &apos;text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,*/*;q=0.8&apos;,</span><br><span class="line">    &apos;Accept-Encoding&apos;: &apos;gzip, deflate, sdch&apos;,</span><br><span class="line">    &apos;Accept-Language&apos;: &apos;zh-CN,zh;q=0.8&apos;,</span><br><span class="line">    &apos;Connection&apos;: &apos;keep-alive&apos;,</span><br><span class="line">    &apos;Cookie&apos;: cooike,</span><br><span class="line">    &apos;Host&apos;: &apos;lib-nuanxin.wqxuetang.com&apos;,</span><br><span class="line">    &apos;Upgrade-Insecure-Requests&apos;: &apos;1&apos;,</span><br><span class="line">    &apos;User-Agent&apos;: &apos;Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/49.0.2623.112 Safari/537.36&apos;,</span><br><span class="line">  &#125;</span><br><span class="line">  try:</span><br><span class="line">    bookid = int(bookid)</span><br><span class="line">  except Exception as exc:</span><br><span class="line">    print(exc)</span><br><span class="line">    raise</span><br><span class="line">  if bookid &lt; 1:</span><br><span class="line">    # logger.warning(f&apos; bookid &#123;bookid&#125; &lt; 1, setting bookid to 1&apos;)</span><br><span class="line">    # bookid = 1</span><br><span class="line">    raise Exception(&apos; bookid must be bigger than zero&apos;)</span><br><span class="line"></span><br><span class="line">  try:</span><br><span class="line">    print(url)</span><br><span class="line">    resp = requests.get(url,headers=head)</span><br><span class="line">    resp.raise_for_status()</span><br><span class="line">  except Exception as exc:</span><br><span class="line">    print(exc)</span><br><span class="line">  try:</span><br><span class="line">    jdata = resp.json()</span><br><span class="line">  except Exception as exc:</span><br><span class="line">    print(exc)</span><br><span class="line">    jdata = &#123;&#125;</span><br><span class="line">  data = jdata.get(&apos;data&apos;)</span><br><span class="line">  print(data)</span><br><span class="line">  if data is None:</span><br><span class="line">    raise Exception(</span><br><span class="line">      &apos;returned None, something is not right...可能无此书号，也有可能是网络有问题或IP被限制……&apos;  # noqa</span><br><span class="line">    )</span><br><span class="line">  bookinfo.jdata = jdata</span><br><span class="line">  # print(data.get(&apos;canreadpages&apos;))</span><br><span class="line">  print(data.get(&apos;name&apos;), data.get(&apos;canreadpages&apos;))</span><br><span class="line">  return data.get(&apos;name&apos;), data.get(&apos;canreadpages&apos;)</span><br><span class="line">def fetch_png(bookid, page=1):</span><br><span class="line">  &apos;&apos;&apos; download booid page img &apos;&apos;&apos;</span><br><span class="line">  token = gen_jwt_token(bookid, page,cooike)</span><br><span class="line">  print(token)</span><br><span class="line">  url = f&apos;&#123;URL&#125;/page/img/&#123;bookid&#125;/&#123;page&#125;?k=&#123;token&#125;&apos;</span><br><span class="line">  print(url)</span><br><span class="line">  headers = &#123;</span><br><span class="line">    &apos;accept&apos;: &apos;image / webp, image / *, * / *;q = 0.8&apos;,</span><br><span class="line">    &apos;referer&apos;: f&apos;&#123;URL&#125;/read/pdf/&#123;bookid&#125;&apos;,</span><br><span class="line">    &apos;user-agent&apos;: &apos;Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36&apos;,</span><br><span class="line">    # noqa</span><br><span class="line">  &#125;</span><br><span class="line">  req = requests.get(url,headers=headers)</span><br><span class="line">  res = req.content</span><br><span class="line">  if not os.path.exists(str(bookid)):</span><br><span class="line">    os.mkdir(str(bookid))</span><br><span class="line">  with open(str(bookid)+&apos;/&apos;+str(page+1000)+&apos;.jpg&apos;,&apos;wb&apos;)as f:</span><br><span class="line">      f.write(res)</span><br><span class="line"></span><br><span class="line">  return res</span><br><span class="line">if __name__ == &apos;__main__&apos;:</span><br><span class="line">    &apos;&apos;&apos;使用时更改bookid和将你的cooike更换成你的&apos;&apos;&apos;</span><br><span class="line">    &apos;&apos;&apos;https://lib-nuanxin.wqxuetang.com/v1/read/k?bid=3187886&apos;&apos;&apos;</span><br><span class="line">    &apos;&apos;&apos;cooike用上面的url然后进去f12调试复制里面的cooike&apos;&apos;&apos;</span><br><span class="line">    bookid =3187886</span><br><span class="line">    cooike = &apos;_gid=377254409517; _gidv=6699d59c633414a0287f63aa61c56d4e; PHPSESSID=ngeq25ktm1cp2ipd54kabr2eii; Hm_lvt_a84b27ffd87daa3273555205ef60df89=1580866455,1580876574,1580883745,1580883761; Hm_lpvt_a84b27ffd87daa3273555205ef60df89=1580883767; acw_tc=3ccdc15315808917923211688e5e6c7e01cc28622fbf0190a83bc6ce183541&apos;</span><br><span class="line">    try:</span><br><span class="line">      page = bookinfo(bookid,cooike)[1]</span><br><span class="line">      print(page)</span><br><span class="line">      if not os.path.exists(str(bookid)):</span><br><span class="line">        os.mkdir(str(bookid))</span><br><span class="line">      for i in range(1,int(page)):</span><br><span class="line">        if not os.path.exists(str(bookid)+&apos;/&apos;+str(i+1000)+&apos;.jpg&apos;):</span><br><span class="line">          try:</span><br><span class="line">             print(i)</span><br><span class="line">             gen_jwt_token(bookid,i,cooike)</span><br><span class="line">             fetch_png(bookid,i)</span><br><span class="line">             time.sleep(6) </span><br><span class="line">          except Exception as e:</span><br><span class="line">            print(e)</span><br><span class="line">    except Exception as e:</span><br><span class="line">       print(e)</span><br></pre></td></tr></table></figure><p>若大量遇到下面这种情况：<br><img src="https://gitee.com/yhndbd/img/raw/master/picc/wenquanketang-spider/20200205054853614.png" alt=""><br>空列表，则说明你的cooike可能过期及时更换就好</p><p>跑完一遍后打开你的图片保存路径，然后排序按大小，然后翻到最下面若和以下一样说明这几张没成功，删了 重新来一遍就好，重新跑，不会覆盖之前的，只会抓取没有成功的：<br><img src="https://gitee.com/yhndbd/img/raw/master/2020/20200205055155346.png" alt=""></p><p>最后推荐一个好用的小工具，图片合成pdf工具：<br><a href="http://forspeed.onlinedown.net/down/FreePic2Pdf.zip" target="_blank" rel="noopener">pic2pdf</a></p><p>拥有这些，就可以成功的得到了自己的电子书。。今天就到这儿吧</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;前言&lt;/h1&gt;&lt;p&gt;今天打开发现文泉课堂需要登陆才能进行访问，一登陆，发现，昨天的502，明显好多了今天附上所有源码，供大家学习和参考&lt;/p&gt;
&lt;figure 
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="python" scheme="http://www.windknew.com/blog/tags/python/"/>
    
  </entry>
  
  <entry>
    <title>文泉课堂知识库图书爬虫</title>
    <link href="http://www.windknew.com/spider-wenquanketang/"/>
    <id>http://www.windknew.com/spider-wenquanketang/</id>
    <published>2020-02-04T05:38:17.000Z</published>
    <updated>2020-02-10T08:14:15.056Z</updated>
    
    <content type="html"><![CDATA[<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>昨天导员老师发了个通知，说在疫情期间，清华大学的文泉课堂资源免费开放，那何不用爬虫技术，将所有的的电子书下载下来，于是就有了这篇文章</p><h2 id="思路"><a href="#思路" class="headerlink" title="思路"></a>思路</h2><p>首先确定一下爬取的思路，浏览了一下发现并没有直接下载的链接，只能免费的阅读里面的书，打开阅读界面，书是以图片的形式呈现的，于是我们的爬虫思路是按顺序爬取所有的图片，最后合成一个pdf文件，这样我们就成功的获取到了这本书的pdf版</p><h2 id="过程"><a href="#过程" class="headerlink" title="过程"></a>过程</h2><p>我们打开浏览器，随便打开一本书，然后打开调试，发现网页源码并不能直接获得，是通过动态加载的，所以只能考虑图片地址的规律</p><p><img src="C:\Users\lyh\AppData\Roaming\Typora\typora-user-images\1580799748700.png" alt="1580799748700"></p><p>我们会发现，图片的url是页数，后面是一串字符串，这时经百度发现这是<a href="https://baijiahao.baidu.com/s?id=1608021814182894637&amp;wfr=spider&amp;for=pc" target="_blank" rel="noopener">jwt</a></p><p>可以理解成是web验证身份的一种方式吧，我也是第一次接触，在网上看了很多相关的文章，在这里推荐几篇</p><p><a href="https://blog.csdn.net/weixin_42030357/article/details/95629924" target="_blank" rel="noopener">利用JWT生成Token的原理及公钥和私钥加密和解密的原则</a></p><p><a href="http://blog.leapoahead.com/2015/09/06/understanding-jwt/" target="_blank" rel="noopener">JSON Web Token - 在Web应用间安全地传递信息</a></p><p><a href="https://baijiahao.baidu.com/s?id=1608021814182894637&amp;wfr=spider&amp;for=pc" target="_blank" rel="noopener">10分钟了解JSON Web令牌（JWT）</a></p><p><a href="https://blog.csdn.net/lizhiqiang1217/article/details/90523209" target="_blank" rel="noopener">Jwt简介</a></p><p>简单地说JWT 的原理是，服务器认证以后，生成一个 JSON 对象，发回给用户，就像下面这样。</p><figure class="highlight py"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">eyJhbGciOiJIUzI1NiJ9.eyJpc3MiOiJuaW5naGFvLm5ldCIsImV4cCI6IjE0Mzg5NTU0NDUiLCJuYW1lIjoid2FuZ2hhbyIsImFkbWluIjp0cnVlfQ.SwyHTEx_RQppr97g4J5lKXtabJecpejuef8AqKYMAJc</span><br></pre></td></tr></table></figure><p>jwt由三部分构成分别如下</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">Header（头部）</span><br><span class="line">Payload（负载）</span><br><span class="line">Signature（签名）</span><br></pre></td></tr></table></figure><p>我百度了一下有个<a href="http://jwt.calebb.net/" target="_blank" rel="noopener">jwt</a>的在线解密的网站，进去后随便复制一个图片的token如图：</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200204034646697.png" alt=""></p><h2 id="里面的数据："><a href="#里面的数据：" class="headerlink" title="里面的数据："></a>里面的数据：</h2><ol><li><p>alg属性表示签名的算法（algorithm），默认是 HMAC SHA256（写成HS256）；typ属性表示这个令牌（token）的类型（type），JWT 令牌统一写为JWT。</p></li><li><p>中间的dict是Payload，可以理解成我们要给服务器的数据，其中p代表页数，t是时间戳，b是书的id就是bid，k值我看了半天没看懂，后来在网页中我发现了个请求如下图：</p><p>​       <img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200204040745561.png" alt="k值"></p></li></ol><pre><code>刚好和上面的k值里的u，i，t，b，n对上，所以我就肯定没错了，是 这个  了，然后所有的东西确定了之后，我们就开始构建吧,然后在Headers里找到相关信息，并进行获取就行</code></pre><ol start="3"><li>最下面的是Signature 部分是对前两部分的签名，防止数据篡改。</li></ol><p>算出签名以后，把 Header、Payload、Signature 三个部分拼成一个字符串，每个部分之间用”点”（.）分隔，就可以返回给用户。</p><p>代码如下图示</p><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">def</span> <span class="title">gen_jwt_token</span><span class="params">(bookid, page)</span>:</span></span><br><span class="line">  <span class="string">''' get jwt token '''</span></span><br><span class="line">  cur_time = time.time()  //时间戳</span><br><span class="line">  jwtkey = gen_jwt_key(bookid)  //token里的k值</span><br><span class="line">  jwttoken = jwt.encode(</span><br><span class="line">    &#123;</span><br><span class="line">      <span class="string">"p"</span>: page,</span><br><span class="line">      <span class="string">"t"</span>: int(cur_time) * <span class="number">1000</span>,</span><br><span class="line">      <span class="string">"b"</span>: str(bookid),</span><br><span class="line">      <span class="string">"w"</span>: <span class="number">1000</span>,</span><br><span class="line">      <span class="comment"># "k": json.dumps(self.jwtkey),</span></span><br><span class="line">      <span class="string">"k"</span>: json.dumps(jwtkey),</span><br><span class="line">      <span class="string">"iat"</span>: int(cur_time),</span><br><span class="line">    &#125;,  //进行编码</span><br><span class="line">    JWT_SECRET,</span><br><span class="line">    algorithm=<span class="string">'HS256'</span>,</span><br><span class="line">  ).decode(<span class="string">'ascii'</span>)</span><br><span class="line">  <span class="keyword">return</span> jwttoken</span><br></pre></td></tr></table></figure><p>k值获取代码</p><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">def</span> <span class="title">gen_jwt_key</span><span class="params">(bookid)</span>:</span></span><br><span class="line">  URL =<span class="string">'https://lib-nuanxin.wqxuetang.com'</span></span><br><span class="line">  url = <span class="string">f'<span class="subst">&#123;URL&#125;</span>/v1/read/k?bid=<span class="subst">&#123;bookid&#125;</span>'</span></span><br><span class="line">  <span class="keyword">try</span>:</span><br><span class="line">    resp = requests.get(url,headers = headers)</span><br><span class="line">    resp.raise_for_status()</span><br><span class="line">  <span class="keyword">except</span> Exception <span class="keyword">as</span> exc:</span><br><span class="line">    print(exc)</span><br><span class="line"></span><br><span class="line">  <span class="keyword">try</span>:</span><br><span class="line">    jdata = resp.json()</span><br><span class="line">  <span class="keyword">except</span> Exception <span class="keyword">as</span> exc:</span><br><span class="line">    jdata = &#123;&#125;</span><br><span class="line"></span><br><span class="line">  res = jdata.get(<span class="string">'data'</span>)</span><br><span class="line">  <span class="keyword">if</span> res <span class="keyword">is</span> <span class="keyword">None</span>:</span><br><span class="line">    <span class="keyword">raise</span> Exception(<span class="string">'returned None, something is not right...'</span>)</span><br><span class="line"></span><br><span class="line">  <span class="keyword">return</span> res</span><br></pre></td></tr></table></figure><p>有了这些我们就可以来轻松的获取图片了</p><p>我们可以发现图片的url规律是</p><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">URL = <span class="string">'https://lib-nuanxin.wqxuetang.com'</span></span><br><span class="line"><span class="string">f'<span class="subst">&#123;URL&#125;</span>/page/img/<span class="subst">&#123;bookid&#125;</span>/<span class="subst">&#123;page&#125;</span>?k=<span class="subst">&#123;token&#125;</span>'</span></span><br></pre></td></tr></table></figure><p>然后就可以来获取图片了</p><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br></pre></td><td class="code"><pre><span class="line"><span class="function"><span class="keyword">def</span> <span class="title">fetch_png</span><span class="params">(bookid, page)</span>:</span></span><br><span class="line">  <span class="string">''' download book page img '''</span></span><br><span class="line">  token = gen_jwt_token(bookid, page)</span><br><span class="line">  print(token)</span><br><span class="line">  url = <span class="string">f'<span class="subst">&#123;URL&#125;</span>/page/img/<span class="subst">&#123;bookid&#125;</span>/<span class="subst">&#123;page&#125;</span>?k=<span class="subst">&#123;token&#125;</span>'</span></span><br><span class="line">  print(url)</span><br><span class="line">  headers = &#123;</span><br><span class="line">    <span class="string">'accept'</span>: <span class="string">'image / webp, image / *, * / *;q = 0.8'</span>,</span><br><span class="line">    <span class="string">'referer'</span>: <span class="string">f'<span class="subst">&#123;URL&#125;</span>/read/pdf/<span class="subst">&#123;bookid&#125;</span>'</span>,</span><br><span class="line">    <span class="string">'user-agent'</span>: <span class="string">'Mozilla/5.0 (Windows NT 10.0; WOW64)    AppleWebKit/537.36 (KHTML, like Gecko) Chrome/69.0.3497.100 Safari/537.36'</span>,</span><br><span class="line">  &#125;</span><br><span class="line">  req = requests.get(url,headers=headers)</span><br><span class="line">  res = req.content</span><br><span class="line">  <span class="keyword">if</span> <span class="keyword">not</span> os.path.exists(str(bookid)):</span><br><span class="line">    os.mkdir(str(bookid))</span><br><span class="line">  <span class="keyword">with</span> open(str(bookid)+<span class="string">'/'</span>+str(page)+<span class="string">'.jpg'</span>,<span class="string">'wb'</span>)<span class="keyword">as</span> f:</span><br><span class="line">      f.write(res)</span><br></pre></td></tr></table></figure><p>当我们获取到书的所有图片如图：</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200204042704956.png" alt=""></p><p>然后我们再用python将这些图片合成一个完整的pdf</p><p>具体代码如下：</p><figure class="highlight python"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br><span class="line">20</span><br><span class="line">21</span><br><span class="line">22</span><br><span class="line">23</span><br><span class="line">24</span><br><span class="line">25</span><br><span class="line">26</span><br><span class="line">27</span><br><span class="line">28</span><br><span class="line">29</span><br><span class="line">30</span><br><span class="line">31</span><br><span class="line">32</span><br><span class="line">33</span><br><span class="line">34</span><br><span class="line">35</span><br><span class="line">36</span><br><span class="line">37</span><br><span class="line">38</span><br><span class="line">39</span><br><span class="line">40</span><br><span class="line">41</span><br><span class="line">42</span><br><span class="line">43</span><br><span class="line">44</span><br><span class="line">45</span><br><span class="line">46</span><br><span class="line">47</span><br><span class="line">48</span><br></pre></td><td class="code"><pre><span class="line"><span class="comment"># -*- coding:utf-8 -*-</span></span><br><span class="line"><span class="comment">#!/usr/bin/env python</span></span><br><span class="line"><span class="comment"># Author:windknew</span></span><br><span class="line"></span><br><span class="line"><span class="keyword">import</span> os</span><br><span class="line"><span class="keyword">from</span> reportlab.lib.units <span class="keyword">import</span> mm, inch</span><br><span class="line"><span class="keyword">from</span> reportlab.lib.pagesizes <span class="keyword">import</span> A4,A5, landscape</span><br><span class="line"><span class="keyword">from</span> reportlab.pdfgen <span class="keyword">import</span> canvas</span><br><span class="line"></span><br><span class="line"></span><br><span class="line"><span class="comment"># 图片文件名称列表</span></span><br><span class="line">IMAGEFILES = []</span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">def</span> <span class="title">convertpdf</span><span class="params">(pdfFile)</span>:</span></span><br><span class="line">  <span class="string">'''多个图片合成一个pdf文件'''</span></span><br><span class="line">  (w, h) = landscape(A5) <span class="comment">#</span></span><br><span class="line">  cv = canvas.Canvas(pdfFile,pagesize=landscape(A5))</span><br><span class="line">  <span class="keyword">for</span> imagePath <span class="keyword">in</span> IMAGEFILES:</span><br><span class="line">     print(imagePath)</span><br><span class="line">     cv.drawImage(imagePath, <span class="number">0</span>, <span class="number">0</span>, w, h)</span><br><span class="line">     cv.showPage()</span><br><span class="line">  cv.save()</span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">def</span> <span class="title">getListImages</span><span class="params">(dirPath)</span>:</span></span><br><span class="line">  <span class="string">'''读取指定文件夹下所有的JPEG图片，存入列表'''</span></span><br><span class="line">  <span class="keyword">if</span> dirPath <span class="keyword">is</span> <span class="keyword">None</span> <span class="keyword">or</span> len(dirPath) == <span class="number">0</span>:</span><br><span class="line">     <span class="keyword">raise</span> ValueError(<span class="string">'dirPath不能为空，该值为存放图片的具体路径文件夹！'</span>)</span><br><span class="line">  <span class="keyword">if</span> os.path.isfile(dirPath):</span><br><span class="line">     <span class="keyword">raise</span> ValueError(<span class="string">'dirPath不能为具体文件，该值为存放图片的具体路径文件夹！'</span>)</span><br><span class="line">  <span class="keyword">if</span> os.path.isdir(dirPath):</span><br><span class="line">     <span class="keyword">for</span> imageName <span class="keyword">in</span> os.listdir(dirPath):</span><br><span class="line">        <span class="keyword">if</span> imageName.endswith(<span class="string">'.jpg'</span>) <span class="keyword">or</span>   imageName.endswith(<span class="string">'.jpeg'</span>):</span><br><span class="line">           absPath =converPath(dirPath) + imageName</span><br><span class="line">           IMAGEFILES.append(absPath)</span><br><span class="line"></span><br><span class="line"><span class="function"><span class="keyword">def</span> <span class="title">converPath</span><span class="params">(dirPath)</span>:</span></span><br><span class="line">  <span class="keyword">if</span> dirPath <span class="keyword">is</span> <span class="keyword">None</span> <span class="keyword">or</span> len(dirPath) == <span class="number">0</span>:</span><br><span class="line">     <span class="keyword">raise</span> ValueError(<span class="string">'dirPath不能为空！'</span>)</span><br><span class="line">  <span class="keyword">if</span> os.path.isfile(dirPath):</span><br><span class="line">     <span class="keyword">raise</span> ValueError(<span class="string">'dirPath不能为具体文件，该值为文件夹路径！'</span>)</span><br><span class="line">  <span class="keyword">if</span> <span class="keyword">not</span> str(dirPath).endswith(<span class="string">"\\"</span>):</span><br><span class="line">     <span class="keyword">return</span> dirPath + <span class="string">"\\"</span></span><br><span class="line">  <span class="keyword">return</span> dirPath</span><br><span class="line"></span><br><span class="line"><span class="keyword">if</span> __name__ == <span class="string">'__main__'</span>:</span><br><span class="line">    getListImages(<span class="string">'C:/Users/lyh/Desktop/ershoushu/2175744/'</span>)</span><br><span class="line">    pdfFile = converPath(<span class="string">'C:/Users/lyh/Desktop/ershoushu/2175744/'</span>)+<span class="string">'2175744'</span>+ <span class="string">".pdf"</span></span><br><span class="line">    convertpdf(pdfFile)</span><br></pre></td></tr></table></figure><h1 id="结语总结"><a href="#结语总结" class="headerlink" title="结语总结"></a>结语总结</h1><p>   这样我们就成功的获取到了一本想要的pdf，但是文泉课堂不知什么原因有时候就会502，这样的话我们就需要多爬几次，直到把整本书的img都抓到，这次分享就到这儿了</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;前言&lt;/h1&gt;&lt;p&gt;昨天导员老师发了个通知，说在疫情期间，清华大学的文泉课堂资源免费开放，那何不用爬虫技术，将所有的的电子书下载下来，于是就有了这篇文章&lt;/p&gt;
      
    
    </summary>
    
      <category term="python" scheme="http://www.windknew.com/blog/categories/python/"/>
    
    
      <category term="爬虫" scheme="http://www.windknew.com/blog/tags/%E7%88%AC%E8%99%AB/"/>
    
      <category term="python" scheme="http://www.windknew.com/blog/tags/python/"/>
    
  </entry>
  
  <entry>
    <title>使用hexo搭建博客（四）</title>
    <link href="http://www.windknew.com/hexo-3/"/>
    <id>http://www.windknew.com/hexo-3/</id>
    <published>2020-02-04T04:18:25.000Z</published>
    <updated>2020-02-10T08:11:55.804Z</updated>
    
    <content type="html"><![CDATA[<h1 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h1><p>承接上篇博客，上篇博客中我们在Github上部署成功，但Github上的访问速度在国内较慢，而且免费提供的资源有限，不适于长时期的博客运作，所以在此篇文章中，来说一下，我部署在云服务器的过程以及遇到的问题</p><p>首先我们了解一下，hexo利用git更新的流程，部署在Github上和部署在云服务器上没有特别大的本质区别</p><p>整个流程就是本地将markdown文件渲染成静态文件，然后Git推送到服务器的r代码仓库，让服务器通过钩子（hook）同步网站根目录，再利用nginx托管这些静态资源，就可以实现访问</p><h1 id="环境"><a href="#环境" class="headerlink" title="环境"></a>环境</h1><h2 id="本地环境"><a href="#本地环境" class="headerlink" title="本地环境"></a>本地环境</h2><p>Windows10,在本地已经装好了Git，nodejs，hexo，并且在本地已经成功的能调试出来hexo</p><h2 id="服务器环境"><a href="#服务器环境" class="headerlink" title="服务器环境"></a>服务器环境</h2><p>华为的ECS（centos7）</p><p>已装好了git，nodejs，以及编译好了nginx（编译这玩意儿有些慢，我编译的时候大概花了将近30分钟）</p><h1 id="本地机器配置"><a href="#本地机器配置" class="headerlink" title="本地机器配置"></a>本地机器配置</h1><h2 id="配置密钥"><a href="#配置密钥" class="headerlink" title="配置密钥"></a>配置密钥</h2><p>在终端使用git bash生成公匙，命令如下：</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">ssh-keygen -t rsa</span><br></pre></td></tr></table></figure><p>然后一路回车，</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200130111102078/20200130111145685.png" alt=""></p><p>就会在如图示的文件路径下生成一个密钥文件id_rsa.pub</p><p>这个密钥文件我们后面会用到，这个密钥相当于我们访问服务器的钥匙</p><h1 id="云服务器配置"><a href="#云服务器配置" class="headerlink" title="云服务器配置"></a>云服务器配置</h1><h2 id="Git，nodejs，Nginx等安装"><a href="#Git，nodejs，Nginx等安装" class="headerlink" title="Git，nodejs，Nginx等安装"></a>Git，nodejs，Nginx等安装</h2><p>具体安装过程可自行百度</p><h2 id="创建git新用户以及进行配置"><a href="#创建git新用户以及进行配置" class="headerlink" title="创建git新用户以及进行配置"></a>创建git新用户以及进行配置</h2><h3 id="创建git新用户"><a href="#创建git新用户" class="headerlink" title="创建git新用户"></a>创建git新用户</h3><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">adduser git #加入git用户</span><br><span class="line">passwd git #配置你的密码</span><br><span class="line">chmod 740 /etc/sudoers/ #修改git的sudo使用权限为只读</span><br><span class="line">vim /etc/sudoers #编辑sudoers</span><br></pre></td></tr></table></figure><p>打开sudoers，找到以下内容</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line"><span class="meta">#</span><span class="bash"><span class="comment"># Allow root to run any commands anywhere</span></span></span><br><span class="line">root    ALL=(ALL)       ALL</span><br></pre></td></tr></table></figure><p>在他的下面加入以下内容</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git ALL=(ALL)   ALL</span><br></pre></td></tr></table></figure><p>然后wq保存，并且将权限修改回来</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">chmod 400 /etc/sudoers</span><br></pre></td></tr></table></figure><h3 id="将公钥配置到服务器上"><a href="#将公钥配置到服务器上" class="headerlink" title="将公钥配置到服务器上"></a>将公钥配置到服务器上</h3><p>就是刚才我们生成的那个文件<br><img src="http://q4uie93wz.bkt.clouddn.com/20200130111102078/20200130111224785.png" alt=""><br>将该文件内容复制，在云服务器端，切换至刚建好的git用户下，创建<strong>.ssh</strong>文件和和<strong>authorized_keys</strong>文件</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">su git</span><br><span class="line">mkdir ~/.ssh</span><br><span class="line">vim ~/.ssh/authorized_keys</span><br></pre></td></tr></table></figure><p>然后修改权限</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">cd ~</span><br><span class="line">chmod 600 .ssh/authorzied_keys # 将文件设置为可读可写</span><br><span class="line">chmod 700 .ssh #将该文件夹设置为可读可写可执行（访问）</span><br></pre></td></tr></table></figure><h3 id="测试git链接"><a href="#测试git链接" class="headerlink" title="测试git链接"></a><strong>测试git链接</strong></h3><p>切换到本地机器在本地机器上测试是否能连接到你的远程Git用户</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">ssh -v git@SERVER_IP</span><br></pre></td></tr></table></figure><p>测试成功会出现如下：<br><img src="http://q4uie93wz.bkt.clouddn.com/20200130111102078/20200130111952913.png" alt=""><br>如果测试不成功，看看具体的输出信息，通常是公钥没配置好的原因，不用担心，把原来生成的公钥删了，try again  就欧克了</p><h3 id="创建网站根目录"><a href="#创建网站根目录" class="headerlink" title="创建网站根目录"></a><strong>创建网站根目录</strong></h3><p>创建网站的根目录目的是为了让nginx进行托管hexo 生成的静态文件</p><p>创建一个目录用于作为网站的根目录，切换到root用</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">su root</span><br><span class="line">mkdir /home/hexo    # 此目录为网站的根目录</span><br></pre></td></tr></table></figure><p>然后变更该目录的所有者</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">chown git:git -R /home/hexo</span><br></pre></td></tr></table></figure><h3 id="配置nginx"><a href="#配置nginx" class="headerlink" title="配置nginx"></a><strong>配置nginx</strong></h3><p>安装过程自行度娘就好，编译好nginx后进入nginx的配置文件</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">vim conf/nginx.conf</span><br></pre></td></tr></table></figure><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br><span class="line">5</span><br><span class="line">6</span><br><span class="line">7</span><br><span class="line">8</span><br><span class="line">9</span><br><span class="line">10</span><br><span class="line">11</span><br><span class="line">12</span><br><span class="line">13</span><br><span class="line">14</span><br><span class="line">15</span><br><span class="line">16</span><br><span class="line">17</span><br><span class="line">18</span><br><span class="line">19</span><br></pre></td><td class="code"><pre><span class="line">server&#123;</span><br><span class="line">        listen       8081;           #监听8081端口</span><br><span class="line">        server_name 139.159.245.212; #你的服务器名，通常是域名，如果是域名，你就需要监听80端口</span><br><span class="line">        root       /home/hexo;       #网站的根目录,根据自己所建自行修改</span><br><span class="line">        location / &#123;</span><br><span class="line"></span><br><span class="line">        &#125;</span><br><span class="line"></span><br><span class="line">   #access_log logs/access.log mylog;</span><br><span class="line"></span><br><span class="line">   error_page 404 /404.html;         #配置40x页面</span><br><span class="line">       location = /40x.html &#123;</span><br><span class="line">   &#125;</span><br><span class="line"></span><br><span class="line">   error_page 500 502 503 504 /50x.html; #配置50x页面</span><br><span class="line">       location = /50x.html &#123;</span><br><span class="line">   &#125;</span><br><span class="line"></span><br><span class="line">   &#125;</span><br></pre></td></tr></table></figure><p>注意使用 <code>nginx -t</code> 命令检查配置文件的语法是否出错。然后使用 <code>systemctl restart nginx.service</code> 或者</p><p>在编译好的nginx目录下使用<code>sbin/nginx -s reload</code>命令重启服务即可</p><h2 id="实现自动化部署"><a href="#实现自动化部署" class="headerlink" title="实现自动化部署"></a>实现自动化部署</h2><h3 id="建立git裸库（就是空的）"><a href="#建立git裸库（就是空的）" class="headerlink" title="建立git裸库（就是空的）"></a><strong>建立git裸库（就是空的）</strong></h3><p>在root用户下</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">su root</span><br><span class="line">cd /home/git   # 在 git 用户目录下创建</span><br><span class="line">git init --bare blog.git</span><br></pre></td></tr></table></figure><p>这时，<code>git</code> 用户的 <code>~</code> 目录下就存在一个 <code>blog.git</code> 文件夹，可使用 <code>ls</code> 命令查看。再修改<code>blog.git</code> 的所有者</p><h3 id="使用钩子同步网站根目录"><a href="#使用钩子同步网站根目录" class="headerlink" title="使用钩子同步网站根目录"></a><strong>使用钩子同步网站根目录</strong></h3><p>在这使用的是 <code>post-receive</code> 这个钩子，当 <code>git</code> 有收发的时候就会调用这个钩子。 在 <code>blog.git</code>裸库的 hooks 文件夹中，新建 <code>post-receive</code> 文件。</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">vim blog.git/hooks/post-receive</span><br></pre></td></tr></table></figure><p>填入以下内容，其中 <code>/home/hexo</code> 为网站目录，根据自己的填入,保存退出。</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">#!/bin/sh</span><br><span class="line">git --work-tree=/home/hexo --git-dir=/home/git/blog.git checkout -f</span><br></pre></td></tr></table></figure><p>该钩子的意思是当本地有提交到服务器时，会将文件放在/home/hexo下</p><p><code>-f</code>这个参数如果在多人协作的博客中可能会引发不好的结果，因为他是强制更新的意思，会将本地版本覆盖掉远程服务器的版本，但是是个人的博客系统就无所谓了</p><p>保存后，要赋予这个文件可执行权限。</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">chmod +x /home/git/blog.git/hooks/post-receive</span><br></pre></td></tr></table></figure><h2 id="本地机器中部署至服务器"><a href="#本地机器中部署至服务器" class="headerlink" title="本地机器中部署至服务器"></a>本地机器中部署至服务器</h2><p>在本地中，和部署到 <code>github</code> 服务一样，需要先 <code>hexo g</code> 命令生成静态文件，通过 <code>hexo s</code> 命令能够正常进行本地访问，并且确保<strong><em>已经安装</em></strong>了 <code>hexo-deployer-git</code>。</p><h3 id="配置Hexo"><a href="#配置Hexo" class="headerlink" title="配置Hexo"></a><strong>配置Hexo</strong></h3><p>hexo 根目录下的 <code>_config.yml</code> 文件，找到 <code>deploy</code>。</p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br><span class="line">4</span><br></pre></td><td class="code"><pre><span class="line">deploy:</span><br><span class="line">    type: git</span><br><span class="line">    repo: git@SERVER:/home/git/blog.git     # 填写你的服务器地址 将SERVER替换掉</span><br><span class="line">    branch: master      # 分支</span><br></pre></td></tr></table></figure><p>之后按照正常的流程部署，也可以在hexo项目中添加脚本scripts,脚本内容如下图所示（在package.json文件中添加）</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200130111102078/20200130114431386.png" alt=""></p><h2 id="测试自动化部署"><a href="#测试自动化部署" class="headerlink" title="测试自动化部署"></a>测试自动化部署</h2><p><img src="http://q4uie93wz.bkt.clouddn.com/20200130111102078/20200130114351552.png" alt=""><br>然后用hexo d 即可推送到远端服务器 然后可以用自己服务器ip访问自己的博客网站了</p><p>本次分享就到这儿，有任何问题欢迎留言，我会在第一时间，进行回复！！</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;前言&lt;/h1&gt;&lt;p&gt;承接上篇博客，上篇博客中我们在Github上部署成功，但Github上的访问速度在国内较慢，而且免费提供的资源有限，不适于长时期的博客运作，
      
    
    </summary>
    
      <category term="教程" scheme="http://www.windknew.com/blog/categories/%E6%95%99%E7%A8%8B/"/>
    
    
      <category term="hexo" scheme="http://www.windknew.com/blog/tags/hexo/"/>
    
      <category term="blog" scheme="http://www.windknew.com/blog/tags/blog/"/>
    
  </entry>
  
  <entry>
    <title>使用hexo搭建博客（三）</title>
    <link href="http://www.windknew.com/hexo-2/"/>
    <id>http://www.windknew.com/hexo-2/</id>
    <published>2020-02-03T05:40:59.000Z</published>
    <updated>2020-02-10T08:11:42.570Z</updated>
    
    <content type="html"><![CDATA[<h1 id="部署发行项目"><a href="#部署发行项目" class="headerlink" title="部署发行项目"></a>部署发行项目</h1><h2 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h2><p>这篇文章是基于你已经注册了github账号和创建了对应的仓库，通过配置ssh来建立连接</p><h2 id="创建Repository"><a href="#创建Repository" class="headerlink" title="创建Repository"></a>创建Repository</h2><p>创建一个Repository，名称规则为</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">username.github.name</span><br></pre></td></tr></table></figure><p>然后编辑hexo的配置文件_config.yml,修改如图示地方。repo修改你的仓库地方</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203031453107.png" alt=""></p><h2 id="生成ssh"><a href="#生成ssh" class="headerlink" title="生成ssh"></a>生成ssh</h2><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">$ ssh-keygen -t rsa -C &quot;邮件地址@youremail.com&quot;</span><br><span class="line">Generating public/private rsa key pair.</span><br><span class="line">Enter file in which to save the key (/Users/your_user_directory/.ssh/id_rsa):&lt;回车&gt;</span><br></pre></td></tr></table></figure><p>然后一路回车</p><h4 id="赋值id-rsa-pub文件内容，在github的settings中，点选SSH-keys，添加一个key，将内容粘贴进去"><a href="#赋值id-rsa-pub文件内容，在github的settings中，点选SSH-keys，添加一个key，将内容粘贴进去" class="headerlink" title=".赋值id_rsa.pub文件内容，在github的settings中，点选SSH keys，添加一个key，将内容粘贴进去"></a>.赋值id_rsa.pub文件内容，在github的settings中，点选SSH keys，添加一个key，将内容粘贴进去</h4><p><img src="C:\Users\lyh\AppData\Roaming\Typora\typora-user-images\1580714396039.png" alt="1580714396039"></p><h4 id="测试是否添加成功"><a href="#测试是否添加成功" class="headerlink" title="测试是否添加成功"></a>测试是否添加成功</h4><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">ssh -T git@github.com</span><br></pre></td></tr></table></figure><h2 id="部署到github上"><a href="#部署到github上" class="headerlink" title="部署到github上"></a>部署到github上</h2><p>在hexo中分别进行生成，上传</p><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br></pre></td><td class="code"><pre><span class="line">hexo g</span><br><span class="line">hexo d</span><br></pre></td></tr></table></figure><h2 id="部署成功后，可通过-http-pangyuanni-github-io-进行访问，其中将pangyuanni替换为你自己的username即可"><a href="#部署成功后，可通过-http-pangyuanni-github-io-进行访问，其中将pangyuanni替换为你自己的username即可" class="headerlink" title="部署成功后，可通过 http://pangyuanni.github.io 进行访问，其中将pangyuanni替换为你自己的username即可"></a>部署成功后，可通过 <a href="http://pangyuanni.github.io/" target="_blank" rel="noopener">http://pangyuanni.github.io</a> 进行访问，其中将pangyuanni替换为你自己的username即可</h2><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203032221032.png" alt=""></p><p>此次分享到这儿 下篇博客分享如何部署到自己的与服务器上</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h1 id=&quot;部署发行项目&quot;&gt;&lt;a href=&quot;#部署发行项目&quot; class=&quot;headerlink&quot; title=&quot;部署发行项目&quot;&gt;&lt;/a&gt;部署发行项目&lt;/h1&gt;&lt;h2 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;
      
    
    </summary>
    
      <category term="教程" scheme="http://www.windknew.com/blog/categories/%E6%95%99%E7%A8%8B/"/>
    
    
      <category term="hexo" scheme="http://www.windknew.com/blog/tags/hexo/"/>
    
      <category term="blog" scheme="http://www.windknew.com/blog/tags/blog/"/>
    
  </entry>
  
  <entry>
    <title>使用hexo搭建博客（二）</title>
    <link href="http://www.windknew.com/hexo-1/"/>
    <id>http://www.windknew.com/hexo-1/</id>
    <published>2020-02-02T02:34:30.000Z</published>
    <updated>2020-02-10T08:11:26.806Z</updated>
    
    <content type="html"><![CDATA[<h2 id="前言"><a href="#前言" class="headerlink" title="前言"></a>前言</h2><p>   承接上篇博客，上篇博客中我们已经能够在本地成功运行我们的hexo博客，这篇文章我们来说说hexo的主题等个性化操作</p><h2 id="主题"><a href="#主题" class="headerlink" title="主题"></a>主题</h2><p>  Hexo官网有很多很多主题供我们选择，我们可以在这些主题的基础之下进行修改，或者加入我们个性化的元素，hexo的官网网址是<a href="https://hexo.io/zh-cn/，" target="_blank" rel="noopener">https://hexo.io/zh-cn/，</a><br>  <img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203120627780.png" alt=""><br>  打开之后是这样，打开之后就是对hexo优点的介绍，然后我们选择主题然后打开就可以看到很多很多主题，由于hexo的服务器在国外加载可能较慢，耐心等待就好。</p><p>  <img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203120721133.png" alt=""></p><p>然后每个主题对应的名字就是主题的github地址，在我们hexo项目文件中找到theme进入之后，使用git clone 加主题的github地址，就可以把相应的主题文件克隆到我们的本地，我用我使用的material-x 这个主题为例，地址是<a href="https://github.com/xaoxuu/hexo-theme-material-x.git" target="_blank" rel="noopener">https://github.com/xaoxuu/hexo-theme-material-x.git</a></p><figure class="highlight shell"><table><tr><td class="gutter"><pre><span class="line">1</span><br></pre></td><td class="code"><pre><span class="line">git clone https://github.com/xaoxuu/hexo-theme-material-x.git</span><br></pre></td></tr></table></figure><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203121716821.png" alt=""></p><p>这样就能将主题文件克隆到本地，如图示，当然也可以在浏览器里下载然后，解压到你的themes文件夹下</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203121822897.png" alt=""></p><p>克隆完看看  看看使用说明，有没有相关的依赖包需要下载，若有按照说明进行下载，如 material-x</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203011121694.png" alt=""></p><p>npm i -S hexo-generator-search hexo-generator-json-content hexo-renderer-less</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203011259181.png" alt=""></p><h2 id="Hexo网站配置文件"><a href="#Hexo网站配置文件" class="headerlink" title="Hexo网站配置文件"></a>Hexo网站配置文件</h2><figure class="highlight plain"><table><tr><td class="gutter"><pre><span class="line">1</span><br><span class="line">2</span><br><span class="line">3</span><br></pre></td><td class="code"><pre><span class="line">在根目录下的_config.yml主要是对网站的总属性进行设置</span><br><span class="line">如：网站标题，网站logo,网站插件使用等全局的属性</span><br><span class="line">主题目录下的_config.yml主要是针对网站的布局，导航等特性设置进行设</span><br></pre></td></tr></table></figure><h2 id="启用主题"><a href="#启用主题" class="headerlink" title="启用主题"></a>启用主题</h2><p>打开站点配置文件（根目录下的_config.yml）找到theme，将其值改为你下载的主题的名字，如下</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203125512343.png" alt=""></p><p><strong>PS</strong> :注意theme的冒号后面有个空格，不然会报错</p><p>然后再次启动我们的hexo，打开localshost:4000就可以看到主题效果</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203011347920.png" alt=""></p><p>这样我们就更换了一个主题</p><p>关于网站的配置我们都可在网站的配置文件下更改：</p><p>刚更换完主题后，配置文件是这样的：</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203012031216.png" alt=""></p><p>自己配置完是这样的</p><p><img src="http://q4uie93wz.bkt.clouddn.com/20200203120623653/20200203011744303.png" alt=""></p><p>title是网站的标题</p><p>avatar 是网站的图标，</p><p>logo是网站的logo，</p><p>subtitle 是网站副标题</p><p>description 是网站描述</p><p>author 是作者</p><p>timezone 是时区</p><p>language 是语言</p><p>其他配置暂时可忽略</p><p>然后对于其他关于主题的设置可以到themes文件夹下里的主题文件里的_config.yml里面进行相关配置，比如评论系统，字数统计，背景图，等等相关配置都在里面进行配置，在配置文件里都有相关说明。</p><p>此次分享就到这儿，下篇博客我们分享如何部署项目</p>]]></content>
    
    <summary type="html">
    
      
      
        &lt;h2 id=&quot;前言&quot;&gt;&lt;a href=&quot;#前言&quot; class=&quot;headerlink&quot; title=&quot;前言&quot;&gt;&lt;/a&gt;前言&lt;/h2&gt;&lt;p&gt;   承接上篇博客，上篇博客中我们已经能够在本地成功运行我们的hexo博客，这篇文章我们来说说hexo的主题等个性化操作&lt;/p&gt;
&lt;h2 i
      
    
    </summary>
    
      <category term="教程" scheme="http://www.windknew.com/blog/categories/%E6%95%99%E7%A8%8B/"/>
    
    
      <category term="hexo" scheme="http://www.windknew.com/blog/tags/hexo/"/>
    
      <category term="blog" scheme="http://www.windknew.com/blog/tags/blog/"/>
    
  </entry>
  
</feed>
