JavaWeb核心(下)

JavaWeb核心(下)

EL和JSTL核心技术

EL表达式(熟悉)

基本概念

​ EL(Expression Language)表达式提供了在JSP中简化表达式的方法,可以方便地访问各种数据并输出

主要功能

依次访问pageContext、request、session和application作用域对象存储的数据

获取请求参数值

访问Bean对象的属性

访问集合中的数据

输出简单的运算结果

访问内置对象的数据
1、访问方式

<%=request.getAttribute(“ varName”)%>

用EL实现: ${ varName }

2、执行流程

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pRfFfOeb-1624432057317)(E:\MarkDown\拉勾笔记\EL执行流程)]

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现从内置对象中获取数据并打印</title>
</head>
<body>
<%
    /*pageContext.setAttribute("name1","pageContext对象中的属性值:zhangfei");
    request.setAttribute("name2","request对象中的属性值:guanyu");
    session.setAttribute("name3","session对象中的属性值:liubei");
    application.setAttribute("name4","session对象中的属性值:zhaoyun");*/
    /*pageContext.setAttribute("name","pageContext对象中的属性值:zhangfei");*/
    request.setAttribute("name","request对象中的属性值:guanyu");
    session.setAttribute("name","session对象中的属性值:liubei");
    application.setAttribute("name","session对象中的属性值:zhaoyun");
%>

<%-- 使用JSP中原始方式获取数据 --%>
<%--<%= "name1的数值为:" + pageContext.getAttribute("name1")%><br/>  &lt;%&ndash; zhangfei &ndash;%&gt;
<%= "name2的数值为:" + request.getAttribute("name2")%><br/>      &lt;%&ndash; guanyu &ndash;%&gt;
<%= "name3的数值为:" + session.getAttribute("name3")%><br/>      &lt;%&ndash; liubei &ndash;%&gt;
<%= "name4的数值为:" + application.getAttribute("name4")%><br/>  &lt;%&ndash; zhaoyun &ndash;%&gt;--%>

<%-- 使用EL表达式实现获取数据和打印 --%>
<%--<h1>name1的数值为:${name1}</h1><br/>
name2的数值为:${name2}<br/>
name3的数值为:${name3}<br/>
name4的数值为:${name4}<br/>--%>
    
<h3>name的数值为:${name}</h3><br/>

</body>
</html>
访问请求参数的数据

1、在EL之前使用下列方式访问请求参数的数据

​ request.getParameter(name);

​ request.getParameterValues(name);

2、在EL中使用下列方式访问请求参数的数据

​ param:接收的参数只有一个值

​ paramValues:接受的参数有多个值

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现一个简单页面负责向JSP传递参数</title>
</head>
<body>
<form action="el_param.jsp" method="post">
    姓名:<input type="text" name="name"><br/>
    爱好:<input type="checkbox" name="hobby" value="唱歌">唱歌<br/>
          <input type="checkbox" name="hobby" value="跳舞">跳舞<br/>
          <input type="checkbox" name="hobby" value="学习">学习<br/>
          <input type="submit" value="提交"><br/>
</form>
</body>
</html>


<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现请求参数数值的获取</title>
</head>
<body>
<%
    request.setCharacterEncoding("utf-8");
%>

<%-- 使用JSP语法中的原始方式获取请求参数值 --%>
<%--<%= "姓名是:" + request.getParameter("name") %><br/>
<%= "爱好是:" + request.getParameter("hobby") %><br/>--%>

<%-- 使用EL表达式中的方式获取请求参数值 --%>
姓名是:${param.name}<br/>
爱好是:${paramValues.hobby[0]}<br/>
</body>
</html>
访问Bean对象的属性
1、访问方式

方式一: $ { 对象名 . 属性名 },例如:${user.name}

方式二: $ { 对象名 [“属性名”] },例如:${user[“name”]}

2、主要区别

1、当要存取的属性名中包含一些特殊字符,如: . 或 ,等并非字母或数字的符号,就一定要使用 [ ]而不是.的方式

2、使用[]的方式可以动态取值

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现Bean对象中属性的获取和打印</title>
</head>
<body>
<%-- 使用JSP语法规则中的原始方式实现对象的创建和设置以及输出 --%>
<%
    Person person = new Person();
    person.setName("zhangfei");
    person.setAge(30);
    pageContext.setAttribute("person",person);

    pageContext.setAttribute("var1","name");
    pageContext.setAttribute("var2","age");
%>

<%--<%= "获取到的姓名为:" + person.getName() %><br/>
<%= "获取到的年龄为:" + person.getAge() %><br/>--%>

<%-- 使用EL表达式实现属性的获取和打印 --%>
获取到的姓名是:${person.name}<br/>
获取到的年龄是:${person.age}<br/>
<br/>

<%-- 另外一种写法 --%>
${person["name"]}<br/>
${person["age"]}<br/>

<br/>
<%-- 测试一下动态取值的效果 --%>
动态取值的结果为:${person[var1]}    <%-- zhangfei 30--%>
</body>
</html>
访问集合中的数据
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现集合中数据内容的获取和打印</title>
</head>
<body>
<%
    // 准备一个List集合并添加数据内容
    List<String> list = new LinkedList<>();
    list.add("two");
    list.add("one");
    list.add("three");
    // 将整个集合放入指定的内置对象中
    pageContext.setAttribute("list",list);

    // 准备一个Map集合并添加数据
    Map<String,Integer> map = new HashMap<>();
    map.put("one",1);
    map.put("two",2);
    map.put("th.ree",3);
    // 将整个集合放入指定的内置对象中
    pageContext.setAttribute("map",map);

%>

<%-- 使用EL表达式实现集合中数据内容的获取 --%>
集合中下标为0的元素是:${list[0]}<br/>     <%-- two --%>
集合中下标为1的元素是:${list[1]}<br/>     <%-- one --%>
集合中下标为2的元素是:${list[2]}<br/>     <%-- three --%>
<hr/>
<%-- 使用EL表达式实现Map集合中数据内容的获取 不支持下标 --%>
整个Map集合中的元素有:${map}<br/>
获取带有特殊字符key对应的数值为:${map["th.ree"]}<br/>     <%-- 3 --%>

