JavaWeb学习笔记

一 丶HTML5

1.html简介

Hyper Text Markup Language (超文本标记语言)

简写:HTML

HTML 通过标签来标记要显示的网页中的各个部分。网页文件本身是一种文本文件,

通过在文本文件中添加标记符,可以告诉浏览器如何显示其中的内容(如:文字如何处理,画

面如何安排,图片如何显示等)

2.创建html文件

3.html文件的书写规范

<!DOCTYPE html><!--约束,声明-->
<html lang="zh_CN"><!--表示中文-->
</html>
<html>                         表示整个HTML页面的开始
    <head><!--表示头部信息,一般包括三部分内容,title标签,css样式,js脚本-->
        <meta charset="UTF-8">
        <title>标题</title>     标题
    </head>
    <body><!--body是页面的主体内容-->
        页面主体内容             
    </body>
</html>                        表示整个html页面的结束

Html 的代码注释

4.HTML标签介绍

1.标签的格式
<标签名>封装的数据</标签名>
2.标签名大小写不敏感
3.标签拥有自己的属性

1.基本属性:bgcolor=“red” 可以修改简单的样式效果

2.事件属性:οnclick=“alert(‘你好!’);” 可以直接设置事件响应后的代码。


4.标签分为单标签和双标签

1.单标签格式

<标签名/>
<br/><!--换行-->
<hr/><!--水平线-->

2.双标签格式

<标签名>...封装的数据...</标签名>
5.标签的语法
<!--标签不能交叉嵌套-->
正确:<div><span>早安,尚硅谷</span></div> 
错误:<div><span>早安,尚硅谷</div></span> <hr /> 

<!-- ②标签必须正确关闭 --> 
<!-- i.有文本内容的标签: -->
正确:<div>早安,尚硅谷</div> 
错误:<div>早安,尚硅谷 <hr /> 

    <!-- ii.没有文本内容的标签: --> 
    正确:<br />
    错误:<br> <hr /> 
    
    <!-- ③属性必须有值,属性值必须加引号 --> 
    正确:<font color="blue">早安,尚硅谷</font> 
    错误:<font color=blue>早安,尚硅谷</font> 
    错误:<font color>早安,尚硅谷</font> <hr /> 
    
    <!-- ④注释不能嵌套 --> 
    正确:<!-- 注释内容 --> <br/> 
    错误:<!-- <!-- 这是错误的 html 注释 --> --> <hr />

注意事项:

html 代码不是很严谨。有时候标签不闭合,也不会报错。

6.常用标签
6.1font字体标签
<body> <!-- 字体标签 需求 1:在网页上显示 我是字体标签 ,并修改字体为 宋体,颜色为红色。

font 标签是字体标签,它可以用来修改文本的字体,颜色,大小(尺寸) color 属性修改颜色
face 属性修改字体
size 属性修改文本大小 -->
    <font color="red" face="宋体" size="7">我是字体标签</font> </body>
6.2特殊字符
<!-- 特殊字符 需求 1:把 <br> 换行标签 变成文本 转换成字符显示在页面上 
常用的特殊字符: 
< ===>>>> &lt; 
> ===>>>> &gt; 
空格 ===>>>> &nbsp; 
-->

<!--通常情况下,HTML 会裁掉文档中的空格。假如你在文档中连续输入 10 个空格,那么 HTML 会去掉其中的9个。如果使用 &nbsp;,就可以在文档中增加空格。-->

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Vw4RRSY1-1624636891027)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210329170240203.png)]

6.3标题标签
<body>    <!--标题标签h1-h6都是标题标签h1最大align 是对齐属性leftrightcenter-->    <h1 align="left">标题1</h1>    <h2>标题2</h2>    <h3>标题3</h3>    <h4>标题4</h4>    <h5>标题5</h5>    <h6>标题6</h6></body>
6.4超链接(重点)
<body>    <!-- a 标签是 超链接 href 属性设置连接的地址 target 属性设置哪个目标进行跳转 _self 表示当前页面(默认值)_blank 表示打开新页面来进行跳转 --><a href="http://localhost:8080">百度</a><a href="http://localhost:8080" target="_self">百度_self</a><br/> <a href="http://localhost:8080" target="_blank">百度_blank</a><br/> </body>
6.5列表标签

无序列表

有序列表

<!--需求 1:使用无序,列表方式,把东北 F4,赵四,刘能,小沈阳,宋小宝,展示出来 ul 是无序列表ol 是有序列表type 属性可以修改列表项前面的符号 li 是列表项 --><ul type="none">    <li>赵四</li>    <li>赵四</li>    <li>赵四</li>    <li>赵四</li></ul>
6.6img标签

img 标签可以在 html 页面上显示图片

<body>    <!--img标签是图片标签,用来显示图片src属性可以设置图片的路径width 属性设置图片的宽度height 属性设置图片的高度border 属性设置图片边框大小alt 属性设置当指定路径找不到图片时,用来代替显示的文本内容在 JavaSE 中路径也分为相对路径和绝对路径.相对路径:从工程名开始算绝对路径:盘符:/目录/文件名在web中路径分为相对路径和绝对路径相对路径:. 表示当前文件所在的目录.. 表示当前文件所在的上一级目录文件名 表示当前文件所在目录的文件,相当于 ./文件名 ./ 可以省略绝对路径:正确格式是: http://ip:port/工程名/资源路径-->    <img src="">    <img src="1.jpg" width="200" height="260" border="1" alt="美女找不到"/>     <img src="../2.jpg" width="200" height="260" />     <img src="../imgs/3.jpg" width="200" height="260" />    <img src="../imgs/4.jpg" width="200" height="260" />    <img src="../imgs/5.jpg" width="200" height="260" />    <img src="../imgs/6.jpg" width="200" height="260" /></body>
6.7表格标签(重点)
<body>    <!--需求 1:做一个 带表头的 ,三行,三列的表格,并显示边框需求 2:修改表格的宽度,高度,表格的对齐方式,单元格间距。<b></b> 加粗table 标签是表格标签       border   设置表格标签           width    宽       height   高       align       cellspacing 设置单元格间距tr 是航标签th 是表头标签(加粗并且居中)td 是单元格标签     align 设置对齐方式--> <table border="1" width="400" height="200">     <tr>     <th>1.1</th>     <td>1.2</td>     <td>1.3</td>     </tr>     <tr>     <td>2.1</td>     <td>2.2</td>     <td>2.3</td>     </tr>     <tr>     <td>3.1</td>     <td>3.2</td>     <td>3.3</td>     </tr>    </table>   </body>
6.8跨行跨列表格(次重点)
colspan属性设置跨列
rowspan属性设置跨行
<body>    <!--需求 1:新建一个五行,五列的表格,第一行,第一列的单元格要跨两列第二行第一列的单元格跨两行,第四行第四列的单元格跨两行两列。colspan 属性设置跨列rowspan 属性设置跨行-->        <table width="500" height="500" cellspacing="0" border="1" >        <tr>        <td colspan="2">1.1</td>        <td>1.2</td>        <td>1.3</td>        <td>1.4</td>        </tr>         <tr>        <td rowspan="2 ">1.1</td>        <td>1.2</td>        <td>1.3</td>        <td>1.4</td>        </tr>         <tr>        <td>1.1</td>        <td>1.2</td>        <td>1.3</td>        <td>1.4</td>        </tr>         <tr>        <td>1.1</td>        <td>1.2</td>        <td>1.3</td>        <td>1.4</td>        </tr>    </table></body>
6.9iframe框架标签(内嵌窗口)

ifarme 标签它可以在一个 html 页面上,打开一个小窗口,去加载一个单独的页面.

<body>    我是一个单独的页面<br/>    <!--ifarme 标签可以在页面上开辟一个小区域显示一个单独的页面ifarme 和 a 标签组合使用的步骤:1 在 iframe 标签中使用 name 属性定义一个名称2 在 a 标签的 target 属性上设置 iframe 的 name 的属性值--> <iframe src="3.标题标签.html" weight="500" height=""/>   </body>
6.10表单标签(重点,必须掌握)

什么是表单?

表单就是 html 页面中,用来收集用户信息的所有元素集合.然后把这些信息发送给服务器

*input type=text文件输入框value设置默认显示内容
*input type=password密码输入框value设置默认显示内容
*input type=radio单选框name属性可以对其分组
*checked="checked"表示默认选中
*input type=checkbox复选框checked="checked"表示默认选中
*input type=reset重置按钮value属性修改按钮上的文本
*input type=submit提交按钮value修改按钮上的文本
*input type=button按钮value修改按钮上的文本
*input type=file是文件上传域*
*input type=hidden隐藏域 当我们要发送某些信息,而这些信息,不需要用户参与,就可以使用隐藏域(提交的 时候同时发送给服务器)*
*select下拉列表框*
*option标签是下拉列表框中的选项selected="selected"设置默认选中
*textarea表示多行文本输入框起始标签和结束标签中的内容是默认值)
*rows属性设置可以显示几行的高度
*cols属性设置每行可以显示几个字符宽度
<body>    <!--需求 1:创建一个个人信息注册的表单界面。包含用户名,密码,确认密码。性别(单选),兴趣爱好(多选),国籍(下拉列表)隐藏域,自我评价(多行文本域)。重置,提交。-->    <!--form 标签就是表单input type=text   是文件输入框        value   设置默认显示内容input type=password 是密码输入框 value 设置默认显示内容input type=radio 是单选框 name 属性可以对其进行分组checked="checked"表示默认选中input type=checkbox 是复选框 checked="checked"表示默认选中input type=reset 是重置按钮 value 属性修改按钮上的文本input type=submit 是提交按钮 value 属性修改按钮上的文本input type=button 是按钮 value 属性修改按钮上的文本input type=file 是文件上传域input type=hidden 是隐藏域 当我们要发送某些信息,而这些信息,不需要用户参与,就可以使用隐藏域(提交的 时候同时发送给服务器)select 标签是下拉列表框option 标签是下拉列表框中的选项 selected="selected"设置默认选中textarea 表示多行文本输入框 (起始标签和结束标签中的内容是默认值)rows 属性设置可以显示几行的高度cols 属性设置每行可以显示几个字符宽度--> <form>    用户名称:<input type="text" value="默认值"/><br/>    用户密码:<input type="password" value="abc"/><b/>    确认密码:<input type="password" value="abc"/><b/>    性别:<input type="radio" name="sex"/><input type="radio" name="sex" checked="checked"/><br/>    兴趣爱好:<input type="checkbox" checked="checked"/>Java<input type="checkbox"/>JavaScript    <input type="checkbox" />C++<br/>    国籍:<select>    <option>--请选择国籍--</option>    <option selected="selected">中国</option>    <option>美国</option>    <option>小日本</option></select><br/>    自我评价:<textarea rows="10" cols="20">我才是默认值</textarea><br/>    <input type="reset" value="abc"/>    <input type="submit"/></form></body>

表单格式化

<body><form><h1 align="center">用户注册</h1>    <table align="center">        <tr>            <td> 用户名称:</td>            <td><input type="text" value="默认值"/></td>        </tr>        <tr>            <td> 用户密码:</td>            <td><input type="password" value="abc"/></td>        </tr>        <tr>            <td>确认密码:</td>            <td><input type="password" value="abc"/></td>        </tr>        <tr>            <td>性别:</td>            <td><input type="radio" name="sex"/><input type="radio" name="sex" checked="checked"/></td>        </tr>        <tr>            <td> 兴趣爱好:</td>            <td><input type="checkbox" checked="checked"/>Java <input type="checkbox"/>JavaScript <input                    type="checkbox"/>C++            </td>        </tr>        <tr>            <td>国籍:</td>            <td><select>                <option>--请选择国籍--</option>                <option selected="selected">中国</option>                <option>美国</option>                <option>小日本</option>            </select></td>        </tr>        <tr>            <td>自我评价:</td>            <td><textarea rows="10" cols="20">我才是默认值</textarea></td>        </tr>        <tr>            <td><input type="reset"/></td>            <td align="center"><input type="submit"/></td>        </tr>    </table></form></body>

表单提交

form 标签是表单标签**

action 属性设置提交的服务器地址

method 属性设置提交的方式 GET(默认值)或 POST

表单提交的时候,数据没有发送给服务器的三种情况:

1、表单项没有 name 属性值

2、单选、复选(下拉列表中的 option 标签)都需要添加 value 属性,以便发送给服务器

3、表单项不在提交的 form 标签中

GET 请求的特点是:

1、浏览器地址栏中的地址是:action 属性[+?+请求参数]

请求参数的格式是:name=value&name=value

2、不安全

3、它有数据长度的限制

POST 请求的特点是:

1、浏览器地址栏中只有 action 属性值

2、相对于 GET 请求要安全

3、理论上没有数据长度的限制

<form action="http://localhost:8080" method="post"><input type="hidden" name="action" value="login"/>    <h1 align="center">用户注册</h1>    <table align="center">        <tr>            <td> 用户名称:</td>            <td><input type="text" name="username" value="默认值"/></td>        </tr>        <tr>            <td> 用户密码:</td>            <td><input type="password" name="password" value="abc"/></td>        </tr>        <tr>            <td>性别:</td>            <td><input type="radio" name="sex" value="boy"/><input type="radio" name="sex" checked="checked"                                                                     value="girl"/></td>        </tr>        <tr>            <td> 兴趣爱好:</td>            <td>                <input name="hobby" type="checkbox" checked="checked" value="java"/>Java <input name="hobby"                                                                                                type="checkbox"                                                                                                value="js"/>JavaScript                <input name="hobby" type="checkbox" value="cpp"/>C++            </td>        </tr>        <tr>            <td>国籍:</td>            <td><select name="country">                <option value="none">--请选择国籍--</option>                <option value="cn" selected="selected">中国</option>                <option value="usa">美国</option>                <option value="jp">小日本</option>            </select></td>        </tr>        <tr>            <td>自我评价:</td>            <td><textarea name="desc" rows="10" cols="20">我才是默认值</textarea></td>        </tr>        <tr>            <td><input type="reset"/></td>            <td align="center"><input type="submit"/></td>        </tr>    </table></form>
6.11其他标签
div标签默认独占一行
span 标签它的长度是封装数据的长度
p 段落标签默认会在段落的上方或下方各空出一行来(如果已有就不再空)
<body><div>div 标签 1</div><div>div 标签 2</div><span>span 标签 1</span> <span>span 标签 2</span><p>p 段落标签 1</p><p>p 段落标签 2</p></body>

二丶CSS

2.1CSS技术介绍

CSS 是「层叠样式表单」。是用于(增强)控制网页样式并允许将样式信息与网页内容分离的一种标记性语言。

2.2CSS语法规则

选择器:浏览器根据“选择器”决定受 CSS 样式影响的 HTML 元素(标签)。

属性: (property) 是你要改变的样式名,并且每个属性都有一个值。属性和值被冒号分开,并 由花括号包围,这样就组成了一个完整的样式声明(declaration),例如:p {color: blue}

**多个声明:**如果要定义不止一个声明,则需要用分号将每个声明分开。虽然最后一条声明的 最后可以不加分号(但尽量在每条声明的末尾都加上分号)

2.3CSS和HTML的结合方式

2.3.1第一种方法

在标签的 style 属性上设置”key:value value;”,修改标签样式。

<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>Title</title></head><body> <!--需求 1:分别定义两个 div、span 标签,分别修改每个 div 标签的样式为:边框 1 个像素,实线,红色。--><div style="border: 1px solid red;">div 标签 1</div><div style="border: 1px solid red;">div 标签 2</div><span style="border: 1px solid red;">span 标签 1</span> <span style="border: 1px solid red;">span 标签 2</span></body></html>

问题:这种方式的缺点?

1.如果标签多了。样式多了。代码量非常庞大。

2.可读性非常差。

3.Css 代码没什么复用性可方言。

2.3.2第二种方法

在 head 标签中,使用 style 标签来定义各种自己需要的 css 样式。

格式如下:

xxx {

Key : value value;

}

<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>Title</title> <!--style 标签专门用来定义 css 样式代码-->    <style type="text/css"> /* 需求 1:分别定义两个 div、span 标签,分别修改每个 div 标签的样式为:边框 1 个像素,实线,红色。*/    div {        border: 1px solid red;    }    span {        border: 1px solid red;    } </style></head><body><div>div 标签 1</div><div>div 标签 2</div><span>span 标签 1</span> <span>span 标签 2</span></body></html>

问题:这种方式的缺点。

1.只能在同一页面内复用代码,不能在多个页面中复用 css 代码。

2.维护起来不方便,实际的项目中会有成千上万的页面,要到每个页面中去修改。工作量太大了。

2.3.3第三种方法

把 css 样式写成一个单独的 css 文件,再通过 link 标签引入即可复用。

使用 html 的 <link rel=“stylesheet” type=“text/css” href="./styles.css" /> 标签 导入 css 样 式文件。

1.CSS文件代码

div{    border: 5px solid red;}span{    border: 1px solid red;}

2.html文件代码

<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>Title</title> <!--link 标签专门用来引入 css 样式代码-->    <link rel="stylesheet" type="text/css" href="1.css"/></head><body><div>div 标签 1</div><div>div 标签 2</div><span>span 标签 1</span> <span>span 标签 2</span></body></html>

2.4CSS选择器

2.4.1标签名选择器

标签名选择器的格式是:

标签名{

属性:值;

}