</body>
</html>
常用的内置对象
类别标识符描述
JSPpageContextPageContext 处理当前页面
作用域pageScope同页面作用域属性名称和值有关的Map类
requestScope同请求作用域属性的名称和值有关的Map类
sessionScope同会话作用域属性的名称和值有关的Map类
applicationScope同应用程序作用域属性的名称和值有关的Map类
请求参数param根据名称存储请求参数的值的Map类
paramValues把请求参数的所有值作为一个String数组来存储的Map类
请求头header根据名称存储请求头主要值的Map类
headerValues把请求头的所有值作为一个String数组来存储的Map类
Cookiecookie根据名称存储请求附带的cookie的Map类
初始化参数initParam根据名称存储Web应用程序上下文初始化参数的Map类
常用的运算符
1、算术运算符
算术运算符说明范例运算结果
+${1+2}3
-${2-1}1
*${2*3}6
/或div 16 / 5 或 {16/5}或 16/5{16div5}3.2
% 或 mod取余KaTeX parse error: Expected '}', got 'EOF' at end of input: {16%5}或{16mod5}1
2、关系运算符
关系运算符说明范例运算结果
==或eq等于 1 = = 2 或 {1==2}或 1==2{1 eq 2}false
!= 或ne不等于 2 ! = 1 或 {2!=1}或 2!=1{1 ne 2}true
< 或lt小于 2 < 3 或 {2<3}或 2<3{2 lt 3 }true
> 或 gt大于 16 > 5 或 {16>5}或 16>5{16 gt 5}true
<= 或 le小于等于 16 < = 5 或 {16<=5}或 16<=5{16 le 5}false
>= 或 ge大于等于 16 > = 5 或 {16>=5}或 16>=5{16 ge 5}true
3、逻辑运算符
逻辑运算符说明范例运算结果
&& 或 and与运算KaTeX parse error: Expected '}', got '&' at position 6: {true&̲&true}或{true and true}true
| | 或or或运算${true | | false} 或 ${true or false}true
! 或not非运算 ! t r u e 或 {!true}或 !true{not true }false
4、条件运算符
${条件表达式? 语句1 : 语句2}
5、验证运算符
${empty 表达式}
返回布尔值判断表达式是否为"空"值,null值、无元素的集合或数组、长度为零的String被认为是空值
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现常用运算符的使用</title>
</head>
<body>
<%
    // 通过内置对象设置属性的方式来准备操作数
    request.setAttribute("ia",5);
    request.setAttribute("ib",2);
    request.setAttribute("b1",true);
    request.setAttribute("b2",false);
%>

<%-- 实现上述所有操作数的获取和打印 --%>
ia的数值为:${ia}<br/>   <%-- 5 --%>
ib的数值为:${ib}<br/>   <%-- 2 --%>
b1的数值为:${b1}<br/>   <%-- true --%>
b2的数值为:${b2}<br/>   <%-- false --%>
<hr/>

<%-- 实现算术运算符的使用 --%>
ia+ib的结果为:${ia+ib}<br/>     <%-- 7 --%>
ia-ib的结果为:${ia-ib}<br/>     <%-- 3 --%>
ia*ib的结果为:${ia*ib}<br/>     <%-- 10 --%>
ia/ib的结果为:${ia/ib}<br/>     <%-- 2.5 --%>
ia%ib的结果为:${ia%ib}<br/>     <%-- 1 --%>
<hr/>

<%-- 实现关系运算符的使用 --%>
ia大于ib的结果为:${ia > ib}<br/>          <%-- true --%>
ia大于等于ib的结果为:${ia >= ib}<br/>     <%-- true --%>
ia小于ib的结果为:${ia < ib}<br/>          <%-- false --%>
ia小于等于ib的结果为:${ia <= ib}<br/>     <%-- false --%>
ia等于ib的结果为:${ia == ib}<br/>         <%-- false --%>
ia大于ib的结果为:${ia != ib}<br/>         <%-- true --%>
<hr/>

<%-- 实现逻辑运算符的使用 --%>
b1并且b2的结果为:${b1 && b2}<br/>      <%-- false --%>
b1或者b2的结果为:${b1 || b2}<br/>      <%-- true --%>
b1取反的结果为:${!b1}<br/>             <%-- false --%>
b2取反的结果为:${!b2}<br/>             <%-- true --%>
<hr/>


<%
    String str1 = null;
    String str2 = "";
    String str3 = "hello";

    List<Integer> list1 = new LinkedList<>();
    List<Integer> list2 = Arrays.asList(11,22,33,44,55);

    request.setAttribute("str1",str1);
    request.setAttribute("str2",str2);
    request.setAttribute("str3",str3);
    request.setAttribute("list1",list1);
    request.setAttribute("list2",list2);
%>
<%-- 实现条件运算符和验证运算符的使用 --%>
ia和ib之间最大的是:${ ia>ib? ia : ib}<br/>
判断是否为空的结果是:${empty str1}<br/>       <%-- true --%>
判断是否为空的结果是:${empty str2}<br/>       <%-- true --%>
判断是否为空的结果是:${empty str3}<br/>       <%-- false --%>
判断是否为空的结果是:${empty list1}<br/>       <%-- true --%>
判断是否为空的结果是:${empty list2}<br/>       <%-- false --%>

</body>
</html>

JSTL标签(熟悉)

基本概念

JSTL( JSP Standard Tag Library ) 被称为JSP标准标签库

开发人员可以利用这些标签取代JSP页面上的Java代码,从而提高程序的可读性,降低程序的维护难度

使用方式

下载JSTL的jar包并添加到项目中

JSTLE下载地址:https://tomcat.apache.org/download-taglibs.cgi

在JSP页面中使用taglib指定引入jstl标签库,方式为:

<!-- prefix属性用于指定库前缀 -->
<!-- uri属性用于指定库的标识 -->
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
常用核心标签