标签名选择器,可以决定哪些标签被动的使用这个样式

<!DOCTYPE html><html><head>    <meta charset="UTF-8">    <title>CSS 选择器</title>    <style type="text/css">         div {        border: 1px solid yellow;        color: blue;        font-size: 30px;    }    span {        border: 5px dashed blue;        color: yellow;        font-size: 20px;    } </style></head><body> <!-- 需求 1:在所有 div 标签上修改字体颜色为蓝色,字体大小 30 个像素。边框为 1 像素黄色实线。并且修改所有 span 标签的字体颜色为黄色,字体大小 20 个像素。边框为 5 像素蓝色虚线。 --><div>div 标签 1</div><div>div 标签 2</div><span>span 标签 1</span> <span>span 标签 2</span></body></html>

2.4.2ID选择器

id 选择器的格式是:

#id 属性值{

属性:值;

}

id 选择器,可以让我们通过 id 属性选择性的去使用这个样式。

<!DOCTYPE html><html><head>    <meta charset="UTF-8">    <title>ID 选择器</title>    <style type="text/css">     #id001 {        color: blue;        font-size: 30px;        border: 1px yellow solid;    }    #id002 {        color: red;        font-size: 20px;        border: 5px blue dotted;    } </style></head><body><!-- 需求 1:分别定义两个 div 标签, 第一个 div 标签定义 id 为 id001 ,然后根据 id 属性定义 css 样式修改字体颜色为蓝色, 字体大小 30 个像素。边框为 1 像素黄色实线。第二个 div 标签定义 id 为 id002 ,然后根据 id 属性定义 css 样式 修改的字体颜色为红色,字体大小 20 个像素。 边框为 5 像素蓝色点线。 --><div id="id002">div 标签 1</div><div id="id001">div 标签 2</div></body></html>

2.4.3Class选择器

class 类型选择器的格式是:

.class 属性值{

属性:值;

}

class 类型选择器,可以通过 class 属性有效的选择性地去使用这个样式。

<!DOCTYPE html><html><head>    <meta charset="UTF-8">    <title>class 类型选择器</title>    <style type="text/css">     .class01 {        color: blue;        font-size: 30px;        border: 1px solid yellow;    }    .class02 {        color: grey;        font-size: 26px;        border: 1px solid red;    } </style></head><body><!--需求 1:修改 class 属性值为 class01 的 span 或 div 标签,字体颜色为蓝色,字体大小 30 个像素。边框为 1 像素黄色实线。 需求 2:修改 class 属性值为 class02 的 div 标签,字体颜色为灰色,字体大小 26 个像素。边框为 1 像素红色实线。 --><div class="class02">div 标签 class01</div><div class="class02">div 标签</div><span class="class02">span 标签 class01</span> <span>span 标签 2</span></body></html>

1.id与class的区别
1.1 id相当于人的身份证,不可以重复

1.2 class相当于人的名称可以重复

2.1一个html标签只能绑定一个id名称

2.2一个html标签可以绑定多个class名称

2.id选择器与class选择器的区别
2.1id选择器是以#开头

2.2class选择器是以.开头

3.注意点
3.1id一般情况下是给js用的,所有除非特殊情况下,否则不要用id去设置样式

3.2在企业中一个开发人员对类的使用可以看出这个开发人员的技术水平,一般情况下企业开发中要注重冗余代码的抽取,可以将一些公共的代码抽取到一个类选择器中然后让标签和这个类绑定即可

2.4.4组合选择器

组合选择器的格式是:

选择器 1,选择器 2,选择器 n{

属性:值;

}

组合选择器可以让多个选择器共用同一个 css 样式代码。

<!DOCTYPE html><html><head>    <meta charset="UTF-8">    <title>class 类型选择器</title>    <style type="text/css"> .class01, #id01 {        color: blue;        font-size: 20px;        border: 1px yellow solid;    } </style></head><body> <!-- 需求 1:修改 class="class01" 的 div 标签 和 id="id01" 所有的 span 标签, 字体颜色为蓝色,字体大小 20 个像素。边框为 1 像素黄色实线。 --><div id="id01">div 标签 class01</div><br/> <span>span 标签</span> <br/><div>div 标签</div><br/><div>div 标签 id01</div><br/></body></html>

2.5常用样式

1.字体颜色

color:red;

颜色可以写颜色名如:black, blue, red, green 等

颜色也可以写 rgb 值和十六进制表示值:如 rgb(255,0,0),#00F6DE,如果写十六进制值必 须加#

2.宽度

width:19px;

宽度可以写像素值:19px;

也可以写百分比值:20%;

3.高度

height:20px;

高度可以写像素值:19px;

也可以写百分比值:20%;

4.背景颜色

background-color:#0F2D4C

5.字体样式

color:#FF0000;字体颜色红色

font-size:20px; 字体大小

5.红色1像素实线边框

border:1px solid red;

6.DIV居中

margin-left: auto;

margin-right: auto;

7.文本居中

text-align: center;

8.超链接去下划线

text-decoration: none;

9.表格细线

table {

border: 1px solid black; /设置边框/

border-collapse: collapse; /将边框合并/

}

td,th {

border: 1px solid black; /设置边框/

}

10.列表去除修饰

ul {

list-style: none;

}

示例代码:

<!DOCTYPE html><html><head>    <meta charset="UTF-8">    <title>06-css 常用样式.html</title>    <style type="text/css"> div {        color: red;        border: 1px yellow solid;        width: 300px;        height: 300px;        background-color: green;        font-size: 30px;        margin-left: auto;        margin-right: auto;        text-align: center;    }    table {        border: 1px red solid;        border-collapse: collapse;    }    td {        border: 1px red solid;    }    a {        text-decoration: none;    }    ul {        list-style: none;    } </style></head><body><ul>    <li>11111111111</li>    <li>11111111111</li>    <li>11111111111</li>    <li>11111111111</li>    <li>11111111111</li></ul><table>    <tr>        <td>1.1</td>        <td>1.2</td>    </tr></table><a href="http://www.baidu.com">百度</a><div>我是 div 标签</div></body></html>

三丶JavaScript

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-fhIafiV6-1624636891031)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210329214917262.png)]

1.JavaScript介绍

Javascript 语言诞生主要是完成页面的数据验证。因此它运行在客户端,需要运行浏览器来解析执行 JavaScript 代码。

JS 是 Netscape 网景公司的产品,最早取名为 LiveScript;为了吸引更多 java 程序员。更名为 JavaScript。

JS 是弱类型,Java 是强类型

弱类型就是类型可变

强类型,就是定义变量的时候,类型已确定,而且不可变

int i=12
var i;i=12;i="abc";

特点

  1. 交互性(它可以做的就是信息的动态交互)

  2. 安全性(不允许直接访问本地硬盘)

  3. 跨平台性(只要是可以解释 JS 的浏览器都可以执行,和平台无关)

2.JavaScript和HTML代码的结合方式

2.1第一种方式

只需要在 head 标签中,或者在 body 标签中, 使用 script 标签 来书写 JavaScript 代码

<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>Title</title>    <script type="text/javascript"> // alert 是 JavaScript 语言提供的一个警告框函数。 // 它可以接收任意类型的参数,这个参数就是警告框的提示信息 alert("hello javaScript!"); </script></head><body></body></html></html>

2.2第二种方式

使用 script 标签引入 单独的 JavaScript 代码文件

现在需要使用 script 引入外部的 js 文件来执行

src 属性专门用来引入 js 文件路径(可以是相对路径,也可以是绝对路径)

script 标签可以用来定义 js 代码,也可以用来引入 js 文件

但是,两个功能二选一使用。不能同时使用两个功能

3.变量

什么是变量?变量是可以存放某些值的内存的命名。

JavaScript 的变量类型:

数值类型: number

字符串类型: string

对象类型: object

布尔类型: boolean

函数类型: function

JavaScript 里特殊的值:

**undefined :**未定义,所有 js 变量未赋于初始值的时候,默认值都是 undefined.

**null :**空值

**NaN :**全称是:Not a Number。非数字。非数值

JS 中的定义变量格式

var 变量名;

var 变量名 = 值;

 var i; // alert(i);// undefined i = 12; // typeof()是 JavaScript 语言提供的一个函数。// alert( typeof(i) ); // number    i = "abc"; // 它可以取变量的数据类型返回// alert( typeof(i) ); // String var a = 12; var b = "abc"; alert( a * b ); // NaN 是非数字,非数值

4.关系比较运算

等于: == 等于是简单的做字面值的比较

全等于: === 除了做字面值的比较之外,还会比较两个变量的数据类型

5.逻辑运算

且运算: &&

或运算: ||

取反运算: !

在 JavaScript 语言中,所有的变量,都可以做为一个 boolean 类型的变量去使用。

0 、null、 undefined、””(空串) 都认为是 false;

/*

&& 且运算。

有两种情况:

第一种:当表达式全为真的时候。返回最后一个表达式的值。

第二种:当表达式中,有一个为假的时候。返回第一个为假的表达式的值

|| 或运算

第一种情况:当表达式全为假时,返回最后一个表达式的值

第二种情况:只要有一个表达式为真。就会把回第一个为真的表达式的值 并且 && 与运算 和 ||或运算 有短路。 短路就是说,当这个&&或||运算有结果了之后 。后面的表达式不再执行

*/

6.数组(重点)

JS 中 数组的定义:

格式:

var 数组名 = []; // 空数组

var 数组名 = [1 , ’abc’ , true]; // 定义数组同时赋值元素

        var arr = [true, 1]; // 定义一个空数组         // alert( arr.length ); // 0         arr[0] = 12;         // alert( arr[0] );//12         // alert( arr.length ); // 0                // javaScript 语言中的数组,只要我们通过数组下标赋值,那么最大的下标值,就会自动的给数组做扩容操作。         arr[2] = "abc";         alert(arr.length); //3         // alert(arr[1]);// undefined                // 数组的遍历        for (var i = 0; i < arr.length; i++){             alert(arr[i]);         } 

7.函数(重点)

7.1函数的两种定义方式

第一种,可以使用 function 关键字来定义函数。

使用的格式如下:

``function 函数名(形参列表){`

函数体

}

在 JavaScript 语言中,如何定义带有返回值的函数?

只需要在函数体内直接使用 return 语句返回值即可!

 //定义无参函数        function fun() {            alert("wucanhanshubeidiaoyong")        }        //函数调用才会执行        fun();        //有参函数        function fun2(a, b) {            alert("youcanhanshu" + a + b);        }        fun(12, "abc");        //定义带有返回值的函数        function uf(m, n) {            var s = m + n;            return s;        }

函数的第二种定义方式,格式如下:

使用格式如下:

var 函数名 = function(形参列表) { 函数体

}

var fun=function(){alert("无参函数");}var fun2=function(a,b){alert("有参函数");}

注:在 Java 中函数允许重载。但是在 JS 中函数的重载会直接覆盖掉上一次的定义

就近原则

7.2函数的 arguments 隐形参数(只在 function 函数内)

  • 就是在 function 函数中不需要定义,但却可以直接用来获取所有参数的变量。我们管它叫隐形参数。
  • 隐形参数特别像 java 基础的可变长参数一样。
  • public void fun( Object … args );
  • 可变长参数其他是一个数组。
  • 那么 js 中的隐形参数也跟 java 的可变长参数一样。操作类似数组。
function fun () {   alert(arguments[0]);    alert(arguments[0]);    alert(arguments[0]); }fun(1.2.3); 

8.JS中自定义对象(扩展)

Object 形式的自定义对象

对象的定义:

var 变量名 = new Object(); // 对象实例(空对象)

变量名.属性名 = 值; // 定义一个属性

变量名.函数名 = function(){} // 定义一个函数

对象的访问:

变量名.属性 /

函数名();

var obj=new Object();obj.name="xiaoxiao";obj.age=19;obj.fun=function(){    alert(this.name+this.age);}

{}花括号形式的自定义对像

对象的定义:

var 变量名 = { // 空对象

属性名:值, // 定义一个属性

属性名:值, // 定义一个属性

函数名:function(){} // 定义一个函数

};

对象的访问:

变量名.属性 / 函数名();

var obj ={    name:"xiaoxiao";    age:19;     fun:function(){              }}

9.js中的事件

什么是事件?事件是电脑输入设备与页面进行交互的响应。我们称之为事件。

常用的事件:

onload加载完成事件页面加载完成之后,常用于做页面 js 代码初始化操作
onclick单击事件常用于按钮的点击响应操作。
onblur失去焦点事件常用用于输入框失去焦点后验证其输入内容是否合法。
onchange内容发生改变事件常用于下拉列表和输入框内容发生改变后操作
onsubmit表单提交事件常用于表单提交前,验证所有表单项是否合法。

事件的注册又分为静态注册和动态注册两种:

什么是事件的注册(绑定)?

其实就是告诉浏览器,当事件响应后要执行哪些操作代码,叫事件注册或事件绑定。

静态注册事件:通过 html 标签的事件属性直接赋于事件响应后的代码,这种方式我们叫静态注册。

动态注册事件:是指先通过 js 代码得到标签的 dom 对象,然后再通过 dom 对象.事件名 = function(){} 这种形式赋于事件 响应后的代码,叫动态注册。

动态注册基本步骤

  1. 获取标签对象
  2. 标签对象.事件名=function(){}

onload事件

<script type="text/javascript">   //onload事件方法    function onloadt(){            }    //onload事件动态注册    window.οnlοad=function(){            }</script><!--静态注册onload事件--><body onload="alert('jingtaizhuce')">    </body>

onclick事件

<script type="text/javascript">   //onclick事件方法    function onclickt(){            }    //onlick事件动态注册    window.onlick=function(){        /*        document js提供的一个对象        get 获取        element 标签        by 通过        id  id属性        通过id属性获取标签对象        */      var btnobj=document.getElementById("btn01");        btnobj.οnclick=function(){            alert("dongtai");        }    }</script><body>    <button οnclick="onclickt";>        按钮1    </button>    <button id="btn01">        按钮2    </button></body>

onblur事件

<title>Title</title>    <script type="text/javascript">        function ob() {            //控制台对象,向浏览器打印输出            console.log("静态注册");        }        //动态注册        window.onload = function () {            //1.获取标签对象            var p = document.getElementById("password");            //2.通过标签名.事件名=function(){};            p.onblur = function () {                console.log("静态注册");            }        }    </script></head><body>user:<input type="text" onblur="ob()"><br/>password:<input type="text"><br/>

onchange事件

 <script type="text/javascript">        function f() {            alert("醒醒你没有")        }        window.onload = function () {            var v = document.getElementById("001")            v.onchange=function () {                alert("差不多的了")            }        }    </script></head><body>请选择心中的女神:<!--静态注册onchange事件--><select onchange="f()">    <option>--女生--</option>    <option>--花花--</option>    <option>--欢欢--</option>    <option>--美美--</option></select><br>-------------------------------------<br>请选择心中的男神:<!--静态注册onchange事件--><select onchange="f()" id="001">    <option>--女生--</option>    <option>--花花--</option>    <option>--欢欢--</option>    <option>--美美--</option></select></body>

onsubmit事件

<title>Title</title>    <script type="text/javascript">        //静态        function f() {            //验证所有表单项是否合法            alert("jingtai");            return false;        }        window.onload = function () {            var f = document.getElementById("001");            f.onsubmit = function () {                alert("动态注册表单提交事件----发现不合法");                return false;            }        }    </script></head><body><!--return false可以阻止表单提交--><form action="http:localhost:8080" method="get" onsubmit="return f()">    <input type="submit" value="静态注册"/></form><form action="http:localhost:8080" method="get" id="001" onsubmit="return f()">    <input type="submit" value="动态注册"/></form></body>

10.DOM模型(重点)

DOM 全称是 Document Object Model 文档对象模型

大白话,就是把文档中的标签,属性,文本,转换成为对象来管理。

那么 它们是如何实现把标签,属性,文本转换成为对象来管理呢。这就是我们马上要学习的重点。

10.1Document对象(重点)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-I5xOonag-1624636891033)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210330201821939.png)]

Document 对象的理解:

**第一点:**Document 它管理了所有的 HTML 文档内容。

**第二点:**document 它是一种树结构的文档。有层级关系。

第三点:它让我们把所有的标签 都 对象化

第四点:我们可以通过 document 访问所有的标签对象。

举例:

**有一个人有年龄:**18 岁,性别:女,名字:张某某

我们要把这个人的信息对象化怎么办!

Class Person {

private int age;

private String sex;

private String name;

}

那么 html 标签 要 对象化 怎么办?

<body> <div id="div01">div01</div> </body>

模拟对象化,相当于:

class Dom{

private String id; // id 属性

private String tagName; //表示标签名

private Dom parentNode; //父亲

private List<Dom> children; // 孩子结点

private String innerHTML; // 起始标签和结束标签中间的内容

}

10.2Document **对象中的方法介绍(重点)

document.getElementById(elementId)

通过标签的 id 属性查找标签 dom 对象,elementId 是标签的 id 属性值

document.getElementsByName(elementName)

通过标签的 name 属性查找标签 dom 对象,elementName 标签的 name 属性值

document.getElementsByTagName(tagname)

通过标签名查找标签 dom 对象。tagname 是标签名

document.createElement( tagName)

方法,通过给定的标签名,创建一个标签对象。tagName 是要创建的标签名

注:

document 对象的三个查询方法,如果有 id 属性,优先使用 getElementById 方法来进行查询

如果没有 id 属性,则优先使用 getElementsByName 方法来进行查询

如果 id 属性和 name 属性都没有最后再按标签名查 getElementsByTagName

以上三个方法,一定要在页面加载完成之后执行,才能查询到标签对象。

<script type="text/javascript">        function f() {//1.当我们要操作一个标签的时候要先获取标签对象            var elementById = document.getElementById("username");            var usernametext=elementById.value;            var patt=/^w{5,12}$/;            //text测试是否匹配规则            if (patt.test()){                alert("hefa")            }else {                alert("warning")            }        }    </script></head><body>username:<input type="text" id="username" value="wzg"><button onclick="f()">check</button></body>

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-AOPqFem6-1624636891039)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210330211140849.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-8IkBwWFU-1624636891041)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210330211203507.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-67HP4AJt-1624636891042)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210330211224163.png)]

<script type="text/javascript">        //表示字符串中,是否包含字母e        var patt=new RegExp("e");        var patt = /e/;        //表示字符串中是否包含字母a或b或c        var patt = /[abc]/;        //表示要求字符串,是否包含小写字母        var patt=/[a-z]/        //表示要求字符串,是否包含大写字母        var patt=/[A-Z]/        //表示要求字符串,是否包含任意数字        var patt=/[0-9]/        //表示要求字符串,是否包含任意数字,字母,下划线        var patt=/\w/;        //表示要求字符串,是否包含至少一个a        var patt=/a+/;        //表示要求字符串,是否*包含*零个 或 多个a        var patt=/a*/;        //表示要求字符串,是否包含一个或0个a        var patt=/a?/;        //表示要求字符串,是否包含连续三个a        var patt=/a{3}/;        //表示要求字符串,是否*包含*至少三个连续的a,最多五个连续的a        var patt=/a{3,5}/;        alert(patt);        var str = "abc";        alert(patt.test(str));    </script>

getElementById 方法示例代码:

<script type="text/javascript">        function f() {//1.当我们要操作一个标签的时候要先获取标签对象            var elementById = document.getElementById("002");            //var usernametext = elementById.value;            //innerhtml表示起始标签和结束标签中的内容            //innerhtml属性可读可写            elementById.innerHTML="right";            var patt = /^w{5,12}$/;            //text测试是否匹配规则            if (patt.test(patt)) {                elementById.innerHTML="right";            } else {                elementById.innerHTML="warning";            }        }    </script></head><body>username:<input type="text" id="username" value="wzg"><span id="002" style="color: red">    it not right</span><button onclick="f()">check</button></body>
    <script type="text/javascript">        // 全选        function checkAll() {            // 让所有复选框都选中            // document.getElementsByName();是根据 指定的name属性查询返回多个标签对象集合            // 这个集合的操作跟数组 一样            // 集合中每个元素都是dom对象            // 这个集合中的元素顺序是他们在html页面中从上到下的顺序            var hobbies = document.getElementsByName("hobby");            // checked表示复选框的选中状态。如果选中是true,不选中是false            // checked 这个属性可读,可写            for (var i = 0; i < hobbies.length; i++){                hobbies[i].checked = true;            }        }        //全不选        function checkNo() {            var hobbies = document.getElementsByName("hobby");            // checked表示复选框的选中状态。如果选中是true,不选中是false            // checked 这个属性可读,可写            for (var i = 0; i < hobbies.length; i++){                hobbies[i].checked = false;            }        }        // 反选        function checkReverse() {            var hobbies = document.getElementsByName("hobby");            for (var i = 0; i < hobbies.length; i++) {                hobbies[i].checked = !hobbies[i].checked;                // if (hobbies[i].checked) {                //     hobbies[i].checked = false;                // }else {                //     hobbies[i].checked = true;                // }            }        }    </script></head><body>    兴趣爱好:    <input type="checkbox" name="hobby" value="cpp" checked="checked">C++    <input type="checkbox" name="hobby" value="java">Java    <input type="checkbox" name="hobby" value="js">JavaScript    <br/>    <button onclick="checkAll()">全选</button>    <button onclick="checkNo()">全不选</button>    <button onclick="checkReverse()">反选</button></body>

注:

document 对象的三个查询方法,如果有 id 属性,优先使用 getElementById 方法来进行查询

如果没有 id 属性,则优先使用 getElementsByName 方法来进行查询

如果 id 属性和 name 属性都没有最后再按标签名查getElementsByTagName

以上三个方法,一定要在页面加载完成之后执行,才能查询到标签对象

10.3节点的常用属性和方法

节点就是标签对象

方法:

通过具体的元素节点调用

getElementsByTagName()

方法,获取当前节点的指定标签名孩子节点

appendChild( oChildNode )

方法,可以添加一个子节点,oChildNode 是要添加的孩子节点

属性:

childNodes

属性,获取当前节点的所有子节点

firstChild

属性,获取当前节点的第一个子节点

lastChild

属性,获取当前节点的最后一个子节点

parentNode

属性,获取当前节点的父节点

nextSibling

属性,获取当前节点的下一个节点

previousSibling

属性,获取当前节点的上一个节点

className

用于获取或设置标签的 class 属性值

innerHTML

属性,表示获取/设置起始标签和结束标签中的内容

innerText

属性,表示获取/设置起始标签和结束标签中的文本

四丶JQuery

1.jQuery 介绍

什么是 jQuery ?

jQuery,顾名思义,也就是 JavaScript 和查询(Query),它就是辅助 JavaScript 开发的 js 类库。

jQuery 核心思想!!!

它的核心思想是 write less,do more(写得更少,做得更多),所以它实现了很多浏览器的兼容问题。

jQuery 流行程度

jQuery 现在已经成为最流行的 JavaScript 库,在世界前 10000 个访问最多的网站中,有超过 55%在使用

jQuery。

jQuery 好处!!!

jQuery 是免费、开源的,jQuery 的语法设计可以使开发更加便捷,例如操作文档对象、选择 DOM 元素、

制作动画效果、事件处理、使用 Ajax 以及其他功能

2.jQuery的初体验

需求:使用 jQuery 给一个按钮绑定单击事件?

<script type="text/javascript" src="../script/jquery-1.7.2.js"></script>    <script type="text/javascript">        // window.onload = function () {        // 	var btnObj = document.getElementById("btnId");        // 	// alert(btnObj);//[object HTMLButtonElement]   ====>>>  dom对象        // 	btnObj.onclick = function () {        // 		alert("js 原生的单击事件");        // 	}        // }        $(function () { // 表示页面加载完成 之后,相当 window.onload = function () {}            var $btnObj = $("#btnId"); // 表示按id查询标签对象            $btnObj.click(function () { // 绑定单击事件                alert("jQuery 的单击事件");            });        });    </script></head><body><button id="btnId">SayHello</button></body>

常见问题?

1、使用 jQuery 一定要引入 jQuery 库吗?

答案:

是,必须

2、jQuery 中的$到底是什么?

答案:

它是一个函数

3、怎么为按钮添加点击响应函数的?

答案:

1、使用 jQuery 查询到标签对象

2、使用标签对象.click( function(){} );

3.jQuery核心函数

$ 是 jQuery 的核心函数,能完成 jQuery 的很多功能。 ( ) 就 是 调 用 ()就是调用 ()这个函数1、传入参数为 [ 函数 ] 时:

表示页面加载完成之后。相当于 window.onload = function(){}

2、传入参数为 [ HTML 字符串 ] 时:

会对我们创建这个 html 标签对象

3、传入参数为 [ 选择器字符串 ] 时:

$(“#id 属性值”);

id 选择器,根据 id 查询标签对象

$(“标签名”);

标签名选择器,根据指定的标签名查询标签对象

$(“.class 属性值”);

类型选择器,可以根据 class 属性查询标签对象

4、传入参数为 [ DOM 对象 ] 时:

会把这个 dom 对象转换为 jQuery 对象

4.jQuery 对象和 dom 对象区分

4.1什么是 jQuery 对象,什么是 dom 对象

Dom 对象

1.通过 getElementById()查询出来的标签对象是 Dom 对象

2.通过 getElementsByName()查询出来的标签对象是 Dom 对象

3.通过 getElementsByTagName()查询出来的标签对象是 Dom 对象

4.通过 createElement() 方法创建的对象,是 Dom 对象

DOM 对象 Alert 出来的效果是:[object HTML 标签名 Element]

jQuery 对象

5.通过 JQuery 提供的 API 创建的对象,是 JQuery 对象

6.通过 JQuery 包装的 Dom 对象,也是 JQuery 对象

7.通过 JQuery 提供的 API 查询到的对象,是 JQuery 对象

jQuery 对象 Alert 出来的效果是:[object Object]

4.2**问题:**jQuery 对象的本质是什么?

jQuery 对象是 dom 对象的数组 + jQuery 提供的一系列功能函数

4.3jQuery 对象和 Dom 对象使用区别

jQuery 对象不能使用 DOM 对象的属性和方法

DOM 对象也不能使用 jQuery 对象的属性和方法

4.4Dom 对象和 jQuery 对象互转

1、dom 对象转化为 jQuery 对象(重点)

1、先有 DOM 对象

2、$( DOM 对象 ) 就可以转换成为 jQuery 对象

2、jQuery 对象转为 dom 对象(重点)*

1、先有 jQuery 对象

2、jQuery 对象[下标]取出相应的 DOM 对象

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3LU0EQKj-1624636891042)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210401192729522.png)]

5.jQuery 选择器(*********重点)

5.1基本选择器

#ID 选择器:根据 id 查找标签对象

.class 选择器:根据 class 查找标签对象

element 选择器:根据标签名查找标签对象

* 选择器:表示任意的,所有的元素

selector1,selector2 组合选择器:合并选择器 1,选择器 2 的结果并返回

p.myClass

表示标签名必须是 p 标签,而且 class 类型还要是 myClass

5.2层级选择器(********重点)

ancestor descendant

后代选择器

:在给定的祖先元素下匹配所有的后代元素

parent > child

子元素选择器:在给定的父元素下匹配所有的子元素

prev + next

相邻元素选择器:匹配所有紧接在 prev 元素后的 next 元素

prev ~ sibings

之后的兄弟元素选择器:匹配 prev 元素之后的所有 siblings 元素

5.3过滤选择器

基本过滤器:

:first

获取第一个元素

:last

获取最后个元素

:not(selector)

去除所有与给定选择器匹配的元素

:even

匹配所有索引值为偶数的元素,从

0

开始计数

:odd

匹配所有索引值为奇数的元素,从

0

开始计数

:eq(index)

匹配一个给定索引值的元素

:gt(index)

匹配所有大于给定索引值的元素

:lt(index)

匹配所有小于给定索引值的元素

:header

匹配如 h1, h2, h3 之类的标题元素

:animated

匹配所有正在执行动画效果的元素


内容过滤器

:contains(text)匹配包含给定文本的元素
:empty匹配所有不包含子元素或者文本的空元素
:parent匹配含有子元素或者文本的元素
:has(selector)匹配含有选择器所匹配的元素的元素

属性过滤器:

[attribute]匹配包含给定属性的元素。
[attribute=value]匹配给定的属性是某个特定值的元素
[attribute!=value]匹配所有不含有指定的属性,或者属性不等于特定值的元素
[attribute^=value]匹配给定的属性是以某些值开始的元素
[attribute$=value]匹配给定的属性是以某些值结尾的元素
[attribute=value]*匹配给定的属性是以包含某些值的元素
[attrSel1][attrSel2][attrSelN]复合属性选择器,需要同时满足多个条件时使用

表单过滤器

:input

匹配所有

input, textarea, select 和 button 元素

:text

匹配所有

文本输入框

:password

匹配所有的密码输入框

:radio

匹配所有的单选框

:checkbox

匹配所有的复选框

:submit

匹配所有提交按钮

:image

匹配所有 img 标签

:reset

匹配所有重置按钮

:button

匹配所有 input type=button 按钮

:file

匹配所有 input type=file 文件上传

:hidden

匹配所有不可见元素 display:none 或 input type=hidden

表单对象属性过滤器:

:enabled

匹配所有可用元素

:disabled

匹配所有不可用元素

:checked

匹配所有选中的单选,复选,和下拉列表中选中的 option 标签对象

:selected

匹配所有选中的 option

6.jQuery 元素筛选

eq()

获取给定索引的元素

功能跟

:eq()

一样

first()

获取第一个元素

功能跟

:first

一样

last()

获取最后一个元素

功能跟

:last

一样

filter(exp)

留下匹配的元素

is(exp)

判断是否匹配给定的选择器,只要有一个匹配就返回,true

has(exp)

返回包含有匹配选择器的元素的元素

功能跟

:has

一样

not(exp)

删除匹配选择器的元素

功能跟

:not

一样

children(exp)

返回匹配给定选择器的子元素

功能跟

parent>child 一样

find(exp)

返回匹配给定选择器的后代元素

功能跟

ancestor descendant 一样next()

返回当前元素的下一个兄弟元素

功能跟

prev + next 功能一样

nextAll()

返回当前元素后面所有的兄弟元素

功能跟

prev ~ siblings 功能一样

nextUntil()

返回当前元素到指定匹配的元素为止的后面元素

parent()

返回父元素

prev(exp)

返回当前元素的上一个兄弟元素

prevAll()

返回当前元素前面所有的兄弟元素

prevUnit(exp)

返回当前元素到指定匹配的元素为止的前面元素

siblings(exp)

返回所有兄弟元素

add()

把 add 匹配的选择器的元素添加到当前 jquery 对象中

7.jQuery 的属性操作

jQuery

属性操作

html()

它可以设置和获取起始标签和结束标签中的内容。

跟 dom 属性 innerHTML 一样。

text()

它可以设置和获取起始标签和结束标签中的文本。

跟 dom 属性 innerText 一样。

val()

它可以设置和获取表单项的 value 属性值。

跟 dom 属性 value 一样

attr()

可以设置和获取属性的值,不推荐操作 checked、readOnly、selected、disabled 等等

attr 方法还可以操作非标准的属性。比如自定义属性:abc,bbj

prop()

可以设置和获取属性的值,只推荐操作 checked、readOnly、selected、disabled 等等

8.DOM的增删改

内部插入:

appendTo()

a.appendTo(b)

把 a 插入到 b 子元素末尾,成为最后一个子元素prependTo()

a.prependTo(b)

把 a 插到 b 所有子元素前面,成为第一个子元素

外部插入:

insertAfter()

a.insertAfter(b)

得到 ba

insertBefore()

a.insertBefore(b)

得到 ab

替换**😗*

replaceWith()

a.replaceWith(b)

用 b 替换掉 a

replaceAll()

a.replaceAll(b)

用 a 替换掉所有 b

删除:

remove()

a.remove();

删除 a 标签

empty()

a.empty();

清空 a 标签里的内容

9.CSS样式操作

addClass() 添加样式

removeClass()

删除样式

toggleClass()

有就删除,没有就添加样式。

offset()

获取和设置元素的坐标。

10.JQuery动画

基本动画

show()

将隐藏的元素显示

hide()

将可见的元素隐藏。

toggle()

可见就隐藏,不可见就显示。

以上动画方法都可以添加参数。

1、第一个参数是动画 执行的时长,以毫秒为单位

2、第二个参数是动画的回调函数 (动画完成后自动调用的函数)

淡入淡出动画

fadeIn()

淡入(慢慢可见)

fadeOut()

淡出(慢慢消失)

fadeTo()

在指定时长内慢慢的将透明度修改到指定的值。0 透明,1 完成可见,0.5 半透明

fadeToggle()

淡入/淡出 切换

11.JQuery事件操作

$( function(){} );

window.onload = function(){}

的区别?

他们分别是在什么时候触发?

1、jQuery 的页面加载完成之后是浏览器的内核解析完页面的标签创建好 DOM 对象之后就会马上执行。

2、原生 js 的页面加载完成之后,除了要等浏览器内核解析完标签创建好 DOM 对象,还要等标签显示时需要的内容加载完成.

他们触发的顺序?

1、jQuery 页面加载完成之后先执行

2、原生 js 的页面加载完成之后

他们执行的次数?

1、原生 js 的页面加载完成之后,只会执行最后一次的赋值函数。

2、jQuery 的页面加载完成之后是全部把注册的 function 函数,依次顺序全部执行。

jQuery 中其他的事件处理方法:

click()它可以绑定单击事件,以及触发单击事件
mouseover()鼠标移入事件
mouseout()鼠标移出事件
bind()可以给元素一次性绑定一个或多个事件。
one()使用上跟 bind 一样。但是 one 方法绑定的事件只会响应一次。
unbind()跟 bind 方法相反的操作,解除事件的绑定
live()也是用来绑定事件。它可以用来绑定选择器匹配的所有元素的事件。哪怕这个元素是后面动态创建出的也有效
<script type="text/javascript">        $(function () {            //*1.通常绑定事件的方式            //给元素绑定事件              //jquery对象.事件方法(回调函数(){ 触发事件执行的代码 }).事件方法(回调函数(){ 触发事件执行的代码 }).事件方法(回调函数(){ 触发事件执行的代码 })            //绑定事件可以链式操作            $(".head").click(function () {                $(".content").toggle();            }).mouseover(function () {                $(".content").toggle();            });            //*2.jQuery提供的绑定方式:bind(type,[data],fn)函数把元素和事件绑定起来            //type表示要绑定的事件   [data]表示传入的数据   fn表示事件的处理方法            //bind(事件字符串,回调函数),后来添加的元素不会绑定事件            //使用bind()绑定多个事件   type可以接受多个事件类型,使用空格分割多个事件            /* $(".head").bind("click mouseover",function(){                $(".content").toggle();            }); */            //3.one()只绑定一次,绑定的事件只会发生一次one(type,[data],fn)函数把元素和事件绑定起来            //type表示要绑定的事件   [data]表示传入的数据   fn表示事件的处理方法            /* 	$(".head").one("click mouseover",function(){                    $(".content").toggle();                }); */            //4.live方法会为现在及以后添加的元素都绑定上相应的事件            /**    $(".head").live("click",function(){					$(".content").toggle();				});             $("#panel").before("<h5 class='head'>什么是jQuery?</h5>");             */        });    </script>

事件的冒泡

什么是事件的冒泡?

事件的冒泡是指,父子元素同时监听同一个事件。当触发子元素的事件的时候,同一个事件也被传递到了父元素的事件里去响应。

那么如何阻止事件冒泡呢?

在子元素事件函数体内,return false; 可以阻止事件的冒泡传递。

javaScript 事件对象

事件对象,是封装有触发的事件信息的一个 javascript 对象。

我们重点关心的是怎么拿到这个 javascript 的事件对象。以及使用。

如何获取呢 javascript 事件对象呢?

在给元素绑定事件的时候,在事件的 function( event ) 参数列表中添加一个参数,这个参数名,我们习惯取名为 event.这个 event 就是 javascript 传递参事件处理函数的事件对象。

五丶XML

1.XML简介

什么是 xml?

xml 是可扩展的标记性语言。

xml 的作用?

xml 的主要作用有:

1、用来保存数据,而且这些数据具有自我描述性

2、它还可以做为项目或者模块的配置文件

3、还可以做为网络传输数据的格式(现在 JSON 为主)。

2.XML语法

  1. 文档声明。

  2. 元素(标签)

  3. xml 属性

  4. xml 注释

  5. 文本区域(CDATA 区)

2.1文档声明

<?xml version=*"1.0"* encoding=*"UTF-8"*?> xml 声明。

而且这个<?xml

要连在一起写,否则会有报错

属性

version 是版本号

encoding 是 xml 的文件编码

standalone=“yes/no” 表示这个 xml 文件是否是独立的 xml 文件

</books>    <?xml version="1.0" encoding="UTF-8"?> <!-- xml 声明 version 是版本的意思 encoding 是编码 -->    <books> <!-- 这是 xml 注释 -->        <book id="SN123123413241"> <!-- book 标签描述一本图书 id 属性描述 的是图书 的编号 -->            <name>java 编程思想</name> <!-- name 标签描述 的是图书 的信息 -->            <author>华仔</author> <!-- author 单词是作者的意思 ,描述图书作者 -->            <price>9.9</price> <!-- price 单词是价格,描述的是图书 的价格 -->        </book>        <book id="SN12341235123"> <!-- book 标签描述一本图书 id 属性描述 的是图书 的编号 -->            <name>葵花宝典</name> <!-- name 标签描述 的是图书 的信息 -->            <author>班长</author> <!-- author 单词是作者的意思 ,描述图书作者 -->            <price>5.5</price><!-- price 单词是价格,描述的是图书 的价格 -->        </book>    </books>

2.2xml注释

html 和 XML 注释 一样 :


2.3元素标签

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4BGb36fH-1624636891043)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404165015568.png)]

2.4xml属性


xml 的标签属性和 html 的标签属性是非常类似的,属性可以提供元素的额外信息


在标签上可以书写属性:

一个标签上可以书写多个属性。每个属性的值必须使用 引号 引起来

的规则和标签的书写规则一致。


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Ej7slcvE-1624636891044)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404165700294.png)]


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-1XkNQqPS-1624636891045)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404165722340.png)]

2.5xml语法规则

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EBNjD0tn-1624636891046)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404165840414.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-XC8cTR8r-1624636891046)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404165855680.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6t7IUTJV-1624636891049)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404165910666.png)]

XML 文档必须有根元素

XML 文档必须有一个元素是所有其他元素的父元素。该元素称为根元素

<root>  <child>    <subchild>.....</subchild>  </child></root>

XML 的属性值须加引号

与 HTML 类似,XML 也可拥有属性(名称/值的对)。

在 XML 中,XML 的属性值须加引号。请研究下面的两个 XML 文档。第一个是错误的,第二个是正确的:

<note date=08/08/2008><to>George</to><from>John</from></note> <note date="08/08/2008"><to>George</to><from>John</from></note> 

实体引用

在 XML 中,一些字符拥有特殊的意义。

如果你把字符 “<” 放在 XML 元素中,会发生错误,这是因为解析器会把它当作新元素的开始。

这样会产生 XML 错误:

<message>if salary < 1000 then</message>

为了避免这个错误,请用一个实体引用来代替 “<” 字符:

<message>if salary &lt; 1000 then</message> 

在 XML 中,有 5 个预定义的实体引用:

<<小于
>>大于
&&和号
'省略号
""引号

注释:在 XML 中,只有字符 “<” 和 “&” 确实是非法的。大于号是合法的,但是用实体引用来代替它是一个好习惯。


在 XML 中,空格会被保留

HTML 会把多个连续的空格字符裁减为一个:

HTML:  Hello           my name is Tove 

输出: Hello my name is Tove.

在 XML 中,文档中的空格不会被删节。

2.6XML CDATA


CDATA 语法可以告诉 xml 解析器,我 CDATA 里的文本内容,只是纯文本,不需要 xml 语法解析


CDATA 格式:

<![CDATA[** 这里可以把你输入的字符原样显示,不会解析 xml **]]>

3.XML解析技术介绍


xml 可扩展的标记语言。

不管是 html 文件还是 xml 文件它们都是标记型文档,都可以使用 w3c 组织制定的 dom 技术来解析


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Gz8szuMX-1624636891050)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404170549108.png)]

document 对象表示的是整个文档(可以是 html 文档,也可以是 xml 文档)

早期 JDK 为我们提供了两种 xml 解析技术 DOM Sax 简介(已经过时,但我们需要知道这两种技术

dom 解析技术是 W3C 组织制定的,而所有的编程语言都对这个解析技术使用了自己语言的特点进行实现。

Java 对 dom 技术解析标记也做了实现。

sun 公司在 JDK5 版本对 dom 解析技术进行升级:SAX( Simple API for XML )

SAX 解析,它跟 W3C 制定的解析不太一样。它是以类似事件机制通过回调告诉用户当前正在解析的内容。

它是一行一行的读取 xml 文件进行解析的。不会创建大量的 dom 对象。

所以它在解析 xml 的时候,在内存的使用上。和性能上。都优于 Dom 解析。


第三方的解析:

jdom 在 dom 基础上进行了封装 、

dom4j 又对 jdom 进行了封装。

pull 主要用在 Android 手机开发,是在跟 sax 非常类似都是事件机制解析 xml 文件。

这个 Dom4j 它是第三方的解析技术。我们需要使用第三方给我们提供好的类库才可以解析 xml 文件。

4.dom4j解析技术(重点)

由于 dom4j 它不是 sun 公司的技术,而属于第三方公司的技术,我们需要使用 dom4j 就需要到 dom4j 官网下载 dom4j的 jar 包。

4.1dom4j编程步骤

第一步: 先加载 xml 文件创建 Document 对象

第二步:通过 Document 对象拿到根元素对象

第三步:通过根元素.elelemts(标签名); 可以返回一个集合,这个集合里放着。所有你指定的标签名的元素对象

第四步:找到你想要修改、删除的子元素,进行相应在的操作

第五步,保存到硬盘上

4.2获取 document 对象

创建一个 lib 目录,并添加 dom4j 的 jar 包。并添加到类路径。

解析获取 Document 对象的代码

第一步,先创建 SaxReader 对象。这个对象,用于读取 xml 文件,并创建 Document

/** dom4j 获取 Documet 对象 */ @Test public void getDocument() throws DocumentException {     // 要创建一个 Document 对象,需要我们先创建一个 SAXReader 对象     SAXReader reader = new SAXReader();     // 这个对象用于读取 xml 文件,然后返回一个 Document。     Document document = reader.read("src/books.xml");     // 打印到控制台,看看是否创建成功     System.out.println(document); }

4.3遍历 标签 获取所有标签中的内容(*********重点)

需要分四步操作:

第一步,通过创建 SAXReader 对象。来读取 xml 文件,获取 Document 对象

第二步,通过 Document 对象。拿到 XML 的根元素对象

第三步,通过根元素对象。获取所有的 book 标签对象

第四小,遍历每个 book 标签对象。然后获取到 book 标签对象内的每一个元素,再通过 getText() 方法拿到起始标签和结

束标签之间的文本内容


/** 读取 xml 文件中的内容 */ @Test public void readXML() throws DocumentException {     // 需要分四步操作:     // 第一步,通过创建 SAXReader 对象。来读取 xml 文件,获取 Document 对象     // 第二步,通过 Document 对象。拿到 XML 的根元素对象     // 第三步,通过根元素对象。获取所有的 book 标签对象    // 第四步,遍历每个 book 标签对象。然后获取到 book 标签对象内的每一个元素,再通过 getText() 方法拿到起始标签和结束标签之间的文本内容     // 第一步,通过创建 SAXReader 对象。来读取 xml 文件,获取 Document 对象     SAXReader reader = new SAXReader();    Document document = reader.read("src/books.xml");    // 第二步,通过 Document 对象。拿到 XML 的根元素对象    Element root = document.getRootElement();     // 打印测试    // Element.asXML() 它将当前元素转换成为 String 对象     // System.out.println( root.asXML() );     // 第三步,通过根元素对象。获取所有的 book 标签对象    // Element.elements(标签名)它可以拿到当前元素下的指定的子元素的集合    List<Element> books = root.elements("book");     // 第四小,遍历每个 book 标签对象。然后获取到 book 标签对象内的每一个元素,     for (Element book : books) {         // 测试        // System.out.println(book.asXML());        // 拿到 book 下面的 name 元素对象         Element nameElement = book.element("name");         // 拿到 book 下面的 price 元素对象        Element priceElement = book.element("price");        // 拿到 book 下面的 author 元素对象        Element authorElement = book.element("author");         // 再通过 getText() 方法拿到起始标签和结束标签之间的文本内容        System.out.println("书名" + nameElement.getText() + " , 价格:" + priceElement.getText() + ", 作者:"+authorElement.getText());    }}

六丶Tomcat

1.JavaWeb的概念

a)什么是 JavaWeb

JavaWeb 是指,所有通过 Java 语言编写可以通过浏览器访问的程序的总称,叫 JavaWeb。

JavaWeb 是基于请求和响应来开发的。


b)什么是请求

请求是指客户端给服务器发送数据,叫请求 Request。


c)什么是响应

响应是指服务器给客户端回传数据,叫响应 Response。


d)请求和响应的关系

请求和响应是成对出现的,有请求就有响应。


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-bPU4jXWl-1624636891050)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404192128406.png)]

2.Web 资源的分类

web 资源按实现的技术和呈现的效果的不同,又分为静态资源和动态资源两种。

静态资源:html、css、js、txt、mp4 视频 , jpg 图片

动态资源:jsp 页面、Servlet 程序

3.常用的 Web 服务器

Tomcat:由 Apache 组织提供的一种 Web 服务器,提供对 jsp 和 Servlet 的支持。它是一种轻量级的 javaWeb 容器(服务器),也是当前应用最广的 JavaWeb 服务器(免费)。

Jboss:是一个遵从 JavaEE 规范的、开放源代码的、纯 Java 的 EJB 服务器,它支持所有的 JavaEE 规范(免费)。

GlassFish: 由 Oracle 公司开发的一款 JavaWeb 服务器,是一款强健的商业服务器,达到产品级质量(应用很少)。

Resin:是 CAUCHO 公司的产品,是一个非常流行的服务器,对 servlet 和 JSP 提供了良好的支持,性能也比较优良,resin 自身采用 JAVA 语言开发(收费,应用比较多)。

WebLogic:是 Oracle 公司的产品,是目前应用最广泛的 Web 服务器,支持 JavaEE 规范,而且不断的完善以适应新的开发要求,适合大型项目(收费,用的不多,适合大公司)。

4.Tomcat 的使用

目录介绍

bin 专门用来存放 Tomcat 服务器的可执行程序

conf 专门用来存放 Tocmat 服务器的配置文件

lib 专门用来存放 Tomcat 服务器的 jar 包

logs 专门用来存放 Tomcat 服务器运行时输出的日记信息

temp 专门用来存放 Tomcdat 运行时产生的临时数据

webapps 专门用来存放部署的 Web 工程。

work 是 Tomcat 工作时的目录,用来存放 Tomcat 运行时 jsp 翻译为 Servlet 的源码,和 Session 钝化的目录。


如何启动 Tomcat 服务器

找到 Tomcat 目录下的 bin 目录下的 startup.bat 文件,双击,就可以启动 Tomcat 服务器。


如何测试 Tomcat 服务器启动成功???

打开浏览器,在浏览器地址栏中输入以下地址测试:

1、http://localhost:8080

2、http://127.0.0.1:8080

3、http://真实 ip:8080

当出现如下界面,说明 Tomcat 服务器启动成功!!!


如何部暑 web 工程到 Tomcat

第一种部署方法:只需要把 web 工程的目录拷贝到 Tomcat webapps 目录下

即可

第二种部署方法:

找到 Tomcat 下的 conf 目录\Catalina\localhost\ 下,创建如下的配置文件:

abc.xml 配置文件内容如下:

<!-- Context 表示一个工程上下文 path 表示工程的访问路径:/abc docBase 表示你的工程目录在哪里 --> <Context path="/abc" docBase="E:\book" />

访问这个工程的路径如下:http://ip:port/abc/

就表示访问 E:\book 目录

:保存格式为utf-8


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-C0gAq3W3-1624636891052)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404231319809.png)]


ROOT 的工程的访问,以及 默认 index.html 页面的访问

当我们在浏览器地址栏中输入访问地址如下:

http://ip:port/ ====>>>> 没有工程名的时候,默认访问的是 ROOT 工程。

当我们在浏览器地址栏中输入的访问地址如下:

http://ip:port/工程名/ ====>>>> 没有资源名,默认访问 index.html 页面


5.IDEA 整合 Tomcat 服务器

操作的菜单如下:File | Settings | Build, Execution, Deployment | Application Servers


6.IDEA 中动态 web 工程的操作

img

img

在这里插入图片描述

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-dU2o9GiO-1624636891053)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210404234132451.png)]

7.如何给动态 web 工程添加额外 jar

1、可以打开项目结构菜单操作界面,添加一个自己的类库:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Cm0Q0rCm-1624636891054)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405130611244.png)]

2、添加你你类库需要的 jar 包文件。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2gpLaAXV-1624636891054)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405130633437.png)]

3、选择你添加的类库,给哪个模块使用:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2JyLHlvf-1624636891055)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405130659374.png)]

4、选择 Artifacts 选项,将类库,添加到打包部署中:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-C4LiHJo1-1624636891055)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405130723161.png)]

8.如何在 IDEA 中部署工程到 Tomcat 上运行

1、建议修改 web 工程对应的 Tomcat 运行实例名称:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pozbfGwa-1624636891056)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405132751743.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-5bQaadAO-1624636891056)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405132823853.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-giCEXhcy-1624636891057)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405132853485.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Q4pfYpq8-1624636891057)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405132924740.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yGbgi84F-1624636891059)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405133005468.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-X8X9wzJF-1624636891059)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405133228215.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ORkJ0Bdf-1624636891060)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210406200538593.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-619YKr65-1624636891060)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210407185655107.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FkjVL0ag-1624636891061)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210406200608970.png)]

七丶Servlet

1.Servlet

什么是Servlet

1、Servlet 是 JavaEE 规范之一。规范就是接口

2、Servlet 就 JavaWeb 三大组件之一。三大组件分别是:Servlet 程序、Filter 过滤器、Listener 监听器。

3、Servlet 是运行在服务器上的一个 java 小程序,它可以接收客户端发送过来的请求,并响应数据给客户端。


手动实现 Servlet 程序

1、编写一个类去实现 Servlet 接口

2、实现 service 方法,处理请求,并响应数据

3、到 web.xml 中去配置 servlet 程序的访问地址


<?xml version="1.0" encoding="UTF-8"?><web-app xmlns="http://xmlns.jcp.org/xml/ns/javaee"         xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"         xsi:schemaLocation="http://xmlns.jcp.org/xml/ns/javaee http://xmlns.jcp.org/xml/ns/javaee/web-app_4_0.xsd"         version="4.0">    <!--servlet 标签配置程序-->    <servlet>        <!-- 起别名,一般是类名-->        <servlet-name>HelloServlet</servlet-name>        <!--是servlet程序的全类名-->        <servlet-class>com.atguigu.servlet.HelloServlet</servlet-class>    </servlet>    <!--配置访问地址-->    <servlet-mapping>        <!--告诉服务器当前配置的地址给那个servle程序使用-->        <servlet-name>HelloServlet</servlet-name>        <!--配置访问地址        / 表示在服务器解析的时候,表示地址为http://ip:port/工程路径        /hello http://ip:port/工程路径/hello        -->        <url-pattern>/hello</url-pattern>    </servlet-mapping></web-app>

常见错误 1:url-pattern 中配置的路径没有以斜杠打头。

常见错误 2:servlet-name 配置的值不存在.

常见错误 3:servlet-class 标签的全类名配置错误.


url 地址到 Servlet 程序的访问

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-HinMbO73-1624636891062)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405163845125.png)]


Servlet 的生命周期

1、执行 Servlet 构造器方法

2、执行 init 初始化方法

第一、二步,是在第一次访问,的时候创建 Servlet 程序会调用。

3、执行 service 方法

第三步,每次访问都会调用。

4、执行 destroy 销毁方法

第四步,在 web 工程停止的时候调用。


GET POST 请求的分发处理

/**     * service方法专门处理请求和响应     *     * @param servletRequest     * @param servletResponse     * @throws ServletException     * @throws IOException     */    @Override    public void service(ServletRequest servletRequest, ServletResponse servletResponse) throws ServletException, IOException {        System.out.println("被访问了");        //类型转换(因为有getMethod方法)        //把父类强转为子类        HttpServletRequest httpServletRequest = (HttpServletRequest) servletRequest;        //获取请求的方式        String method = httpServletRequest.getMethod();        if ("GET".equals(method)) {            doGet();        } else {            doPost();        }    }    //get请求操作    public void doGet() {        System.out.println("get请求");        System.out.println();    }    //post请求操作    public void doPost() {        System.out.println("post请求");    }

通过继承 HttpServlet 实现 Servlet 程序

一般在实际项目开发中,都是使用继承 HttpServlet 类的方式去实现 Servlet 程序。

1、编写一个类去继承 HttpServlet 类

2、根据业务需要重写 doGet 或 doPost 方法

3、到 web.xml 中的配置 Servlet 程序的访问地址

使用 IDEA 创建 Servlet 程序

菜单:new ->Servlet 程序

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-RUkoSo9C-1624636891062)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405203314248.png)]

配置 Servlet 的信息:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-DmVsGX7v-1624636891063)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405203400598.png)]


Servlet 类的继承体系

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Uac9WG3t-1624636891064)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210405204628633.png)]


2.ServletConfig

ServletConfig 类从类名上来看,就知道是 Servlet 程序的配置信息类。

Servlet 程序和 ServletConfig 对象都是由 Tomcat 负责创建,我们负责使用。

Servlet 程序默认是第一次访问的时候创建,ServletConfig 是每个 Servlet 程序创建时,就创建一个对应的 ServletConfig 对象。


ServletConfig 类的三大作用

、可以获取 Servlet 程序的别名 servlet-name 的值

2、获取初始化参数 init-param

3、获取 ServletContext 对象


<!--配置在servlet文件里面--><init-param>        <!--参数名-->        <param-name>username</param-name>        <!--参数值-->        <param-value>root</param-value>    </init-param>        <init-param>            <param-name>url</param-name>            <param-value>jdbc:mysql://localhost:3306</param-value>        </init-param>
@Override    public void init(ServletConfig servletConfig) throws ServletException {        System.out.println("init初始化方法");        // 1、可以获取 Servlet 程序的别名 servlet-name 的值        System.out.println(servletConfig.getServletName());       // 2、获取初始化参数 init-param             //调用父类的方法,防止空指针异常 super.init(config)                     System.out.println(servletConfig.getInitParameter("username"));       // 3、获取 ServletContext 对象 System.out.println(servletConfig.getServletContext());        System.out.println(servletConfig.getInitParameter("url"));            }

3.ServletContext

什么是 ServletContext?

1、ServletContext 是一个接口,它表示 Servlet 上下文对象

2、一个 web 工程,只有一个 ServletContext 对象实例。

3、ServletContext 对象是一个域对象。

4、ServletContext 是在 web 工程部署启动的时候创建。在 web 工程停止的时候销毁


什么是域对象?

域对象,是可以像 Map 一样存取数据的对象,叫域对象。

这里的域指的是存取数据的操作范围,整个 web 工程。


存数据取数据删除数据
Mapput()get()remove()
域对象setAttribute()getAttribute()removeAttribute()

ServletContext 类的四个作用

1、获取 web.xml 中配置的上下文参数 context-param

2、获取当前的工程路径,格式: /工程路径

3、获取工程部署后在服务器硬盘上的绝对路径

4、像 Map 一样存取数据


4**.HTTP** 协议

什么是 HTTP 协议

什么是协议?

协议是指双方,或多方,相互约定好,大家都需要遵守的规则,叫协议。

所谓 HTTP 协议,就是指,客户端和服务器之间通信时,发送的数据,需要遵守的规则,叫 HTTP 协议。

HTTP 协议中的数据又叫报文。


请求的 HTTP 协议格式

客户端给服务器发送数据叫请求。

服务器给客户端回传数据叫响应。

请求又分为 GET 请求,和 POST 请求两种


GET 请求

1、请求行

(1) 请求的方式 GET

(2) 请求的资源路径[+?+请求参数]

(3) 请求的协议的版本号 HTTP/1.1

2、请求头 key : value 组成 不同的键值对,表示不同的含义。


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xzqFn0Gf-1624636891065)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210406164453277.png)]


POST 请求

1、请求行

(1) 请求的方式 POST

(2) 请求的资源路径[+?+请求参数]

(3) 请求的协议的版本号 HTTP/1.1

2、请求头

  1.             key : value                 不同的请求头,有不同的含义 
    

空行

3、请求体 ===>>> 就是发送给服务器的数据

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GWrrjQxb-1624636891065)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210406185932948.png)]


常用请求头的说明

Accept: 表示客户端可以接收的数据类型

Accpet-Languege: 表示客户端可以接收的语言类型

User-Agent: 表示客户端浏览器的信息

Host: 表示请求时的服务器 ip 和端口号


哪些是 GET 请求,哪些是 POST 请求

GET 请求有哪些:

1、form 标签 method=get

2、a 标签

3、link 标签引入 css

4、Script 标签引入 js 文件

5、img 标签引入图片

6、iframe 引入 html 页面

7、在浏览器地址栏中输入地址后敲回车

POST 请求有哪些:

8、form 标签 method=post


响应的 HTTP 协议格式

1、响应行

(1) 响应的协议和版本号

(2) 响应状态码

(3) 响应状态描述符

2、响应头

(1) key : value 不同的响应头,有其不同含义

空行

3、响应体 ---->>> 就是回传给客户端的数据


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7i51yOJC-1624636891066)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210406191609137.png)]

常用的响应码说明

200表示请求成功
302表示请求重定向
404表示请求服务器已经收到了,但是你要的数据不存在(请求地址错误)
500表示服务器已经收到请求,但是服务器内部错误(代码错误)

MIME 类型说明

MIME 是 HTTP 协议中数据类型。

MIME 的英文全称是"Multipurpose Internet Mail Extensions" 多功能 Internet 邮件扩充服务。MIME 类型的格式是“大类型/小类型”,并与某一种文件的扩展名相对应。


常见的 MIME 类型:

文件MIME类型
超文本标记语言文本.html, .htm text/html
普通文本.txt text/pain
RTF文本.rtf application/rtf
GIF图形.gif image/gif
JPEG图形.jepg, .jpg image/jpeg
au声音文件.au audio/basic
MIDI音乐文件mid,.midi audio/midi,audio/x-midi
RealAudio音乐文件.ra, .ram audio/x-pn-realaudio
MPEG文件.mpg,.mpeg video/mpeg
AVI文件.avi video/x-msvideo
GZIP文件.gz application/x-gzip
TAR文件.tar application/x-tar

5.HttpServletRequest

HttpServletRequest 类有什么作用。

每次只要有请求进入 Tomcat 服务器,Tomcat 服务器就会把请求过来的 HTTP 协议信息解析好封装到 Request 对象中。然后传递到 service 方法(doGet 和 doPost)中给我们使用。我们可以通过 HttpServletRequest 对象,获取到所有请求的信息。


HttpServletRequest 类的常用方法

getRequestURI()获取请求的资源路径
getRequestURL()获取请求的统一资源定位符(绝对路径)
getRemoteHost()获取客户端的 ip 地址
getHeader()获取请求头
getParameter()获取请求的参数
getParameterValues()获取请求的参数(多个值的时候使用)
getMethod()获取请求的方式 GET 或 POST
setAttribute(key, value);设置域数据
getAttribute(key);获取域数据
getRequestDispatcher()获取请求转发对象

常用 API 示例代码:

public class RequestAPIServlet extends HttpServlet {//            | getRequestURI()           | 获取请求的资源路径|//            | ------------------------- | ------------------------------------ |//            | getRequestURL()           | 获取请求的统一资源定位符(绝对路径) |//            | getRemoteHost()           | 获取客户端的 ip 地址                 |//            | getHeader()               | 获取请求头                           |//            | getParameter()            | 获取请求的参数                       |//            | getParameterValues()      | 获取请求的参数(多个值的时候使用)   |//            | getMethod()               | 获取请求的方式 GET 或 POST           |//            | setAttribute(key, value); | 设置域数据                           |//            | getAttribute(key);        | 获取域数据                           |//            | getRequestDispatcher()    | 获取请求转发对象                     |/**/    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //1.        System.out.println("URI" + req.getRequestURI());        //2.        System.out.println("URL" + req.getRequestURL());        //3.        System.out.println("ip" + req.getRemoteHost());    }}

如何获取请求参数

<!DOCTYPE html><html lang="en"><head>    <meta charset="UTF-8">    <title>Title</title></head><body><!--注意大小写--><form action="http://localhost:8080/Servlet/parameterServlet" method="post">    用户名:<input type="text" name="username"><br/>    密码:<input type="password" name="password"><br/>    兴趣爱好:<input type="checkbox" name="hobby" value="cpp">C++    <input type="checkbox" name="hobby" value="java">Java    <input type="checkbox" name="hobby" value="py">Python    <input type="checkbox" name="hobby" value="js">JavaScript<br/>    <input type="submit"></form></body></html>
public class ParameterServlet extends HttpServlet {    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        System.out.println("---------doGet------------");        String username = req.getParameter("username");        String password = req.getParameter("password");        String[] hobby = req.getParameterValues("hobby");        System.out.println("用户名" + username);        System.out.println("密码" + password);        System.out.println("爱好" + hobby);    }    @Override    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //避免乱码        req.setCharacterEncoding("UTF-8");        System.out.println("---------doPost------------");        String username = req.getParameter("username");        String password = req.getParameter("password");        //同时传多个参数        String[] hobby = req.getParameterValues("hobby");        System.out.println("用户名" + username);        System.out.println("密码" + password);        System.out.println("爱好" + hobby);    }}

doGet 请求的中文乱码解决:

// 获取请求参数

String username = req.getParameter(“username”);

//1

先以 iso8859-1 进行编码

//2

再以 utf-8 进行解码

username = new String(username.getBytes(“iso-8859-1”), “UTF-8”);

d)POST 请求的中文乱码解决

@Override

protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException,

IOException {

// 设置请求体的字符集为 UTF-8*,从而解决* post 请求的中文乱码问题

req.setCharacterEncoding(“UTF-8”);

System.out.println("-------------doPost------------");

// 获取请求参数

String

username

=

req.getParameter(“username”);

String

password

=

req.getParameter(“password”);

String[] hobby = req.getParameterValues(“hobby”);

System.out.println("用户名:"

+ username);

System.out.println(密码: +

password);

System.out.println(兴趣爱好: + Arrays.asList(hobby));

}


请求的转发

什么是请求的转发?

请求转发是指,服务器收到请求后,从一次资源跳转到另一个资源的操作叫请求转发。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-hlD0aMTM-1624636891067)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210406210202743.png)]

public class Servlet1 extends HttpServlet {    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //获取请求参数        String username = req.getParameter("username");        System.out.println("在servlet 1中查看"+username);        //盖章传到2        req.setAttribute("key","柜台1的章");        //问路        /*        请求转发必须以/开头,映射到IDEA的web目录        注意大小写         */        RequestDispatcher requestDispatcher = req.getRequestDispatcher("/servlet2");        //走到柜台2        requestDispatcher.forward(req,resp);    }}

public class Servlet2 extends HttpServlet {    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //获取请求参数        String username = req.getParameter("username");        System.out.println("在servlet 2中查看" + username);        //查看柜台1是否有盖章        Object key = req.getAttribute("key");        System.out.println("检查柜台1"+key);        System.out.println("处理自己的事");    }}

base 标签的作用

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-cE0J4rOM-1624636891068)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210407164325653.png)]

<head>    <meta charset="UTF-8">    <title>Title</title>    <!--base是相对路径的参考值    -->    <base href="http://localhost:8080/Servlet/a/b/c.html"></head><body>这是a下的b下的c.html<br/><a href="../../index.html">跳回首页</a></body></html>

Web 中的相对路径和绝对路径

在 javaWeb 中,路径分为相对路径和绝对路径两种:

相对路径是:

.

表示当前目录

表示上一级目录

资源名

表示当前目录/资源名

绝对路径:

http://ip:port/工程路径/资源路径

在实际开发中,路径都使用绝对路径,而不简单的使用相对路径。

1、绝对路径

2、base+相对


web / 斜杠的不同意义

在 web 中 / 斜杠 是一种绝对路径。

/ 斜杠 如果被浏览器解析,得到的地址是:http://ip:port/

斜杠


/ 斜杠 如果被服务器解析,得到的地址是:http://ip:port/工程路径

1、<url-pattern>/servlet1</url-pattern>

2、servletContext.getRealPath(“/”);

3、request.getRequestDispatcher(“/”);

特殊情况: response.sendRediect(“/”); 把斜杠发送给浏览器解析。得到 http://ip:port/

6.HttpServletResponse

6.1HttpServletResponse 类的作用

HttpServletResponse 类和 HttpServletRequest 类一样。每次请求进来,Tomcat 服务器都会创建一个 Response 对象传递给 Servlet 程序去使用。HttpServletRequest 表示请求过来的信息,HttpServletResponse 表示所有响应的信息,我们如果需要设置返回给客户端的信息,都可以通过 HttpServletResponse 对象来进行设置

6.2两个输出流的说明。

字节流 getOutputStream(); 常用于下载(传递二进制数据)

字符流 getWriter(); 常用于回传字符串(常用)

两个流同时只能使用一个。

使用了字节流,就不能再使用字符流,反之亦然,否则就会报错。


6.3如何往客户端回传数据

public class ResponseIoServlet extends HttpServlet {    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //往客户端回传字符串数据        PrintWriter writer = resp.getWriter();        writer.println("respon contect");    }}

解决响应中文乱码方案二(推荐):

// 它会同时设置服务器和客户端都使用 UTF-8 字符集,还设置了响应头

// 此方法一定要在获取流对象之前调用才有效

resp.setContentType(“text/html; charset=UTF-8”);


6.4请求重定向

请求重定向,是指客户端给服务器发请求,然后服务器告诉客户端说。我给你一些地址。你去新地址访问。叫请求重定向(因为之前的地址可能已经被废弃)。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qmmTfI2i-1624636891069)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210407173228636.png)]


请求重定向的第一种方案:

// 设置响应状态码 302 ,表示重定向,(已搬迁)

resp.setStatus(302);

// 设置响应头,说明 新的地址在哪里

resp.setHeader(“Location”, “http://localhost:8080”);

请求重定向的第二种方案(推荐使用):

resp.sendRedirect(“http://localhost:8080”);

七丶书城项目

1.JavaEE 项目的三层架构

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yKiYH8j0-1624636891070)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210407190407205.png)]

分层的目的是为了解耦。解耦就是为了降低代码的耦合度。方便项目后期的维护和升级


web层com.atguigu.web/servlet/controllerService 接口包
service层com.atguigu.service com.atguigu.utilsService 接口实现类
dao持久层com.atguigu.dao com.atguigu.dao.implDao 接口包
实体bean对象com.atguigu.pojo/entity/domain/beanDao 接口实现类
测试包com.atguigu.test/junitJavaBean 类
工具类com.atguigu.utils

2.先创建书城需要的数据库和表

DROP DATABASE IF EXISTS book;CREATE DATABASE book;-- `id`不是单引号,注释后面要加空格 --USE book;CREATE TABLE t_user(`id` INT PRIMARY KEY AUTO_INCREMENT,`username` VARCHAR(20) NOT NULL UNIQUE,`password` VARCHAR(32) NOT NULL,`email` VARCHAR(200));INSERT INTO t_user(`username`,`password`,`email`)VALUE('admin','admin','admin@atguigu.com');SELECT * FROM t_user;

3.编写工具类 JdbcUtils

package itguiguWeb.pojo;public class User {    //把id设为Integer是因为可以进行==null的判断,int的默认值为0,integer为null    private Integer id;    private String username;    private String password;    private String email;    public Integer getId() {        return id;    }    public void setId(Integer id) {        this.id = id;    }    public String getUsername() {        return username;    }    public void setUsername(String username) {        this.username = username;    }    public String getPassword() {        return password;    }    public void setPassword(String password) {        this.password = password;    }    public String getEmail() {        return email;    }    public void setEmail(String email) {        this.email = email;    }    @Override    public String toString() {        return "User{" +                "id=" + id +                ", username='" + username + '\'' +                ", password='" + password + '\'' +                ", email='" + email + '\'' +                '}';    }    public User(Integer id, String username, String password, String email) {        this.id = id;        this.username = username;        this.password = password;        this.email = email;    }    public User() {    }}

3.编写工具类 JdbcUtils

3.1导入需要的 jar 包(数据库和连接池需要):

druid-1.1.9.jar

mysql-connector-java-5.1.7-bin.jar

以下是测试需要:

hamcrest-core-1.3.jar

junit-4.12.jar


3.2 src 源码目录下编写 jdbc.properties 属性配置文件:

username=rootpassword=2580147url=jdbc:mysql://localhost:3306/book?useSSL=false&allowPublicKeyRetrieval=true&serverTimezone=UTCdriverClassName=com.mysql.cj.jdbc.DriverinitialSize=5maxActive=10

3.2编写 JdbcUtils 工具类:

package itguiguWeb.utils;import com.alibaba.druid.pool.DruidDataSource;import com.alibaba.druid.pool.DruidDataSourceFactory;import java.io.InputStream;import java.sql.Connection;import java.sql.SQLException;import java.util.Properties;public class JdbcUtils {    private static DruidDataSource dataSource;    static {        Properties properties = new Properties();        //读取jdbc.properties属性配置文件        InputStream inputStream = JdbcUtils.class.getClassLoader().getResourceAsStream("jdbc.properties");        try {            //从流中加载数据            properties.load(inputStream);            //创建数据库连接池            dataSource = (DruidDataSource) DruidDataSourceFactory.createDataSource(properties);            //System.out.println(dataSource.getConnection());        } catch (Exception e) {            e.printStackTrace();        }    }    /**     * 获取数据库池中的连接     *     * @return如果返回null,说明获取连接失败     */    public static Connection getConnection() {        Connection conn = null;        try {            conn = dataSource.getConnection();        } catch (Exception e) {            e.printStackTrace();        }        return conn;    }    /**     * 关闭数据库连接池     *     * @param conn     */    public static void close(Connection conn) {        if (conn != null) {            try {                conn.close();            } catch (SQLException throwables) {                throwables.printStackTrace();            }        }    }}

3.4JdbcUtils 测试

package itguiguWeb.test;import itguiguWeb.utils.JdbcUtils;import org.junit.Test;import java.sql.Connection;public class Jdbc {    @Test    public void testJdbc() {        for (int i = 0; i < 100; i++) {            Connection connection = JdbcUtils.getConnection();            System.out.println(connection);            JdbcUtils.close(connection);        }    }}

4.编写 BaseDao

package itguiguWeb.dao.impl;import itguiguWeb.utils.JdbcUtils;import org.apache.commons.dbutils.QueryRunner;import org.apache.commons.dbutils.handlers.BeanHandler;import org.apache.commons.dbutils.handlers.BeanListHandler;import org.apache.commons.dbutils.handlers.ScalarHandler;import java.sql.Connection;import java.sql.SQLException;import java.util.Collection;import java.util.List;public abstract class BassDao {    //使用db操作数据库    private QueryRunner queryRunner = new QueryRunner();    /**     * update()执行 insert update detele 语句     *     * @return 如果返回-1说明执行失败     */    public int update(String sql, Object... args) {        Connection connection = JdbcUtils.getConnection();        try {            return queryRunner.update(connection, sql, args);        } catch (SQLException throwables) {            throwables.printStackTrace();        } finally {            //关闭连接            JdbcUtils.close(connection);        }        return -1;    }    /**     * 查询返回一个javaBean的sql语句     *     * @param type 返回的对象类型     * @param sql  执行的sql语句     * @param args sql对应的参数值     * @param <T>  返回类型的泛型     * @return     */    public <T> Object queryForOne(Class<T> type, String sql, Object... args) {        Connection connection = JdbcUtils.getConnection();        try {            return queryRunner.query(connection, sql, new BeanHandler<T>(type), args);        } catch (SQLException e) {            e.printStackTrace();        } finally {            //关闭连接            JdbcUtils.close(connection);        }        return null;    }    /**     * 查询返回多个值javaBean的sql语句     *     * @param type     * @param sql     * @param args     * @param <T>     * @return     */    public <T> List<T> queryForList(Class<T> type, String sql, Object... args) {        Connection connection = JdbcUtils.getConnection();        try {            return queryRunner.query(connection, sql, new BeanListHandler<>(type), args);        } catch (SQLException e) {            e.printStackTrace();        } finally {            //关闭连接            JdbcUtils.close(connection);        }        return null;    }    /**     * 执行返回一行一列的sql语句     *     * @param sql     * @param args     * @return     */    public Object queryForSingleValue(String sql, Object... args) {        Connection collection = JdbcUtils.getConnection();        try {            return queryRunner.query(collection, sql, new ScalarHandler(), args);        } catch (Exception e) {            e.printStackTrace();            return null;        } finally {            JdbcUtils.close(collection);        }    }}

5.编写 UserDao****和测试

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qG89DWcJ-1624636891071)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210408193210130.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-w8qkgt7S-1624636891071)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210408193258093.png)]

八丶JSP

1.什么是JSP,它有什么作用?

jsp 的全换是 java server pages。Java 的服务器页面。

jsp 的主要作用是代替 Servlet 程序回传 html 页面的数据。

因为 Servlet 程序回传 html 页面数据是一件非常繁锁的事情。开发成本和维护成本都极高。

2.jsp 的本质是什么

jsp 页面本质上是一个 Servlet 程序。

当我们第一次访问 jsp 页面的时候。Tomcat 服务器会帮我们把 jsp 页面翻译成为一个 java 源文件。并且对它进行编译成为.class 字节码程序。我们打开 java 源文件不难发现其里面的内容是:

我们跟踪原代码发现,HttpJspBase 类。它直接地继承了 HttpServlet 类。也就是说。jsp 翻译出来的 java 类,它间接了继承了 HttpServlet 类。也就是说,翻译出来的是一个 Servlet 程序.

3.JSP头部的page指令

jsp的page指令可以修改jsp页面中的一些重要的属性,或者行为

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
language属性表示jsp翻译后是什么语言文件,暂时只支持java
contentType属性表示jsp返回的数据类型是什么,是源码中的response.setContType参数值
pageEncoding属性表示当前 jsp 页面文件本身的字符集
import属性跟 java 源代码中一样。用于导包,导类
autoFlush属性设置当 out 输出流缓冲区满了之后,是否自动刷新冲级区。默认值是 true
buffer属性设置 out 缓冲区的大小。默认是 8kb
errorPage属性设置当 jsp 页面运行时出错,自动跳转去的错误页面路径
isErrorPage属性设置当前 jsp 页面是否是错误信息页面。默认是 false。如果是 true 可以获取异常信息
session属性设置访问当前 jsp 页面,是否会创建 HttpSession 对象。默认是 true
extends属性设置 jsp 翻译出来的 java 类默认继承谁

3.1jsp中的常用脚本

声明脚本

声明脚本的格式是:

<%! 声明java代码 %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %><html><head>    <title>Title</title></head><body><%--1.声明类的属性--%><%!    private Integer id;    private String name;    private static Map<String, Object> map;%>><%--2.声明静态代码块--%><%!    static {        map = new HashMap<>();        map.put("key1", "value1");        map.put("key2", "value2");        map.put("key3", "value3");        map.put("key4", "value4");    }%><%--3.声明类方法--%><%!    public int abc() {        return 12;    }%><%--4.生成内部类--%><%!    public static class A {        private Integer id = 12;        private String abc = "abc";    }%></body></html>

3.2表达式脚本

表达式脚本的格式是:

<%=表达式%>

**表达式脚本的作用是:**在jsp 页面上输出数据

表达式脚本的特点:

1、所有的表达式脚本都会被翻译到_jspService() 方法中

2、表达式脚本都会被翻译成为 out.print()输出到页面上

3、由于表达式脚本翻译的内容都在_jspService() 方法中,所以_jspService()方法中的对象都可以直接使用。

4、表达式脚本中的表达式不能以分号结束。

<%--1.输出整型--%><%=12%> <br/><%--2.输出浮点型--%><%= 12.12%> <br/><%--3.输出字符串--%><%= "我是字符串"%> <br/><%--4.输出对象--%><%=map%> <br/>

3.3代码脚本

代码脚本的格式是:

<%java语句    %>

代码脚本的作用是:可以在 jsp 页面中,编写我们自己需要的功能(写的是 java 语句)

代码脚本的特点是:

1、代码脚本翻译之后都在_jspService 方法中

2、代码脚本由于翻译到_jspService()方法中,所以在_jspService()方法中的现有对象都可以直接使用。

3、还可以由多个代码脚本块组合完成一个完整的 java 语句。

4、代码脚本还可以和表达式脚本一起组合使用,在 jsp 页面上输出数据

<%    int i=13;    if (i==12){        System.out.println("尧哥好帅");    }else {        System.out.println("尧哥又骗人");    }%><%    for (int j=0;j<10;j++){        System.out.println(j);    }%>

3.4jsp中的三种注释

html注释

<!--注释-->

html 注释会被翻译到 java 源代码中。在_jspService 方法里,以 out.writer 输出到客户端


java 注释

<% // 单行 java 注释 /* 多行 java 注释 */ %>

java 注释会被翻译到 java 源代码中


jsp 注释

<%-- 这是 jsp 注释 --%>

jsp 注释可以注掉,jsp 页面中所有代码

4.jsp 九大内置对象

jsp 中的内置对象,是指 Tomcat 在翻译 jsp 页面成为 Servlet 源代码后,内部提供的九大对象,叫内置对象

对象描述
requestHttpServletRequest 接口的实例
responseHttpServletResponse 接口的实例
outJspWriter类的实例,用于把结果输出至网页上
sessionHttpSession类的实例
applicationServletContext类的实例,与应用上下文有关
configServletConfig类的实例
pageContextPageContext类的实例,提供对JSP页面所有对象以及命名空间的访问
page类似于Java类中的this关键字
ExceptionException类的对象,代表发生错误的JSP页面中对应的异常对象

request对象

request对象是javax.servlet.http.HttpServletRequest 类的实例。每当客户端请求一个JSP页面时,JSP引擎就会制造一个新的request对象来代表这个请求。

request对象提供了一系列方法来获取HTTP头信息,cookies,HTTP方法等等。


response对象

response对象是javax.servlet.http.HttpServletResponse类的实例。当服务器创建request对象时会同时创建用于响应这个客户端的response对象。

response对象也定义了处理HTTP头模块的接口。通过这个对象,开发者们可以添加新的cookies,时间戳,HTTP状态码等等。


response对象

out对象是 javax.servlet.jsp.JspWriter 类的实例,用来在response对象中写入内容。

最初的JspWriter类对象根据页面是否有缓存来进行不同的实例化操作。可以在page指令中使用buffered='false’属性来轻松关闭缓存。

JspWriter类包含了大部分java.io.PrintWriter类中的方法。不过,JspWriter新增了一些专为处理缓存而设计的方法。还有就是,JspWriter类会抛出IOExceptions异常,而PrintWriter不会。

下表列出了我们将会用来输出boolean,char,int,double,String,object等类型数据的重要方法:

方法描述
out.print(dataType dt)输出Type类型的值
out.println(dataType dt)输出Type类型的值然后换行
out.flush()刷新输出流

session对象

session对象是 javax.servlet.http.HttpSession 类的实例。和Java Servlets中的session对象有一样的行为。

session对象用来跟踪在各个客户端请求间的会话。


application对象

application对象直接包装了servlet的ServletContext类的对象,是javax.servlet.ServletContext 类的实例。

这个对象在JSP页面的整个生命周期中都代表着这个JSP页面。这个对象在JSP页面初始化时被创建,随着jspDestroy()方法的调用而被移除。

通过向application中添加属性,则所有组成您web应用的JSP文件都能访问到这些属性。


config对象

config对象是 javax.servlet.ServletConfig 类的实例,直接包装了servlet的ServletConfig类的对象。

这个对象允许开发者访问Servlet或者JSP引擎的初始化参数,比如文件路径等。

以下是config对象的使用方法,不是很重要,所以不常用:

config.getServletName();

它返回包含在元素中的servlet名字,注意,元素在 WEB-INF\web.xml 文件中定义。


pageContext 对象

pageContext对象是javax.servlet.jsp.PageContext 类的实例,用来代表整个JSP页面。

这个对象主要用来访问页面信息,同时过滤掉大部分实现细节。

这个对象存储了request对象和response对象的引用。application对象,config对象,session对象,out对象可以通过访问这个对象的属性来导出。

pageContext对象也包含了传给JSP页面的指令信息,包括缓存信息,ErrorPage URL,页面scope等。

PageContext类定义了一些字段,包括PAGE_SCOPE,REQUEST_SCOPE,SESSION_SCOPE, APPLICATION_SCOPE。它也提供了40余种方法,有一半继承自javax.servlet.jsp.JspContext 类。

其中一个重要的方法就是 removeAttribute(),它可接受一个或两个参数。比如,pageContext.removeAttribute(“attrName”) 移除四个scope中相关属性,但是下面这种方法只移除特定 scope 中的相关属性:

pageContext.removeAttribute("attrName", PAGE_SCOPE);

page 对象

这个对象就是页面实例的引用。它可以被看做是整个JSP页面的代表。

page 对象就是this对象的同义词。


exception 对象

exception 对象包装了从先前页面中抛出的异常信息。它通常被用来产生对出错条件的适当响应。

5.jsp四大域对象

pageContext(PageContextImpl 类)当前 jsp 页面范围内有效
request(HttpServletRequest 类)一次请求内有效
session(HttpSession 类)一个会话范围内有效(打开浏览器访问服务器,直到关闭浏览器)
application(ServletContext 类)整个 web 工程范围内都有效(只要 web 工程不停止,数据都在)

域对象是可以像 Map 一样存取数据的对象。四个域对象功能一样。不同的是它们对数据的存取范围。

虽然四个域对象都可以存取数据。在使用上它们是有优先顺序的。

四个域在使用的时候,优先顺序分别是,他们从小到大的范围的顺序。

pageContext ====>>> request ====>>> session ====>>> application


6.jsp 中的 out 输出和 response.getWriter 输出的区

response 中表示响应,我们经常用于设置返回给客户端的内容(输出)

out 也是给用户做输出使用的

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-jEmSb2lk-1624636891072)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210410132016417.png)]

由于 jsp 翻译之后,底层源代码都是使用 out 来进行输出,所以一般情况下。我们在 jsp 页面中统一使用 out 来进行输出。避免打乱页面输出内容的顺序。

out.write() 输出字符串没有问题

out.print() 输出任意数据都没有问题(都转换成为字符串后调用的 write 输出)

深入源码,浅出结论:在 jsp 页面中,可以统一使用 out.print()来进行输出


7.jsp 的常用标签

7.1jsp静态包含

<%@ page contentType="text/html;charset=UTF-8" language="java" %><html><head>    <title>Title</title></head><body>头部信息<br/>主题内容<br/><%--<%@include file="foot.jsp"%> 就是静态包含file属性指定你要包含的jsp页面的路径地址中得第一个斜杠/表示为http://ip:port/工程路径/映射到代码的web目录--%><%@include file="foot.jsp" %></body></html

7.2jsp动态包含

<%--<jsp:include page="foot.jsp"></jsp:include> 这是动态包含page 属性指定你要包含的jsp页面的路径动态包含也可以像静态包含一样,把被包含的内容执行输出到包含位置动态包含的特点: 1、动态包含会把包含的 jsp 页面也翻译成为 java 代码 2、动态包含底层代码使用如下代码去调用被包含的 jsp 页面执行输出。 JspRuntimeLibrary.include(request, response, "/include/footer.jsp", out, false); 3、动态包含,还可以传递参数--%><jsp:include page="foot.jsp">    <jsp:param name="username" value="bbj"/>     <jsp:param name="password" value="root"/></jsp:include></body>

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-UMzmxfGk-1624636891073)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210410140530348.png)]

7.3jsp标签转发

<%--    <jsp:forward page=""></jsp:forward> 是请求转发标签,它的功能就是请求转发         page 属性设置请求转发的路径         --%> <jsp:forward page="/scope2.jsp"></jsp:forward>

8.什么是 Listener 监听器?

1、Listener 监听器它是 JavaWeb 的三大组件之一。JavaWeb 的三大组件分别是:Servlet 程序、Filter 过滤器、Listener 监听器。

2、Listener 它是 JavaEE 的规范,就是接口

3、监听器的作用是,监听某种事物的变化。然后通过回调函数,反馈给客户(程序)去做一些相应的处理。

8.1ServletContextListener 监听器

ServletContextListener 它可以监听 ServletContext 对象的创建和销毁。

ServletContext 对象在 web 工程启动的时候创建,在 web 工程停止的时候销毁。

监听到创建和销毁之后都会分别调用 ServletContextListener 监听器的方法反馈。


如何使用 ServletContextListener 监听器监听 ServletContext 对象。

使用步骤如下:

1、编写一个类去实现 ServletContextListener

2、实现其两个回调方法

3、到 web.xml 中去配置监听器

九丶EL表达式

1.什么是 EL 表达式,EL表达式的作用?

EL 表达式的全称是:Expression Language。是表达式语言。

EL 表达式的什么作用:EL 表达式主要是代替 jsp 页面中的表达式脚本在 jsp 页面中进行数据的输出。

因为 EL 表达式在输出数据的时候,要比 jsp 的表达式脚本要简洁很多。


EL 表达式的格式是:${表达式}

EL 表达式在输出 null 值的时候,输出的是空串。jsp 表达式脚本输出 null 值的时候,输出的是 null 字符串。

2.EL 表达式搜索域数据的顺序

EL 表达式主要是在 jsp 页面中输出数据。

主要是输出域对象中的数据。

当四个域中都有相同的 key 的数据的时候,EL 表达式会按照四个域的从小到大的顺序去进行搜索,找到就输出

3.EL 表达式输出 Bean **的普通属性,数组属性。List **集 **合属性,**map 集合属性

输出 Person:${ p }<br/>输出 Person 的 name 属性:${p.name} <br>输出 Person 的 pnones 数组属性值:${p.phones[2]} <br>输出 Person 的 cities集合中的元素值:${p.cities} <br>输出 Person 的 List 集合中个别元素值:${p.cities[2]} <br>输出 Person 的 Map 集合: ${p.map} <br>输出 Person 的 Map集合中某个 key 的值: ${p.map.key3} <br>输出 Person 的 age 属性:${p.age} <br>

4.EL表达式的运算

语法:${ 运算表达式} , EL 表达式支持如下运算符:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-EzqGWzb8-1624636891074)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412104010423.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-iAejSpuj-1624636891075)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412104022549.png)]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-nXmsThXU-1624636891076)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412104036769.png)]

empty 运算

empty 运算可以判断一个数据是否为空,如果为空,则输出 true,不为空输出 false。

以下几种情况为空:

1、值为 null 值的时候,为空

2、值为空串的时候,为空

3、值是 Object 类型数组,长度为零的时候

4、list 集合,元素个数为零

5、map 集合,元素个数为零

三元运算

表达式 1?表达式 2:表达式 3

如果表达式 1 的值为真,返回表达式 2 的值,如果表达式 1 的值为假,返回表达式 3 的值

${12!=12?"好帅的陈文尧":"猪"}

.”点运算 和 [] 中括号运算符

.点运算,可以输出 Bean 对象中某个属性的值。

[]中括号运算,可以输出有序集合中某个元素的值。

并且[]中括号运算,还可以输出 map 集合中 key 里含有特殊字符的 key 的值

EL表达式的 11 个隐含对象

变量类型作用
pageContextPageContextlmpl获取jsp中的九大内置对象
pageScopeMap<String,Object>获取 pageContext 域中的数据
requestScopeMap<String,Object>
sessionScopeMap<String,Object>
applicationScopeMap<String,Object>
paramMap<String,String>它可以获取请求参数的值
paramValuesMap<String,String[]>它也可以获取请求参数的值,获取多个值的时候使用
headerMap<String,String>它可以获取请求头的信息
headerValuesMap<String,String[]>它可以获取请求头的信息,它可以获取多个值的情况
cookieMap<String,Cookie>它可以获取当前请求的 Cookie 信息
initParamMap<String,String>它可以获取在 web.xml 中配置的上下文参数

EL 获取四个特定域中的属性

pageScope ====== pageContext 域

requestScope ====== Request 域

sessionScope ====== Session 域

applicationScope ====== ServletContext 域

pageContext 对象的使用

\1.

协议:

\2.

服务器 ip:

3.

服务器端口:

\4.

获取工程路径:

\5.

获取请求方法:

\6.

获取客户端 ip 地址:

\7.

获取会话的 id 编号:

1.协议: ${ req.scheme }<br>2.服务器 ip:${ pageContext.request.serverName }<br>3.服务器端口:${ pageContext.request.serverPort }<br>4.获取工程路径:${ pageContext.request.contextPath }<br>5.获取请求方法:${ pageContext.request.method }<br>6.获取客户端 ip 地址:${ pageContext.request.remoteHost }<br>7.获取会话的 id 编号:${ pageContext.session.id }<br>

十丶JSTL标签库

JSTL 标签库 全称是指 JSP Standard Tag Library JSP 标准标签库。是一个不断完善的开放源代码的 JSP 标签库。

EL 表达式主要是为了替换 jsp 中的表达式脚本,而标签库则是为了替换代码脚本。这样使得整个 jsp 页面变得更佳简洁

JSTL 由五个不同功能的标签库组成

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-GXILdakp-1624636891076)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412130044550.png)]

1.JSTL 标签库的使用步骤

1.先导入 jstl 标签库的 jar 包

taglibs-standard-impl-1.2.1.jar

taglibs-standard-spec-1.2.1.jar

2.使用 taglib 指令引入标签库

CORE 标签库 <%@ taglib prefix="c"uri="http://java.sun.com/jsp/jstl/core" %> XML 标签库<%@ taglib prefix="x"uri="http://java.sun.com/jsp/jstl/xml" %> FMT 标签库 <%@ taglib prefix="fmt"uri="http://java.sun.com/jsp/jstl/fmt" %> SQL 标签库 <%@ taglib prefix="sql"uri="http://java.sun.com/jsp/jstl/sql" %> FUNCTIONS 标签库 <%@ taglib prefix="fn"uri="http://java.sun.com/jsp/jstl/functions" %>

2.core核心库使用

1.<c:set />(使用很少)

作用:set 标签可以往域中保存数据

<%--     i.<c:set />        作用:set 标签可以往域中保存数据         域对象.setAttribute(key,value);scope 属性设置保存到哪个域     page 表示 PageContext 域(默认值)     request 表示 Request 域     session 表示 Session 域     application 表示 ServletContext 域     var 属性设置 key 是多少     value 属性设置值 --%> 保存之前:${ sessionScope.abc } <br> <c:set scope="session" var="abc" value="abcValue"/>保存之后:${ sessionScope.abc } <br>

2.<c:if />

if标签用来做if判断

<%--    ii.<c:if /> i        f 标签用来做 if 判断。             test 属性表示判断的条件(使用 EL 表达式输出)             --%> <c:if test="${ 12 == 12 }">     <h1>12 等于 12</h1> </c:if> <c:if test="${ 12 != 12 }">    <h1>12 不等于 12</h1> </c:if>

3.**<**c:choose> <c:when> **<**c:otherwise>标签

作用:多路判断。跟 switch … case … default 非常接近

<%--     iii.<c:choose> <c:when> <c:otherwise>标签        作用:多路判断。跟 switch ... case .... default 非常接近             choose 标签开始选择判断             when 标签表示每一种判断情况             test 属性表示当前这种判断情况的值             otherwise 标签表示剩下的情况             <c:choose> <c:when> <c:otherwise>标签使用时需要注意的点:                 1、标签里不能使用 html 注释,要使用 jsp 注释 2、when 标签的父标签一定要是 choose 标签                --%> <% request.setAttribute("height", 180); %><c:choose>     <%-- 这是 html 注释 --%>     <c:when test="${ requestScope.height > 190 }">        <h2>小巨人</h2>     </c:when>    <c:when test="${ requestScope.height > 180 }">         <h2>很高</h2>    </c:when>    <c:when test="${ requestScope.height > 170 }">         <h2>还可以</h2>    </c:when><c:otherwise>     <c:choose>         <c:when test="${requestScope.height > 160}"> <h3>大于 160</h3>         </c:when>         <c:when test="${requestScope.height > 150}"> <h3>大于 150</h3>        </c:when>         <c:when test="${requestScope.height > 140}"> <h3>大于 140</h3>         </c:when>        <c:otherwise>             其他小于 140         </c:otherwise>     </c:choose>    </c:otherwise> </c:choose>

5.<c:forEach />

作用:遍历输出使用

1.遍历 1 10,输出
<%--1.遍历 1 到 10,输出     begin 属性设置开始的索引     end 属性设置结束的索引     var 属性表示循环的变量(也是当前正在遍历到的数据)     for (int i = 1; i < 10; i++)         --%><table border="1">     <c:forEach begin="1" end="10" var="i">         <tr>            <td>第${i}行</td>         </tr>     </c:forEach> </table>
2.遍历 Object 数组
<%-- 2.遍历 Object 数组    for (Object item: arr)         items 表示遍历的数据源(遍历的集合)         var 表示当前遍历到的数据         --%> <% request.setAttribute("arr", new String[]{"18610541354","18688886666","18699998888"});%><c:forEach items="${ requestScope.arr }" var="item"> ${ item } <br> </c:forEach>
3.遍历Map集合
<% Map<String,Object> map = new HashMap<String, Object>(); map.put("key1", "value1"); map.put("key2", "value2"); map.put("key3", "value3"); // for ( Map.Entry<String,Object> entry : map.entrySet()) { // } request.setAttribute("map", map); %><c:forEach items="${ requestScope.map }" var="entry"> <h1>${entry.key} = ${entry.value}</h1> </c:forEach>
4.遍历 List 集合—list 中存放 Student **类,有属性:编号,用户名,密码,年龄,**电话信息
<%--4.遍历 List 集合---list 中存放 Student 类,有属性:编号,用户名,密码,年龄,电话信息--%> <% List<Student> studentList = new ArrayList<Student>(); for (int i = 1; i <= 10; i++) {    studentList.add(new Student(i,"username"+i ,"pass"+i,18+i,"phone"+i)); }request.setAttribute("stus", studentList); %><table>     <tr><th>编号</th>        <th>用户名</th>        <th>密码</th>         <th>年龄</th>         <th>电话</th>         <th>操作</th>     </tr>     <%    --items 表示遍历的集合        var 表示遍历到的数据        begin 表示遍历的开始索引值         end 表示结束的索引值        step 属性表示遍历的步长值         varStatus 属性表示当前遍历到的数据的状态        for(int i = 1; i < 10; i+=2)             --%>     <c:forEach begin="2" end="7" step="2" varStatus="status" items="${requestScope.stus}" var="stu">         <tr><            td>${stu.id}</td>             <td>${stu.username}</td>            <td>${stu.password}</td>             <td>${stu.age}</td>            <td>${stu.phone}</td>             <td>${status.step}</td>        </tr>     </c:forEach> </table>

十一丶文件的上传和下载

1.文件的上传介绍(重点)

1.要有一个form标签,method=post请求

2.form标签的encType 属性值必须为 multipart/form-data 值

3.在 form 标签中使用 input type=file 添加上传的文件

4.编写服务器代码(Servlet 程序)接收,处理上传的数据

encType=multipart/form-data 表示提交的数据,以多段(每一个表单项一个数据段)的形式进行拼

接,然后以二进制流的形式发送给服务器


1.**文件上传,**HTTP 协议的说明

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-yEJyAuR9-1624636891077)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412150852037.png)]

2.commons-fileupload.jar 常用 API 介绍说明

commons-fileupload.jar 需要依赖 commons-io.jar 这个包,所以两个包我们都要引入。

第一步,就是需要导入两个 jar 包:

commons-fileupload-1.2.1.jar

commons-io-1.4.jar


commons-fileupload.jar commons-io.jar 包中,我们常用的类有哪些?

ServletFileUpload 类,用于解析上传的数据。

FileItem 类,表示每一个表单项。

boolean ServletFileUpload.isMultipartContent(HttpServletRequest request);

判断当前上传的数据格式是否是多段的格式。

public List parseRequest(HttpServletRequest request)

解析上传的数据

boolean FileItem.isFormField()

判断当前这个表单项,是否是普通的表单项。还是上传的文件类型。

true 表示普通类型的表单项

false 表示上传的文件类型

String FileItem.getFieldName()

获取表单项的 name 属性值

String FileItem.getString()

获取当前表单项的值。

String FileItem.getName();

获取上传的文件名

void FileItem.write( file );

将上传的文件写到 参数 file 所指向抽硬盘位置

3.fileupload类库使用

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ddGd76qd-1624636891078)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412163245732.png)]

2.文件下载

下载的常用 API 说明:

response.getOutputStream();

servletContext.getResourceAsStream();

servletContext.getMimeType();

response.setContentType();

response.setHeader(“Content-Disposition”, “attachment; fileName=1.jpg”);

这个响应头告诉浏览器。这是需要下载的。而 attachment 表示附件,也就是下载的一个文件。fileName=后面,

表示下载的文件名。

完成上面的两个步骤,下载文件是没问题了。但是如果我们要下载的文件是中文名的话。你会发现,下载无法正确显示出正确的中文名。

原因是在响应头中,不能包含有中文字符,只能包含 ASCII 码


附件中文名乱码问题解决方案:

**方案一:**URLEncoder 解决 IE 和谷歌浏览器的 附件中

文名问题。

如果客户端浏览器是 IE 浏览器 或者 是谷歌浏览器。我们需要使用 URLEncoder 类先对中文名进行 UTF-8 的编码

操作。

因为 IE 浏览器和谷歌浏览器收到含有编码后的字符串后会以 UTF-8 字符集进行解码显示。

// 把中文名进行 UTF-8 编码操作。

String str = “attachment; fileName=” + URLEncoder.encode(“中文.jpg”, “UTF-8”);

// 然后把编码后的字符串设置到响应头中

response.setHeader(“Content-Disposition”, str);

**方案二:**BASE64 编解码 解决 火狐浏览器的附件中文名问

如果客户端浏览器是火狐浏览器。 那么我们需要对中文名进行 BASE64 的编码操作。

这时候需要把请求头 Content-Disposition: attachment; filename=中文名

编码成为:Content-Disposition: attachment; filename==?charset?B?xxxxx?=

=?charset?B?xxxxx?= 现在我们对这段内容进行一下说明。

=?

charset

B

xxxx

?=BASE64 编解码操作:

因为火狐使用的是 BASE64 的编解码方式还原响应中的汉字。所以需要使用 BASE64Encoder 类进行编码操作。

// 使用下面的格式进行 BASE64 编码后

String str =

“attachment; fileName=” + “=?utf-8?B?”

+ new

BASE64Encoder().encode(“中文.jpg”.getBytes(“utf-8”))

+ “?=”;

// 设置到响应头中

response.setHeader(“Content-Disposition”, str);

那么我们如何解决上面两种不同编解码方式呢。我们只需要通过判断请求头中 User-Agent 这个请求头携带过来的

浏览器信息即可判断出是什么浏览器。

如下:

String ua = request.getHeader(“User-Agent”);

//

判断是否是火狐浏览器

if

(ua.contains(“Firefox”)) {

// 使用下面的格式进行 BASE64 编码后

String str =

“attachment; fileName=” + “=?utf-8?B?”

+ new

BASE64Encoder().encode(“中文.jpg”.getBytes(“utf-8”))

+ “?=”;

// 设置到响应头中

response.setHeader(“Content-Disposition”, str);

} else {

// 把中文名进行 UTF-8 编码操作。

String str = “attachment; fileName=” + URLEncoder.encode(“中文.jpg”, “UTF-8”);

// 然后把编码后的字符串设置到响应头中

response.setHeader(“Content-Disposition”, str);

}


十二丶Cookie和Session

1.Cookie

1.什么是Cookie?

1、Cookie 翻译过来是饼干的意思。

2、Cookie 是服务器通知客户端保存键值对的一种技术。

3、客户端有了 Cookie 后,每次请求都发送给服务器。

4、每个 Cookie 的大小不能超过 4kb

2.如何创建Cookie

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-sN4obXPu-1624636891079)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412170408572.png)]

protected void createCookie(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {     //1 创建 Cookie 对象Cookie cookie = new Cookie("key4", "value4");     //2 通知客户端保存     Cookie resp.addCookie(cookie);     //1 创建 Cookie 对象    Cookie cookie1 = new Cookie("key5", "value5");     //2 通知客户端保存     Cookie resp.addCookie(cookie1); resp.getWriter().write("Cookie 创建成功"); }

3.服务器如何获取cookie

服务器获取客户端的 Cookie 只需要一行代码:req.getCookies():Cookie[]

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-1j2BYBgo-1624636891079)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210412180114798.png)]


cookie的工具类

public class CookieUtils {     /**    * 查找指定名称的 Cookie 对象    * @param name     * @param cookies    * @return     */    public static Cookie findCookie(String name , Cookie[] cookies){         if (name == null || cookies == null || cookies.length == 0) {             return null;         }        for (Cookie cookie : cookies) {             if (name.equals(cookie.getName())) {                 return cookie;            }         }        return null;    }}

servlet程序

protected void getCookie(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {     Cookie[] cookies = req.getCookies();    for (Cookie cookie : cookies) {        // getName 方法返回 Cookie 的 key(名)        // getValue 方法返回 Cookie 的 value 值         resp.getWriter().write("Cookie[" + cookie.getName() + "=" + cookie.getValue() + "] <br/>");     }    Cookie iWantCookie = CookieUtils.findCookie("key1", cookies);     // for (Cookie cookie : cookies) {     // if ("key2".equals(cookie.getName())) {     // iWantCookie = cookie;    // break;     // }     // }     // 如果不等于null,说明赋过值,也就是找到了需要的 Cookie     if (iWantCookie != null) { resp.getWriter().write("找到了需要的 Cookie");                                                      }}

4.Cookie值的修改

方案一:

1、先创建一个要修改的同名(指的就是 key)的 Cookie 对象

2、在构造器,同时赋于新的 Cookie 值。

3、调用 response.addCookie( Cookie );

// 方案一: // 1、先创建一个要修改的同名的 Cookie 对象 // 2、在构造器,同时赋于新的 Cookie 值。Cookie cookie = new Cookie("key1","newValue1"); // 3、调用 response.addCookie( Cookie ); 通知 客户端 保存修改resp.addCookie(cookie);

方案二:

1、先查找到需要修改的 Cookie 对象

2、调用 setValue()方法赋于新的 Cookie 值。

3、调用 response.addCookie()通知客户端保存修改

// 方案二: // 1、先查找到需要修改的 Cookie 对象Cookie cookie = CookieUtils.findCookie("key2", req.getCookies()); if (cookie != null) {     // 2、调用 setValue()方法赋于新的 Cookie 值。     cookie.setValue("newValue2");     // 3、调用 response.addCookie()通知客户端保存修改     resp.addCookie(cookie); }

5.Cookie生命控制

Cookie 的生命控制指的是如何管理 Cookie 什么时候被销毁(删除)

setMaxAge()

正数,表示在指定的秒数后过期

负数,表示浏览器一关,Cookie 就会被删除(默认值是-1)

零,表示马上删除 Cookie

6.Cookie有效路径Path的设置

Cookie 的 path 属性可以有效的过滤哪些 Cookie 可以发送给服务器。哪些不发。

path 属性是通过请求的地址来进行有效的过滤。

CookieA path=/工程路径

CookieB path=/工程路径/abc

请求地址如下:

http://ip:port/工程路径/a.html

CookieA 发送

CookieB 不发送

http://ip:port/工程路径/abc/a.html

CookieA 发送

CookieB 发送

7.Cookie练习-免用户名登录

jsp页面

<form action="http://localhost:8080/Cookie/loginServlet" method="get">    用户名:<input type="text" name="username" value="${cookie.username.value}"><br/>    密码:<input type="password" name="password" id=""><br/>    <input type="submit"></form>

Servlet程序

public class LoginServlet extends HttpServlet {    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        String username = req.getParameter("username");        String password = req.getParameter("password");        if ("ZJH".equals(username) && "2580147".equals(password)) {            //登陆成功,把用户名保存为Cookie            Cookie cookie = new Cookie("username", username);            //设置Cookie保存时间            cookie.setMaxAge(60 * 60 * 24 * 7);//Cookie保存一星期            //保存Cookie            resp.addCookie(cookie);            System.out.println("登陆成功");        } else {//登陆失败            System.out.println("登陆失败");        }    }}

2.Session会话

1.什么是Session会话?

1、Session 就一个接口(HttpSession)。

2、Session 就是会话。它是用来维护一个客户端和服务器之间关联的一种技术。

3、每个客户端都有自己的一个 Session 会话。

4、Session 会话中,我们经常用来保存用户登录之后的信息。

2.如何创建Session和获取(id号)

如何创建和获取 Session。它们的 API 是一样的。

request.getSession()

第一次调用是:创建 Session 会话

之后调用都是:获取前面创建好的 Session 会话对象。


isNew(); 判断到底是不是刚创建出来的(新的)

true 表示刚创建

false 表示获取之前创建


每个会话都有一个身份证号。也就是 ID 值。而且这个 ID 是唯一的。

getId() 得到 Session 的会话 id 值


public class SessionServlet extends BaseServlet {    protected void createGetSession(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //获取和创建Session对象        HttpSession session = req.getSession();        //判断当前session会话,是否是新创建的        boolean aNew = session.isNew();        //获取session会话的唯一标识id        String id = session.getId();        resp.getWriter().write("得到的session,它的id是:" + id + "<br/>");        resp.getWriter().write("这个session是否是新创建的:" + aNew + "<br/>");    }    @Override    protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        super.doPost(req, resp);    }}

3.Session 域数据的存取

 protected void setAttribute(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //获取和创建Session对象        req.getSession().setAttribute("key1", "value1");    }    protected void getAttribute(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {        //获取和创建Session对象        Object key1 = req.getSession().getAttribute("key1");        resp.getWriter().write("从session获取的数据是:" + key1);    }

4.Session 生命周期控制

public void setMaxInactiveInterval(int interval) 设置 Session 的超时时间(以秒为单位),超过指定的时长,Session就会被销毁。

值为正数的时候,设定 Session 的超时时长。

负数表示永不超时(极少使用)

public int getMaxInactiveInterval()获取 Session 的超时时间

public void invalidate() 让当前 Session 会话马上超时无效

Session 默认的超时时长是多少!

Session 默认的超时时间长为 30 分钟。

因为在 Tomcat 服务器的配置文件 web.xml中默认有以下的配置,它就表示配置了当前 Tomcat 服务器下所有的 Session超时配置默认时长为:30 分钟。

30

如果说。你希望你的 web 工程,默认的 Session 的超时时长为其他时长。你可以在你自己的 web.xml 配置文件中做以上相同的配置。就可以修改你的 web 工程所有 Seession 的默认超时时长


[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gp78KSMC-1624636891080)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210413202038052.png)]

十三丶Filter过滤器

1.Filter 什么是过滤器

1、Filter 过滤器它是 JavaWeb 的三大组件之一。三大组件分别是:Servlet 程序、Listener 监听器、Filter 过滤器

2、Filter 过滤器它是 JavaEE 的规范。也就是接口

3、Filter 过滤器它的作用是:拦截请求,过滤响应。

拦截请求常见的应用场景有:

1、权限检查

2、日记操作

3、事务管理

……等等

2.Filter 的初体验

要求:在你的 web 工程下,有一个 admin 目录。这个 admin 目录下的所有资源(html 页面、jpg 图片、jsp 文件、等等)都必须是用户登录之后才允许访问。

思考:根据之前我们学过内容。我们知道,用户登录之后都会把用户登录的信息保存到 Session 域中。所以要检查用户是否登录,可以判断 Session 中否包含有用户登录的信息即可!!!

<%    Object user = session.getAttribute("user");    //如果为空说明还没登陆    if (user == null) {        request.getRequestDispatcher("/login.jsp").forward(request, response);        return;    }    %>

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-crwmzNKN-1624636891081)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210413204535379.png)]


/** * 专门用于拦截请求,过滤响应,可以做权限检查 * * @param servletRequest * @param servletResponse * @param filterChain * @throws IOException * @throws ServletException */@Overridepublic void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {    HttpServletRequest httpServletRequest = (HttpServletRequest) servletRequest;    HttpSession session = httpServletRequest.getSession();    Object user = session.getAttribute("user");    //如果为空说明还没登陆    if (user == null) {        servletRequest.getRequestDispatcher("/login.jsp").forward(servletRequest, servletResponse);        return;    } else {        //让程序继续往下访问用户的目标资源        filterChain.doFilter(servletRequest, servletResponse);    }}
<!--配置filter过滤器-->    <filter>        <!--起一个别名-->        <filter-name>AdminFilter</filter-name>        <!--配置filter的全类名-->        <filter-class>AdminFilter</filter-class>    </filter>    <!--配置拦截路径-->    <filter-mapping>        <filter-name>AdminFilter</filter-name>        <!--配置拦截路径-->        <url-pattern>/admin/*</url-pattern>    </filter-mapping>

Filter 过滤器的使用步骤:

1、编写一个类去实现 Filter 接口

2、实现过滤方法 doFilter()

3、到 web.xml 中去配置 Filter 的拦截路径

完整的用户登录


3.Filter的生命周期

Filter 的生命周期包含几个方法

1、构造器方法

2、init 初始化方法

第 1,2 步,在 web 工程启动的时候执行(Filter 已经创建)


3、doFilter 过滤方法

第 3 步,每次拦截到请求,就会执行


4、destroy 销毁

第 4 步,停止 web 工程的时候,就会执行(停止 web 工程,也会销毁 Filter 过滤器)


4.FilterConfig类

FilterConfig 类见名知义,它是 Filter 过滤器的配置文件类。

Tomcat 每次创建 Filter 的时候,也会同时创建一个 FilterConfig 类,这里包含了 Filter 配置文件的配置信息。

FilterConfig 类的作用是获取 filter 过滤器的配置内容

1、获取 Filter 的名称 filter-name 的内容

2、获取在 Filter 中配置的 init-param 初始化参数

3、获取 ServletContext 对象

5.FilterChain过滤链

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-KReGrACd-1624636891081)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210414185704919.png)]

6.Filter的拦截路径

精确匹配

<url-pattern>/target.jsp</url-pattern>

以上配置的路径,表示请求地址必须为:http://ip:port/工程路径/target.jsp


目录匹配

<url-pattern>/admin/*</url-pattern>

以上配置的路径,表示请求地址必须为:http://ip:port/工程路径/admin/*


后缀名匹配

<url-pattern>*.html</url-pattern>

以上配置的路径,表示请求地址必须以.html 结尾才会拦截到

<url-pattern>*.do</url-pattern>

以上配置的路径,表示请求地址必须以.do 结尾才会拦截到

<url-pattern>*.action</url-pattern>

以上配置的路径,表示请求地址必须以.action 结尾才会拦截到

Filter 过滤器它只关心请求的地址是否匹配,不关心请求的资源是否存在!!!

十四丶JSON AJAX I18N

1.什么是JSON?

JSON (JavaScript Object Notation) 是一种轻量级的数据交换格式。易于人阅读和编写。同时也易于机器解析和生成。JSON 采用完全独立于语言的文本格式,而且很多语言都提供了对 json 的支持(包括 C, C++, C#, Java, JavaScript, Perl, Python等)。 这样就使得 JSON 成为理想的数据交换格式。

json 是一种轻量级的数据交换格式。

轻量级指的是跟 xml 做比较。

数据交换指的是客户端和服务器之间业务数据的传递格式。

1.JSON JavaScript 中的使用

1.JSON的定义

json 是由键值对组成,并且由花括号(大括号)包围。每个键由引号引起来,键和值之间使用冒号进行分隔,多组键值对之间进行逗号进行分隔

// json的定义		var json = {			"key1": 12,			"key2": "abc",			"key3": "true",			"key4": [11, "aee", false],			"key5": {				"key5_1": 666,				"key5_2": "halo"			},			"key6": [{				"key6_1_1": 6661,				"key6_1_2": "hello",			}, {				"key6_1_1": 6662,				"key6_1_2": "hello2"			}			]		};
2.json的访问

json 本身是一个对象。

json 中的 key 我们可以理解为是对象中的一个属性。

json 中的 key 访问就跟访问对象的属性一样: json 对象.key

alert(typeof(jsonObj));// object json 就是一个对象 alert(jsonObj.key1); //12 alert(jsonObj.key2); // abc alert(jsonObj.key3); // truealert(jsonObj.key4);// 得到数组[11,"arr",false]// json 中 数组值的遍历for(var i = 0; i < jsonObj.key4.length; i++) { alert(jsonObj.key4[i]);                                              }alert(jsonObj.key5.key5_1);//551 alert(jsonObj.key5.key5_2);//key5_2_value alert( jsonObj.key6 );// 得到 json 数组 // 取出来每一个元素都是 json 对象 var jsonItem = jsonObj.key6[0]; // alert( jsonItem.key6_1_1 ); //6611 alert( jsonItem.key6_1_2 ); //key6_1_2_value
3.josn的两个常用方法

json 的存在有两种形式。

一种是:对象的形式存在,我们叫它 json 对象。

一种是:字符串的形式存在,我们叫它 json 字符串。

一般我们要操作 json 中的数据的时候,需要 json 对象的格式。

一般我们要在客户端和服务器之间进行数据交换的时候,使用 json 字符串。


JSON.stringify() 把 json 对象转换成为 json 字符串

JSON.parse() 把 json 字符串转换成为 json 对象

2.JOSN在java中的使用

1.javaBean json 的互转
/**     * 1.javaBean和json的互转     */    @Test    public void test() {        Person person = new Person(1, "陈文尧");        //创建gson对象实例        Gson gson = new Gson();        //toJson方法可以把java对象转换成为json字符串        String s = gson.toJson(person);        System.out.println(s);        /*        fromJson把json字符串转换为Java对象        第一个参数是json字符串        第二个参数是转换回去的Java对象类型         */        Person person1 = gson.fromJson(s, Person.class);        System.out.println(person1);    }
2.List和json的互转
/**     * List和json的互转     */    @Test    public void test2() {        List<Person> personList = new ArrayList<>();        Person person = new Person(2, "张佳伟");        personList.add(new Person(1, "陈文尧"));        personList.add(person);        Gson gson = new Gson();        //把list集合转化为json字符串        String toJson = gson.toJson(personList);        System.out.println(toJson);        List list = gson.fromJson(toJson, personList.getClass());        System.out.println(list);    }
3.map和json的互转
 /**     * map和json的互转     */    @Test    public void test3() {        Map<Integer, Person> map = new HashMap<>();        map.put(1, new Person(1, "陈文尧"));        map.put(2, new Person(2, "张家豪"));        Gson gson = new Gson();        String s = gson.toJson(map);        System.out.println(s);        }

2.AJAX请求

1.什么是AJAX请求?

AJAX 即“Asynchronous Javascript And XML”(异步 JavaScript 和 XML),是指一种创建交互式网页应用的网页开发

技术。

ajax 是一种浏览器通过 js 异步发起请求,局部更新页面的技术。

Ajax 请求的局部更新,浏览器地址栏不会发生变化

局部更新不会舍弃原来页面的内容

2.原生ajax请求的示例
function ajaxRequest() {// 				1、我们首先要创建XMLHttpRequest            var xmlhttprequest = new XMLHttpRequest();// 				2、调用open方法设置请求参数            xmlhttprequest.open("GET", "http://localhost:8080/16_json/ajaxServlet?action=javascriptAjax", true)            xmlhttprequest.onreadystatechange = function () {                if (xmlhttprequest.readyState == 4 && xmlhttprequest.status == 200) {                    var parse = JSON.parse(xmlhttprequest.responseText);                    document.getElementById("div01").innerHTML ="编号:"+parse.id+"姓名"+parse.name;                }            }            xmlhttprequest.send();        }
3.jquery中的ajax请求

$.ajax 方法

url 表示请求的地址

type 表示请求的类型 GET 或 POST 请求

data 表示发送给服务器的数据

格式有两种:

一:name=value&name=value

二:{key:value}

success 请求成功,响应的回调函数

dataType 响应的数据类型

常用的数据类型有:

text表示纯文本

xml 表示 xml 数据

json 表示 json 对象

$("#ajaxBtn").click(function(){     $.ajax({ url:"http://localhost:8080/16_json_ajax_i18n/ajaxServlet",            // data:"action=jQueryAjax",            data:{action:"jQueryAjax"},             type:"GET",             success:function (data) {                 // alert("服务器返回的数据是:" + data);                // var jsonObj = JSON.parse(data);                 $("#msg").html("编号:" + data.id + " , 姓名:" + data.name); },            dataType : "json"            }); });

. g e t 方 法 和 .get 方法和 .get.post 方法

url 请求的 url 地址

data 发送的数据

callback 成功的回调函数

type 返回的数据类型


// ajax--get 请求 $("#getBtn").click(function(){   $.get("http://localhost:8080/16_json_ajax_i18n/ajaxServlet","action=jQueryGet",function (data) {      $("#msg").html(" get 编号:" + data.id + " , 姓名:" + data.name);   },"json"); }); // ajax--post 请求 $("#postBtn").click(function(){ $.post("http://localhost:8080/16_json_ajax_i18n/ajaxServlet","action=jQueryPost",function (data) {     $("#msg").html(" post 编号:" + data.id + " , 姓名:" + data.name);},"json");                               });

$.getJSON 方法

url 请求的 url 地址

data 发送给服务器的数据

callback 成功的回调函数

// ajax--getJson 请求 $("#getJSONBtn").click(function(){ $.getJSON("http://localhost:8080/16_json_ajax_i18n/ajaxServlet","action=jQueryGetJSON",function (data) {     $("#msg").html(" getJSON 编号:" + data.id + " , 姓名:" + data.name); });                                 });

表单序列化 serialize()

serialize()可以把表单中所有表单项的内容都获取到,并以 name=value&name=value 的形式进行拼接

// ajax 请求 $("#submit").click(function(){     // 把参数序列化     $.getJSON("http://localhost:8080/16_json_ajax_i18n/ajaxServlet","action=jQuerySerialize&" + $("#form01").serialize(),function (data) {     $("#msg").html(" Serialize 编号:" + data.id + " , 姓名:" + data.name);     }); });

3.i18n国际化(了解内容)

1.什么是i18n国际化?

国际化(Internationalization)指的是同一个网站可以支持多种不同的语言,以方便不同国家,不同语种的用户访问。

关于国际化我们想到的最简单的方案就是为不同的国家创建不同的网站,比如苹果公司,他的英文官网是:http://www.apple.com 而中国官网是 http://www.apple.com/cn

苹果公司这种方案并不适合全部公司,而我们希望相同的一个网站,而不同人访问的时候可以根据用户所在的区域显示不同的语言文字,而网站的布局样式等不发生改变。

于是就有了我们说的国际化,国际化总的来说就是同一个网站不同国家的人来访问可以显示出不同的语言。但实际上这种需求并不强烈,一般真的有国际化需求的公司,主流采用的依然是苹果公司的那种方案,为不同的国家创建不同的页面。所以国际化的内容我们了解一下即可。

国际化的英文 Internationalization,但是由于拼写过长,老外想了一个简单的写法叫做 I18N,代表的是 Internationalization这个单词,以 I 开头,以 N 结尾,而中间是 18 个字母,所以简写为 I18N。以后我们说 I18N 和国际化是一个意思


2.国际化相关要素介绍

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-prR1BClC-1624636891082)(C:\Users\ZJH\AppData\Roaming\Typora\typora-user-images\image-20210415201012161.png)]

3.国际化资源properties测试

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值