1、输出标签

<c:out></c:out> 用来将指定内容输出的标签


<html>
<head>
    <title>实现out输出标签的使用</title>
</head>
<body>
<c:out value="Hello world"></c:out>
</body>
</html>

2、设置标签

<c:set></c:set> 用来设置属性范围值的标签


<html>
<head>
    <title>实现set标签的使用</title>
</head>
<body>
<%-- 表示设置一个名字为name的属性,对应的数值为zhangfei,有效范围为当前页面 --%>
<%-- pageContext.setAttribute("name","zahngfei"); --%>
<c:set var="name" value="zhangfei" scope="page"></c:set>
<%-- 使用out标签打印出来 --%>
<c:out value="${name}"></c:out>
<hr/>

<%-- 设置一个对象的属性值并打印出来 --%>
<jsp:useBean id="person" class="com.wei.demo01.Person" scope="page"></jsp:useBean>
<c:set property="name" value="关羽" target="${person}"></c:set>
<c:set property="age" value="35" target="${person}"></c:set>
<%-- 打印 --%>
<c:out value="${person.name}"></c:out>
<c:out value="${person.age}"></c:out>

</body>
</html>

3、删除标签

<c:remove></c:remove> 用来删除指定数据的标签


<html>
<head>
    <title>实现remove标签的使用</title>
</head>
<body>
<%-- 设置一个属性值并打印 --%>
<c:set var="name" value="liubei" scope="page"></c:set>
<c:out value="${name}"></c:out>
<hr/>

<%-- 删除这个属性值后在此处打印 --%>
<c:remove var="name" scope="page"></c:remove>
<c:out value="${name}" default="无名"></c:out>

</body>
</html>

4、单条件判断标签

<c:if test =“EL条件表达式”>
	满足条件执行
</c:if >


<html>
<head>
    <title>实现if标签的使用</title>
</head>
<body>
<%-- 设置一个变量以及对应的数值 --%>
<c:set var="age" value="17" scope="page"></c:set>
<c:out value="${age}"></c:out>
<hr/>

<%-- 判断该年龄是否成年,若成年则提示已成年了 --%>
<c:if test="${age >= 18}">
    <c:out value="已经成年了!"></c:out>
</c:if>

</body>
</html>

5、多条件判断标签

<c:choose >
    <c:when test =“EL表达式”>
    	满足条件执行
      </c:when>
    	…
    <c:otherwise>
    	不满足上述when条件时执行
    </c:otherwise>
</c:choose >


<html>
<head>
    <title>实现choose标签的使用</title>
</head>
<body>
<%-- 设置一个变量代表考试的成绩并指定数值 --%>
<c:set var="score" value="59" scope="page"></c:set>
<c:out value="${score}"></c:out>
<hr/>

<%-- 进行多条件判断和处理 --%>
<c:choose>
    <c:when test="${score > 60}">
        <c:out value="成绩不错,继续加油喔!"></c:out>
    </c:when>
    <c:when test="${score == 60}">
        <s:out value="60分万岁,多一分浪费"></s:out>
    </c:when>
    <c:otherwise>
        <c:out value="革命尚未成功,同志仍需努力!"></c:out>
    </c:otherwise>
</c:choose>

</body>
</html>

6、循环标签

<c:forEach var=“循环变量” items=“集合”>
…
</c:forEach>


<html>
<head>
    <title>实现循环标签的使用</title>
</head>
<body>
<%
    // 准备一个数组并初始化
    String sArr[] = {"11","22","33","44","55"};
    pageContext.setAttribute("sArr",sArr);
%>

<%-- 使用循环标签遍历数组中的所有元素 --%>
<c:forEach var="ts" items="${sArr}">
    <c:out value="${ts}"></c:out>
</c:forEach>
<hr/>

<%-- 跳跃性遍历  间隔为2 也就是跳过一个遍历一个 --%>
<c:forEach var="ts" items="${sArr}" step="2">
    <c:out value="${ts}"></c:out>
</c:forEach>
<hr/>

<%-- 指定起始和结尾位置  从下标1开始到3结束,包含1和3 --%>
<c:forEach var="ts" items="${sArr}" begin="1" end="3">
    <c:out value="${ts}"></c:out>
</c:forEach>

</body>
</html>
常用函数标签
<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %>

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现常用函数标签的使用</title>
</head>
<body>
<%
    pageContext.setAttribute("var","Hello world!");
%>
原始字符串为:${var}<br/>  <%-- Hello World! --%>
判断该字符串是否包含指定字符串的结果为:${fn:contains(var,"Hello")}<br/>     <%-- true --%>
将字符串中所有字符转换为大写的结果为:${fn:toUpperCase(var)}<br/>            <%-- HELLO WORLD! --%>
将字符串中所有字符转换为小写的结果为:${fn:toLowerCase(var)}<br/>            <%-- hello world! --%>

</body>
</html>
常用格式化标签
<%@ taglib prefix="fmt" uri="http://java.sun.com/jsp/jstl/fmt" %>


<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现格式化标签的使用</title>
</head>
<body>
<%
    // 获取当前系统时间
    Date date = new Date();
    pageContext.setAttribute("date",date);
%>

当前系统时间为:${date}<br/>
<hr/>

<fmt:formatDate value="${date}" pattern="yyyy-MM-dd HH:mm:ss"></fmt:formatDate>

</body>
</html>
自定义标签

如果上面几个标签不能满足需求,程序员也可以自定义标签,步骤如下:

1、编写标签类继承SimpleTagSupport类或TagSupport类并重写doTag方法或doStartTag方法

/**
 * @auther weiwei
 * @date 2021/6/16 15:25
 * @description     自定义标签类
 */
public class HelloTag extends SimpleTagSupport {

    private String name;

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public void doTag() throws JspException, IOException {
        // 获取输出流
        JspWriter out = this.getJspContext().getOut();
        // 写入数据到浏览器
        out.write("自定义标签哦!" + name);
        // 关闭流对象
        out.close();
    }
}

2、定义标签库文件(tld标签库文件)并配置标签说明文件到到WEB-INF下:

<?xml version="1.0" encoding="ISO-8859-1"?>

<taglib xmlns="http://java.sun.com/xml/ns/javaee"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
        xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-jsptaglibrary_2_1.xsd"
        version="2.1">

    <tlib-version>1.0</tlib-version>
    <short-name>my</short-name>
    <uri>http://wei.com</uri>

    <!-- Invoke 'Generate' action to add tags or functions -->
    <tag>
        <name>hello</name>
        <tag-class>com.wei.demo01.HelloTag</tag-class>
        <body-content>empty</body-content>
        
        <attribute>
            <name>name</name>
            <required>true</required>
        </attribute>
    </tag>
    
</taglib>

3、在JSP中添加taglib指令引入标签库使用:

<%@ taglib prefix="my" uri="http://wei.com" %>
<%--
  Created by IntelliJ IDEA.
--%>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现自定义标签的使用</title>
</head>
<body>

<my:hello name="zhangfei"/>

</body>
</html>

小结

EL表达式的概念

主要功能

常用内置对象

常用运算符

JSTL基本概念

使用方法

常用核心标签

函数标签

格式化标签

Filter+Listener核心技术

Filter过滤器(重点)

基本概念

1、Filter本意为”过滤“,是JavaWeb的三大组件之一,三大组件为:Servlet、Filter、Listener

2、过滤器是向Web应用程序的请求和响应处理添加功能的 Web 服务组件

3、过滤器相当于浏览器与Web资源之间的一道过滤网,在访问资源之前通过一系列的过滤器对请求进行修改、判断以及拦截等,也可以对响应进行修改、判断以及拦截等

工作方式

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-HixrnEIP-1624432057328)(E:\MarkDown\拉勾笔记\Filter过滤器工作方式)]

使用方式

1、自定义类实现Filter接口并重写doFilter方法

@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {
    // 1.实现对用户访问主页面的过滤操作,也就是只有用户登录后才能访问主页面,否则一律拦截
    // 判断session中有没有用户名信息,若没有则进行拦截,否则放行
    HttpServletRequest httpServletRequest = (HttpServletRequest)servletRequest;
    HttpSession session = httpServletRequest.getSession();
    Object username = session.getAttribute("username");
    // 获取Servlet的请求路径
    String servletPath = httpServletRequest.getServletPath();

    // 若没有登录,则回到登录界面
    if (null == username && !servletPath.contains("login")){
        servletRequest.getRequestDispatcher("login.jsp").forward(servletRequest, servletResponse);
    } else {
        // TODO 处理逻辑,必须调用下面的方法
        // 若已经登录,则放行
        filterChain.doFilter(servletRequest, servletResponse);
    }
}

2、在web.xml文件中配置过滤器

<filter>
    <filter-name>LoginFilter</filter-name>
    <filter-class>com.wei.demo01.LoginFilter</filter-class>
</filter>
<filter-mapping>
    <filter-name>LoginFilter</filter-name>
    <url-pattern>/main.jsp</url-pattern>
</filter-mapping>
Filter接口
基本概念

javax.servlet.Filter接口主要用于描述过滤器对象,可对资源的请求和响应操作进行筛选操作

常用方法
方法声明功能介绍
void init(FilterConfig filterConfig)实现过滤器的初始化操作
void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)执行过滤操作的功能
void destroy()实现过滤器的销毁操作
FilterConfig接口
基本概念

javax.servlet.FilterConfig接口主要用于描述过滤器的配置信息

常用方法
方法声明功能介绍
String getFilterName()获取过滤器的名字
String getInitParameter(String name)获取指定的初始化参数信息
Enumeration getInitParameterNames()获取所有的初始化操作名称
ServletContext getServletContext()获取ServletContext对象
多个过滤器的使用

如果多个过滤器都满足过滤条件,则容器依据映射的先后顺序来调用各个过滤器

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-roYPfXor-1624432057332)(E:\MarkDown\拉勾笔记\多个过滤器的使用)]

过滤器优点

1、实现代码的“可插拔性”,即增加或减少某个功能模块,不会影响程序正常执行

2、可以将多个相同处理逻辑的模块集中写在过滤器里面,可实现重复利用、也方便代码的维护

Listener监听器(重点)

基本概念

1、Servlet规范中定义的一种特殊的组件,用来监听Servlet容器产生的事件并进行相应的处理

2、容器产生的事件分类如下:

​ 生命周期相关的事件

​ 属性状态相关的事件

​ 存值状态相关的事件

3、底层原理是采用接口回调的方式实现

基本分类
监听器类型功能介绍
javax.servlet.ServletRequestListener监听request作用域的创建和销毁
javax.servlet.ServletRequestAttributeListener监听request作用域的属性状态变化
javax.servlet.http.HttpSessionListener监听session作用域的创建和销毁
javax.servlet.http.HttpSessionAttributeListener监听session作用域的属性状态变化
javax.servlet.ServletContextListener监听application作用域的创建和销毁
javax.servlet.ServletContextAttributeListener监听application作用域的属性状态变化
javax.servlet.http.HttpSessionBindingListener监听对象与session的绑定和解除
javax.servlet.http.HttpSessionActivationListener监听session数值的钝化和活化
监听器详解
1、ServletRequestListener监听器

在ServletRequest创建和关闭时都会通知ServletRequestListener监听器

方法声明功能介绍
void requestInitialized(ServletRequestEvent sre)实现ServletRequest对象的初始化
void requestDestroyed(ServletRequestEvent sre)实现ServletRequest对象的销毁
public class MyRequestListener implements ServletRequestListener {
    @Override
    public void requestDestroyed(ServletRequestEvent servletRequestEvent) {
        System.out.println("请求销毁了...");
    }

    @Override
    public void requestInitialized(ServletRequestEvent servletRequestEvent) {
        System.out.println("创建请求...");
    }
}
<listener>
    <listener-class>com.wei.demo03.MyRequestListener</listener-class>
</listener>
2、ServletRequestAttributeListener监听器

向ServletRequest添加、删除或者替换一个属性的时候,将会通知ServletRequestAttributeListener监听器

方法声明功能介绍
void attributeAdded(ServletRequestAttributeEvent srae)增加属性时触发
void attributeReplaced(ServletRequestAttributeEvent srae)修改属性时触发
void attributeRemoved(ServletRequestAttributeEvent srae)删除属性时触发
<html>
<head>
    <title>实现请求中属性状态的改变</title>
</head>
<body>
<%
    // 实现属性的添加
    request.setAttribute("name","zhangfei");
    // 实现属性的修改
    request.setAttribute("name","guanyu");
    // 实现属性的删除操作
    request.removeAttribute("name");
%>
</body>
</html>
public class MyRequestAttributeListener implements ServletRequestAttributeListener {
    @Override
    public void attributeAdded(ServletRequestAttributeEvent servletRequestAttributeEvent) {
        System.out.println("增加了属性" + servletRequestAttributeEvent.getName());
    }

    @Override
    public void attributeRemoved(ServletRequestAttributeEvent servletRequestAttributeEvent) {
        System.out.println("属性" + servletRequestAttributeEvent.getName() + "被删除了");
    }

    @Override
    public void attributeReplaced(ServletRequestAttributeEvent servletRequestAttributeEvent) {
        System.out.println("修改属性" + servletRequestAttributeEvent.getName());
    }
}
<listener>
    <listener-class>com.wei.demo03.MyRequestAttributeListener</listener-class>
</listener>
3、HttpSessionListener监听器

当一个HttpSession刚被创建或者失效(invalidate)的时候,将会通知HttpSessionListener监听器

方法声明功能介绍
void sessionCreated(HttpSessionEvent se)当一个HttpSession对象被创建时会调用这个方法
void sessionDestroyed(HttpSessionEvent se)当一个HttpSession超时或者调用HttpSession的invalidate()方法让它销毁时,将会调用这个方法
public class MySessionListener implements HttpSessionListener {
    @Override
    public void sessionCreated(HttpSessionEvent httpSessionEvent) {
        System.out.println("创建了session...");
    }

    @Override
    public void sessionDestroyed(HttpSessionEvent httpSessionEvent) {
        System.out.println("session销毁!");
    }
}
<listener>
    <listener-class>com.wei.demo03.MySessionListener</listener-class>
</listener>

<session-config>
    <session-timeout>3</session-timeout>
</session-config>
4、HttpSessionAttributeListener监听器

HttpSession中添加、删除或者替换一个属性的时候,将会通知HttpSessionAttributeListener监听器

方法声明功能介绍
void attributeAdded(HttpSessionBindingEvent se)当往会话中加入一个属性的时候会调用这个方法
void attributeRemoved(HttpSessionBindingEvent se)当从会话中删除一个属性的时候会调用这个方法
void attributeReplaced(HttpSessionBindingEvent se)当改变会话中的属性的时候会调用这个方法
<html>
<head>
    <title>实现会话中属性状态的改变</title>
</head>
<body>
<%
    // 增加属性
    session.setAttribute("name","caocao");
    // 修改属性
    session.setAttribute("name","caoren");
    // 删除属性
    session.removeAttribute("name");
%>
</body>
</html>
public class MySessionAttributeListener implements HttpSessionAttributeListener {
    @Override
    public void attributeAdded(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("增加了属性" + httpSessionBindingEvent.getName());
    }

    @Override
    public void attributeRemoved(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("属性" + httpSessionBindingEvent.getName() + "被删除!");
    }

    @Override
    public void attributeReplaced(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("修改属性" + httpSessionBindingEvent.getName());
    }
}
<listener>
    <listener-class>com.wei.demo03.MySessionAttributeListener</listener-class>
</listener>
5、ServletContextListener监听器

在ServletContext创建和关闭时都会通知ServletContextListener监听器

方法声明功能介绍
void contextInitialized(ServletContextEvent sce)当ServletContext创建的时候,将会调用这个方法
void contextDestroyed(ServletContextEvent sce)当ServletContext销毁的时候(例如关闭应用服务器或者重新加载应用),将会调用这个方法
public class MyContextListener implements ServletContextListener {
    @Override
    public void contextInitialized(ServletContextEvent servletContextEvent) {
        System.out.println("ServletContext对象创建了...");
    }

    @Override
    public void contextDestroyed(ServletContextEvent servletContextEvent) {
        System.out.println("销毁ServletContext对象...");
    }
}
<listener>
    <listener-class>com.wei.demo03.MyContextListener</listener-class>
</listener>
6、ServletContextAttributeListener监听器

向ServletContext添加、删除或者替换一个属性的时候,将会通知ServletContextAttributesListener监听器

方法声明功能介绍
void attributeAdded(ServletContextAttributeEvent scae)往ServletContext中加入一个属性的时候触发
void attributeRemoved(ServletContextAttributeEvent scae)从ServletContext中删除一个属性的时候触发
void attributeReplaced(ServletContextAttributeEvent scae)改变ServletContext中属性的时候触发
<html>
<head>
    <title>实现ServletContext对象属性的改变</title>
</head>
<body>
<%
    // 添加属性
    application.setAttribute("name","sunquan");
    // 修改属性
    application.setAttribute("name","zhouyu");
    // 删除属性
    application.removeAttribute("name");
%>
</body>
</html>
public class MyContextAttributeListener implements ServletContextAttributeListener {
    @Override
    public void attributeAdded(ServletContextAttributeEvent servletContextAttributeEvent) {
        System.out.println("增加了属性" + servletContextAttributeEvent.getName());
    }

    @Override
    public void attributeRemoved(ServletContextAttributeEvent servletContextAttributeEvent) {
        System.out.println("属性" + servletContextAttributeEvent.getName() + "被删除!");
    }

    @Override
    public void attributeReplaced(ServletContextAttributeEvent servletContextAttributeEvent) {
        System.out.println("修改属性" + servletContextAttributeEvent.getName());
    }
}
<listener>
    <listener-class>com.wei.demo03.MyContextAttributeListener</listener-class>
</listener>
7、HttpSessionBindingListener监听器

HttpSession中绑定和解除绑定时,将会通知HttpSessionListener监听器

方法声明功能介绍
void valueBound(HttpSessionBindingEvent event)有对象绑定时调用该方法
void valueUnbound(HttpSessionBindingEvent event)有对象解除绑定时调用该方法
<html>
<head>
    <title>实现session中对象的绑定和解除</title>
</head>
<body>
<%
    // 准备一个Person类型的对象
    Person person = new Person();
    person.setName("zhangfei");
    person.setAge(30);
    // 将对象与session对象进行绑定
    session.setAttribute("person",person);
    // 解除绑定
    session.removeAttribute("person");
%>
</body>
</html>
public class Person implements HttpSessionBindingListener {
    private String name;
    private int age;

    public Person() {
    }

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
    }

    @Override
    public void valueBound(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("对象绑定到session中了" + httpSessionBindingEvent.getName());
    }

    @Override
    public void valueUnbound(HttpSessionBindingEvent httpSessionBindingEvent) {
        System.out.println("解除绑定成功!");
    }
}
8、HttpSessionActivationListener监听器

当有session数值的钝化和活化操作时,将会通知HttpSessionActivationListener监听器

方法声明功能介绍
void sessionWillPassivate(HttpSessionEvent se)有钝化操作时调用该方法
void sessionDidActivate(HttpSessionEvent se)有活化操作时调用该方法
<html>
<head>
    <title>实现session中数据的钝化和活化</title>
</head>
<body>
<%
    // 创建Student类型的对象
    Student student = new Student();
    student.setName("zhangfei");
    // 将数据放入到session中
    session.setAttribute("student",student);
%>
</body>
</html>
<html>
<head>
    <title>实现session中数据的获取</title>
</head>
<body>
<%
    Object student = session.getAttribute("student");
    System.out.println("获取到的数据为:" + student);
%>
</body>
</html>
public class Student implements Serializable, HttpSessionActivationListener {
    private String name;

    public Student() {
    }

    public Student(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Override
    public String toString() {
        return "Student{" +
                "name='" + name + '\'' +
                '}';
    }

    @Override
    public void sessionWillPassivate(HttpSessionEvent httpSessionEvent) {
        System.out.println("执行了钝化操作..." + httpSessionEvent.getSession());
    }

    @Override
    public void sessionDidActivate(HttpSessionEvent httpSessionEvent) {
        System.out.println("活化操作进行中...");
    }
}

配置context.xml文件的方式如下:

<Manager className="org.apache.catalina.session.PersistentManager" saveOnRestart="true">
    <!-- 配置文件存放的路径信息,可以自由指定 -->
    <Store className="org.apache.catalina.session.FileStore" directory="C:\session"/>
</Manager>
实战案例

自定义类实现监听器接口并重写相关方法

public class OnlineUser implements HttpSessionListener, ServletContextListener {
    // 声明一个ServletContext类型的引用负责作为全局对象来记录当前在线用户的数量,通过属性记录
    ServletContext servletContext = null;

    @Override
    public void contextInitialized(ServletContextEvent servletContextEvent) {
        servletContext = servletContextEvent.getServletContext();
    }

    @Override
    public void contextDestroyed(ServletContextEvent servletContextEvent) {
        servletContext = null;
    }

    @Override
    public void sessionCreated(HttpSessionEvent httpSessionEvent) {
        System.out.println("有新用户上线了...");
        Object count = servletContext.getAttribute("count");
        // 若当前用户为第一个用户,则将全局对象中的属性设置为1即可
        if (null == count){
            servletContext.setAttribute("count",1);
        }
        // 若当前用户不是第一个用户,则将全局对象中原有的数据取出来加1后在设置进去
        else {
            Integer integer = (Integer)count;
            integer++;
            servletContext.setAttribute("count",integer);
        }
        System.out.println("当前在线用户数量为:" + servletContext.getAttribute("count"));
    }

    @Override
    public void sessionDestroyed(HttpSessionEvent httpSessionEvent) {
        System.out.println("有用户已下线...");
    }
}

html

<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
    <title>实现当前在线的用户数量</title>
</head>
<body>
<h1>当前在线用户人数为:${applicationScope.count}</h1>
</body>
</html>

在web.xml中配置监听器

<listener>
    <listener-class>com.wei.demo04.OnlineUser</listener-class>
</listener>

小结

1、Filter过滤器

基本概念、工作方式、使用方式、Filter接口、FilterConfig接口、多个过滤器的使用、优点

2、Listener监听器

基本概念、基本分类、案例

Linux系统概述和编程基础

Linux系统概述(常识)

计算机的体系结构

计算机由计算机硬件和计算机软件两个部分组成,其中计算机软件(Computer Software)可分为系统软件和应用软件,系统软件就是操作系统,是其他软件的基础

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-7K4xzfel-1624432057338)(E:\MarkDown\拉勾笔记\计算机体系结构)]

目前主流的操作系统有:Windows系列、Unix系列、Linux系列、Android系列、IOS系列、…

Linux系统的概述

1、Linux系统诞生于1991年,在林纳斯·托瓦兹(Linus Torvalds)上大学期间因不满意教学中使用的MINIX操作系统并出于个人爱好设计和研发的。

2、Linux系统是一套免费、自由、开发源代码的类Unix操作系统,是一个基于Posix(Portable Operating System Interface)标准和多用户、多任务、支持多线程的操作系统。

3、Linux能运行主要的Unix工具软件、应用程序和网络协议,支持32位和64位硬件

主要发行版本

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-G09Wl7Wb-1624432057340)(E:\MarkDown\拉勾笔记\Linux主要发行版本)]

1、Redhat:目前最大的Linux发行商,功能全面并且稳定,于2018年10月被IBM以340亿美元的价格收购。

2、Ubuntu:目前最好的Linux桌面版,拥有很人性化的亮丽的交互界面,强大的软件源支持

3、CentOS:是RHEL的克隆版本,可以认为是免费版本的Redhat系统

CentOS系统安装(掌握)

Vmware的下载和安装

下载地址:https://www.vmware.com/cn.html

按照安装教程一步步操作即可

CentOS系统的下载和安装

下载地址:https://www.centos.org/

按照安装教程通过Vmware软件进行CentOS系统的安装

目录结构(熟悉)

框架结构

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-H1AhfZnW-1624432057342)(E:\MarkDown\拉勾笔记\Linux框架结构)]

目录详解
目录名称功能介绍
/binbinarie:存放二进制可执行文件 (例如tomcat的bin目录)
/sbinsuper binaries:存放二进制文件,只有root用户才能访问
/boot系统启动核心目录,存放系统启动程序文件,例:查看启动文件的大小
/devdevices:用于存放硬件设备文件
/etcetcetera:存放系统配置文件(字体文件等)
/home家目录,每一个用户都有一个”家”,用户的起始目录,创建用户跟随创建相应的家目录
/liblibrary:系统资源文件类库
/proc内存映射目录,可以查看系统相关硬件的信息
/varvariable:可变的,变量. 部署项目用的
/tmptemporary:用来存放临时文件
/root超级用户root的家目录
/usrunix shared resouce: 存放unix共享系统资源,类似于” C:/ Program Files”,用于安装各种软件

常用命令(重点)

Shell的概念

Shell俗称外壳,是提供用户使用界面的一种软件,叫做命令解释器

主要负责接受用户输入的命令,然后调用相应的应用程序,最后向用户输出程序运行的结果

命令的格式

命令 [-选项] [参数]

命令区分大小写,其中选项和参数是可选的,中间采用空格隔开

常用命令的详解
(1)查看目录下文件/目录
命令功能描述
lslist显示文件
ls -l 或 ||list -list显示详细信息
ls -alist -all显示全部(包含隐藏文件)文件
ls -allist -all list 上两个合体
ls 目录名查看目录下有什么东西
目录切换
命令功能描述
cd …上一级目录
cd dirname进入目录
cd 或 cd ~直接回到用户的家目录
cd /回到系统根目录

相对路径:当前目录开头的

绝对路径:根目录 / 开头

查看完整路径
命令功能描述
pwd查看当前目录所在的位置
查看当前用户
命令功能描述
whoami查看当前用户的名称
用户切换
命令功能描述
su普通用户切换到root用户
su root切换到root用户
su 用户名切换到普通用户
exit退回到原来用户

最好使用su和exit搭配使用,否则多次使用su指令会导致用户的”叠加”

管理用户
命令功能描述
useradd xxx创建用户
passwd xxx为创建的用户设置密码
userdel删除用户

删除主目录下的文件:userdel -r 用户名

查看命令的所在目录
命令功能描述
which 命令查看指定命令所在的路径信息
文件操作
命令功能描述
touch fileName创建名字为fileName的文件
touch dir/fileName在dir目录下创建名字为fileName的文件
echo 内容 > fileName把内容覆盖写到文件中,若文件不存在则创建
echo 内容 >> fileName把内容追加到文件中
cat fileName打印文件内容到终端
more fileName分屏查看文件各行内容,不支持回看
less fileName查看文件各部分内容,支持回看
head -n fileName查看文件的前n行内容
tail -n fileName查看文件末尾n行内容
wc fileName查看文件的行数
目录操作
命令功能描述
mkdir 目录名创建普通文件夹
mkdir -p 目录/目录/目录递归方式创建多级父子文件夹
mv dir1 dir2将dir1移动到dir2中
mv dir1/dir2 ./将dir1中dir2移动到当前目录下
mv dir1 name将dir1改名为name
cp dir1 name将dir1拷贝为name
cp -r dir1 dir2需要设置参数 -r (recursive递归) 无视目录层次
rm 文件删除文件
rm -r 目录递归删除目录(无视目录层次)
rm -rf 文件/目录-r force(强制) 删除文件/目录
查找操作
命令功能描述
find / -name passwd[完整名称]查找passwd文件
find ./ -name “p*”查找带”p”的文件
find ./ -type f查找所有文件
grep 内容 fileName从指定文件中查找指定的内容
权限管理
命令功能介绍
chmod 权限 文件/目录名管理指定文件的权限信息,r读:4 w写:2 x执行:1
进程管理
命令功能描述
ps查看当前终端窗口里的进程
ps -aux查看系统中的所有进程
ps -ef查看进程列表
kill 进程号杀死指定的进程
kill -9 进程号强制杀死指定的进程
其它命令
命令功能描述
ifconfig查看当前系统的IP地址等信息
tar zcvf 压缩文件名.tar.gz 路径1 路径2 …实现一组文件或文件夹的打包
tar zxvf 压缩文件名.tar.gz实现解压缩解包
man [章节号] 命令/函数名查询指定的命令或函数

vi工具的使用(重点)

基本概念

vi和vim是Linux系统命令行下的文本编辑器,通常格式为:vi 文件名 或 vim 文件名

三种模式

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ddY7L8RV-1624432057344)(E:\MarkDown\拉勾笔记\vi工具的三种模式)]

使用方式
(1)命令模式的编辑命令
i:在当前位置之前插入
a:在当前位置之后插入
o:在当前行下插入
(2)命令行模式的删除命令
x 	删除一个字符
dw  删除当前词
3dw 删除三个词
dd  删除当前行
5dd 删除五行
(3)命令行模式的修改命令
r  替换一个字符
cw 替换一个单词
cc 替换一行
C  替换从光标至行尾
(4)命令行模式的拷贝命令
yw 	   拷贝词
yy 	   拷贝行(或Y)
dd 	   剪切行
p 	   当前行下粘贴
u      撤销
ctrl+r 取消撤销
(5)底行模式的命令
:w  		存盘
:w newfile  存成新文件
:wq 		存盘退出Vi(或ZZ,或:x)
:q! 		强行退出不存盘
:1,2co3 	拷贝行1,行2在行3之后
:4,5mo6 	移动行4,行5在行6之后
:%s 		/源字符串/目标字符串
:%s 		/源字符串/目标字符串/g 替换每一行中的所有
(6)注意使用

使用vimtutor 命令用来练习vi命令

用户主目录下.vimrc文件可以实现vi的简单设置

小结

计算机体系结构、Linux系统的由来、虚拟机和软件的安装、目录结构、常用命令、vi工具的使用

开发环境搭建和Shell编程

开发环境搭建(掌握)

Xshell和Xftp工具
下载和安装方式

下载地址:https://www.netsarang.com/zh/

安装方式:直接一路点击下一步即可,安装过程选择免费版

使用方式

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-uU9ScJvp-1624432057346)(E:\MarkDown\拉勾笔记\Xshell和Xftp工具使用方式)]

网络模式设置

设置网络连接模式为NAT模式

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-2WK6ehud-1624432057347)(E:\MarkDown\拉勾笔记\网络模式设置)]

修改配置文件

使用root用户打开/etc/sysconfig/network-scripts/ifcfg-eno16777736文件

BOOTPROTO=static
ONBOOT=yes
IPADDR=192.168.44.128
GATEWAY=192.168.44.2
NETMASK=255.255.255.0
DNS1=114.114.114.114
配置文件生效
使用命令使得配置文件生效:service network restart
JDK的下载和安装
下载和安装方式

下载地址:https://www.oracle.com/java/technologies/javase-downloads.html

安装方式:将下载好的jdk安装包通过Xftp工具传输到CentOS系统中,使用tar命令解压即可

配置环境变量

1、使用root用户打开配置文件/etc/profile,向文件末尾追加内容

export JAVA_HOME=/usr/javajdk
export PATH=$JAVA_HOME/bin:$PATH

2、保存退出后让文件生效并验证是否配置成功

source /etc/profile
javac -version
Tomcat的下载和安装
下载和安装方式

下载地址:https://tomcat.apache.org/download-80.cgi

安装方式:将下载好的Tomcat安装包通过Xftp工具传输到CentOS系统中,使用tar命令解压即可

启动和关闭方式
startup.sh
shutdown.sh
开放防火墙端口
/sbin/iptables -I INPUT -p tcp --dport 8080 -j ACCEPT 开启8080端口(暂时开通)
配置环境变量(Linux环境下一律不做Tomcat环境变量配置)

1、使用root用户打开配置文件/etc/profile,向文件末尾追加内容

export CATALINA_HOME=/usr/tomcat
export PATH=$CATALINA_HOME/bin:$PATH

2、保存退出后让文件生效并验证是否配置成功

source /etc/profile
startup.sh
发布Web项目

将Web项目打成war包,通过Xftp工具将war包放在tomcat/webapp目录并启动

Mysql的下载和安装
下载Mysql的repo源
wget http://dev.mysql.com/get/mysql57-community-release-el7-8.noarch.rpm
安装rpm包
rpm -ivh mysql57-community-release-el7-8.noarch.rpm
安装Mysql
yum install mysql-server
启动服务
service mysqld start
查看服务状态
systemctl status mysqld
使用root用户登录
mysql -u root
修改临时密码
alter user 'root'@'localhost' identified by 'QiDian@666';
图形化界面访问数据库
使用SQLyog工具

启动图形化界面工具SQLyog连接虚拟机中Mysql数据库

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-aSD6dxIX-1624432057349)(E:\MarkDown\拉勾笔记\SQLyog连接数据库登录错误)]

解决方案

使用root权限登录数据库后选择mysql库

mysql -u root -p
use mysql;

查看mysql库中的user表的host值后修改为通配符%

select host from user where user='root';
update user set host='%' where user='root';
flush privileges;

查看修改结果并重新测试

select user,host from user;

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-fzkTGrZX-1624432057352)(E:\MarkDown\拉勾笔记\SQLyog登录成功)]

Shell编程(熟悉)

基本概念

Shell是一个命令行解释器,可以接收应用程序或用户命令,然后访问操作系统内核

Shell是一个功能相当强大的编程语言,易编写、易调试、灵活性强

编写第一个程序

使用vi工具创建xxx.sh的文件

以#!/bin/bash开头并编写代码后保存

执行Shell程序的方式

方式一:./文件名,此方式需要执行权限

方式二:/bin/bash 文件名,此方式不需要执行权限

变量的定义
语法格式

定义变量:变量=值

撤销变量:unset 变量

定义规则

变量名称可以由字母、数字和下划线组成,但是不能以数字开头,环境变量名建议大写

不能使用bash里的关键字

中间不能有空格,可以有下划线

在bash中,变量默认类型都是字符串类型,无法直接进行数值运算

变量的值如果有空格,需要使用双引号或单引号括起来

常用运算符
算术运算符

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-n13yrsxZ-1624432057354)(E:\MarkDown\拉勾笔记\Xhell编程常用算术运算符)]

关系运算符

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-bg0RJ8Rl-1624432057356)(E:\MarkDown\拉勾笔记\Xshell编程常用关系运算符)]

流程控制语句
if判断
if [ 条件判断式 ]
 then
 程序
fi
case语句
case $变量名 in
"值1")
 如果变量的值等于值1,则执行程序1
 ;;
"值2")
 如果变量的值等于值2,则执行程序2
 ;;
…省略其他分支…
*)
 如果变量的值都不是以上的值,则执行此程序
 ;;
esac
for循环
for (( 初始值;循环控制条件;变量变化 ))
do
	程序
done
while循环
while [ 条件判断式 ]
do
	程序
done
函数
[ function ] funname[()]
{
 Action;
 [return int;]
}
funname

小结

Xshell和Xftp工具的下载和安装配置网络环境JDK下载和安装(配置环境变量)Tomcat的下载和安装(不配置环境变量)MySQL数据库的下载和安装(在线)Shell编程的概念、变量定义、运算符、流程控制语句、函数

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值