JSP学习笔记


JSP

​ jsp相当于java+html。jsp的最大特点在于,写jsp就像在写html。相比html而言,html只能为用户提供静态数据,而jsp技术允许在页面中嵌套java代码,为用户提供动态数据。相比servlet而言,servlet很难对数据进行排版,而jsp除了可以用java代码产生动态数据的同时,也很容易对数据进行排版。

​ 不管是JSP还是Servlet,虽然都可以用于开发动态web资源。但由于这2门技术各自的特点,在长期的软件实践中,人们逐渐把servlet作为web应用中的控制器组件来使用,而把JSP技术作为数据显示模板来使用。

​ 原因在于,程序的数据通常要美化后再输出,让jsp既用java代码产生动态数据,又做美化会导致页面难以维护;让servlet既产生数据,又在里面嵌套html代码美化数据,同样也会导致程序可读性差,难以维护。 因此最好的办法就是根据这两门技术的特点,让它们各自负责各的,servlet只负责响应请求产生数据,并把数据通过转发技术带给jsp,数据的显示jsp来做。

执行过程

​ jsp本质上就是servlet。第一次访问jsp文件时,会在tomcat的work目录下生成对应的java文件,然后编译为字节码文件,执行jsp时,其实就是执行对应的class文件,再次访问还jsp时,直接从work下找到对应的class文件并执行。


JSP语法

JSP脚本

<!-- jsp脚本,脚本中声明的变量放在_jspService方法中 
    可在路径 tomcat\apache-tomcat-8.0.46\work\Catalina\localhost 下找到源文件并查看
-->
<% 
    //
    int num = 10;
    String name = "zhangsan";
    System.out.println(name);

    Date date = new Date();
    //对日期字符串进行解析和格式化输出
    SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
    String dateStr = sdf.format(date);
    System.out.println(dateStr);
    %>

<!-- 必须保证Java语句的完整性 -->
<% 
  for(int i = 1; i <= 6; i++){
    response.getWriter().write("<h" + i + ">标题" + i + "<h" + i +"/>");
  }
  %>
<%
  for(int i = 1; i <=6; i++){
  %>
<h<%=i %>>标题<%=i %></h<%=i %>>
<%
  }
  %>

<%-- jsp的注释,java代码不会对注释进行处理 --%>

JSP表达式

<!-- jsp表达式 -->
<!-- 相当于out.print(name ); -->
<%=name %>
<%=name.length() %>
<!-- 当前时间 -->
<%= new java.util.Date() %>

JSP声明

<!-- jsp声明 -->
<%!
    //相当于成员变量
    private int aaa = 10;

    //定义一个方法
    public int add(int a, int b){
        return a + b;
    }

    //不建议使用
    int sum = add(10, 12);
    %>
<%
    //调用方法
    System.out.println(add(12, 10));
    System.out.println(sum);
    %>

三大指令

​ JSP指令的基本语法格式:<%@ 指令 属性名=”值” %>


include

​ include指令用于引入其他JSP页面,使用include指令引入其他JSP页面,JSP引擎将把这两个JSP翻译成一个servlet。include指令引入通常也称之为静态引入。

​ 被引入的文件必须遵循JSP语法。被引入的文件可以使用任意的扩展名,即使其扩展名是html,JSP引擎也会按照处理jsp页面的方式处理它里面的内容,为了见明知意,JSP规范建议使用.jspf(JSP fragments)作为静态引入文件的扩展名。

<!-- include.jsp -->
<!-- include指令,相当于将多个文件合成一个文件,转换为一个java文件 
    file 用于指定被引入文件的相对路径,必须使用相对路径
-->
<%@ include file="header.jsp" %>

page

​ 用于定义JSP页面的各种属性,无论page指令出现在JSP页面中的什么地方,它作用的都是整个JSP页面,为了保持程序的可读性和遵循良好的编程习惯,page指令最好是放在整个JSP页面的起始位置。

配置
<!-- 
    contentType 服务器返回给浏览器内容的编码格式,相当于response.setContentType(...) 
    pageEndoing JSP文件的编码格式
    import 导入的包
    session 默认true,表示是否自动创建session对象
    errorPage 指定出错时跳转到的界面,只在本jsp中起作用
    isErrorPage 指定页面是一个错误处理页面
-->
<%@ page import="java.util.Date" %>
<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" 
  session="false"
  errorPage="error.jsp"
  isErrorPage="true"
  %>

<!-- 如果使用exception,必须设置isErrotPage="true",否则无法识别exception -->
<%=exception.toString() %>
全局配置
<!-- 配置全局的错误处理界面 -->
<!-- 在web.xml中配置 -->
<error-page>
    <error-code>404</error-code>
    <location>/404.jsp</location>
</error-page>
<error-page>
    <error-code>500</error-code>
    <location>/500.jsp</location>
</error-page>
<error-page>
    <exception-type>java.lang.NullPointerException</exception-type>
    <location>/error.jsp</location>
</error-page>

taglib

​ 用于在JSP页面中导入标签库


内置对象

​ JSP引擎在调用JSP对应的xxx_jspService时,会传递或创建9个与web开发相关的对象供xxx_jspService使用。JSP技术的设计者为便于开发人员在编写JSP页面时获得这些web对象的引用,特意定义了9个相应的变量,开发人员在JSP页面中通过这些变量就可以快速获得这9大对象的引用。


九大内置对象

  1. request HttpServletRequest
  2. response HttpServletResponse
  3. application ServletContext
  4. session HttpSession
  5. out JspWriter
  6. pafeContext PageContext
  7. exception Throwable
  8. config ServletConfig
  9. page Object(this) 较少使用
out

​ out 隐式对象用于向客户端发送文本数据。

​ out对象是通过调用pageContext对象的getOut方法返回的,其作用和用法与ServletResponse.getWriter方法返回的PrintWriter对象非常相似。

<%@ buffer="8kb" %>
<% 
  //有缓存 jspWriter使用了缓存,缓存满了、或者flush、或者流关闭,都会将缓存中的内容输出
  //JspWriter相当于一种带缓存功能的PrintWriter
  //buffer="8kb"    设置缓存out的缓存,默认8kb
  out.write("hello");
  //刷新缓存
  out.flush();
  //先执行
  response.getWriter().write("hahaha");
  %>
pageContext

​ pageContext对象是JSP技术中最重要的一个对象,它代表当前JSP页面的运行环境,这个对象不仅封装了对其它8大隐式对象的引用,它自身还是一个域对象,可以用来保存数据。并且,这个对象还封装了web开发中经常涉及到的一些常用操作,例如包含和跳转其它资源、检索其它域对象中的属性等。

<%
  //可以获取其他内置对象
  pageContext.getRequest();
  pageContext.getResponse();
  pageContext.getServletContext();
  pageContext.getSession();
  pageContext.getServeltConfig();
  pageContext.getException();
  pageContext.getOut();
  pageContext.getPage();
  %>

<%
  //pageContext 域对象
  //存储数据
  pageContext.setAttribute("msg", "page_msg");
  //第三份参数,指定向那个域中设置数据
  //四个域对象:request, session, application, pageContext
  pageContext.setAttribute("msg", "page_msg", PageContext.PAGE_SCOPE);
  pageContext.setAttribute("msg", "page_msg", PageContext.REQUEST_SCOPE);
  pageContext.setAttribute("msg", "page_msg", PageContext.SESSION_SCOPE);
  pageContext.setAttribute("msg", "page_msg", PageContext.APPLICATION_SCOPE);
  %>

<%
  //获取
  System.out.println(pageContext.getAttribute("msg"));
  System.out.println(request.getAttribute("msg"));
  System.out.println(session.getAttribute("msg"));
  System.out.println(application.getAttribute("msg"));

  //从域中查找属性
  //pageContext->request->session->application
  pageContext.findAttribute("msg");
  %>

应用

<!-- userinfo.jsp -->
<%
  //从域中获取数据
  List<User> list = (List<User>)request.getAttribute("list");
  %>
<table>
  <tr>
    <td>id</td>
    <td>name</td>
  </tr>
  <% for(User user : list){ %>
    <tr>
        <td><%=u.getId() %></td>
        <td><%=u.getName() %></td>
    </tr>
  <% } %>
</table>
//UserInfoServlet.java
List<User> list = new ArrayList<>();
for(int i = 0; i < 10; i++){
  list.add(new User(10 + i, "Tom" + i));
}
request.setAttribute("list", list);
//转发,共享request域中的数据
request.getRequestDispatcher("/userinfo.jsp").forward(request, response);

EL表达式

获取数据

​ EL表达式主要用于替换JSP页面中的脚本表达式,以从各种类型的域中检索java对象、获取数据。使用EL表达式获取数据语法:${标识符}


从指定域中获取数据
<!-- xxx.jsp -->
<%
  //域中写入数据
  request.setAttribute("name", "zhangsan");
  //从域中取数据
  request.getAttribute("name");

  //
  pageContext.setAttribute("name", "lisi");
  %>

<!-- 获取域中的数据,并且显示到页面上
    大括号中的值表示域中的key值,不带双引号
    相当于pageContext.findAttribute("name")
    没有放到域中,无法读取数据
-->
${name }
<!-- 从指定域中获取数据 
    pageScope
    requestScope
    sessionScope
    applicationScope
    都是EL中的内置对象
    pageContext-request-session-applocation
-->
${requestScope.name }
${pageScope.name }

<!-- tomcat8下,可以设置;tomcat7不可以设置 -->
${name="heiheihei" }
${name }
${requestScope.name="123" }
${requestScope.name }
//跳到jsp
request.setAttribute("name", "haha");
request.getRequestDispatcher("/EL.jsp").forward(request, response);
<!-- 无法直接获取一个Java变量的值 -->
<%
  int i = 0;
  %>
${i }
获取对象属性
<!-- 对象 -->
<%
  Student stu = new Student();
  stu.setId(10);
  stu.setName("lisi");
  request.setAttribute("student", stu);
  %>
<!-- 读取对象中的属性值 -->
<!-- 内部通过调用get方法获得值 -->
${student }<!-- 输出对象的内容 -->
${student.id }
${student.name }
获取集合中的值
<!-- 集合 -->
<%
  List<String> list = new ArrayList<String>();
  list.add("zhangsan");
  list.add("lisi");
  request.setAttribute("list", list);

  Map<String, Object> map = new HashMap<String, Object>();
  map.put("name", "aaa");
  map.put("age", 20);
  request.setAttribute("map", map);
  %>
<!-- 根据下标得到集合中数据 -->
${list[0] }
<!-- map中,根据key值获取value -->
${map["name"] }
${map.name }

表达式运算

<!-- 数学运算 -->
${10 + 3 }

<!-- 关系运算符
false,true,false,true,true
-->
${10 < 3 }
${10 > 3 }
${10 == 3 }
${10 != 3 }
${10 gt 3 }

<!-- 逻辑运算符
false,false,true,true,false,false
-->
${true && false }
${true and false }<!-- 逻辑与 -->
${true || false }
${true or false }<!-- 逻辑或 -->
${!true }
${not true }

<!-- 判断字符串是否是空 -->
<%
  String str = "hello";
  request.setAttribute("str", str);
  %>
<!-- false,false,true -->
${str == null || str == "" }
${empty str }
${not empty str }

<!-- 三目运算符 -->
${empty str ? 1 : 111 }

内置对象

​ EL 表达式定义了一些内置(隐式)对象,利用这些隐式对象,开发人员可以获得对web中常用对象的引用,从而获得这些对象中的数据。

隐含对象名称描述
pageContext对应于JSP页面中的pageContext对象(注意:取的是pageContext对象)
pageScope代表page域中用于保存属性的Map对象
requestScope代表request域中用于保存属性的Map对象
sessionScope代表session域中用于保存属性的Map对象
applicationScope代表application域中用于保存属性的Map对象
param表示一个保存了所有请求参数的Map对象
paramValues表示一个保存了所有请求参数的Map对象,它对于某个请求参数,返回的是一个string[]
header表示一个保存了所有http请求头字段的Map对象
headerValues同上,返回string[]数组。注意:如果头里面有“-” ,例Accept-Encoding,则要headerValues[“Accept-Encoding”]
cookie表示一个保存了所有cookie的Map对象
initParam表示一个保存了所有web应用初始化参数的Map对象
<!-- 获取请求参数 -->
${param["id"] }
${param.id }

<!-- 返回数组结构 
    针对有key值相同的多个参数,比如checkbox
-->
${paramValues["hobby"][0] }

<!-- 获取请求头中的数据 -->
${header["Host"] }

<!-- 获取cookie对象 -->
${cookie["JSESSIONID"] }
<!-- 得到cookie的名称和值
    内部调用getName、getvalue方法 
-->
${cookie["JSESSIONID"].name }
${cookie["JSESSIONID"].value }
${cookie.JSESSIONID.value }

<!--  -->
<%
  pageContext.getRequest();
  %>
<!-- 获得应用路径 -->
${pageContext.request.contextPath }
<!-- 可以获取其他对象,但是不能直接调用get方法 -->
${pageContext.out }

<form action="${pageContext.request.contextPath }/xxx.jsp"></form>

JSP标签

内置动作标签

<!-- 创建对象,对象会放到域中
    class 包名+类名
-->
<jsp:useBean id="stu" class="com.ff.servlet.Student" ></jsp:useBean>

<!-- 设置对象的属性值
    name 表示对象的名称
    property 属性名
    value 对应的值
-->
<jsp:setProperty property="name" name="stu" value="lisi" />

<!-- 获取属性值 -->
<jsp:getProperty property="name" name="stu" ></jsp:getProperty>
${stu.name }

<!-- 转发
    WE8-INF 下的资源不能直接访问
    通常情况下,需要通过转发的方式访问
    项目中,访问WE8-INF文件夹下的资源 
-->
<jsp:forward page="WE8-INF/xxx.jsp" ></jsp:forward>

JSTL标签

主要包括
  • 核心标签(c:)
  • JSTL函数(fn:)
  • 格式化标签(fmt:)
  • 数据库标签
  • XML标签
使用
<!-- 导包 导入jstl-1.2.jar文件 -->
<!-- 通过taglib引入jstl的核心标签库,核心标签库的前缀c -->
<%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %>
核心标签库
set/out
<!-- 理解 -->
<!-- 设置值,向域中添加数据 
    var   相当于变量名
    value   对应的值
    scope   指定存放的域
-->
<c:set var="name" value="zhangsan" ></c:set>
<!-- 设置null值 -->
<c:set var="name" value="${null }" ></c:set>
<c:set var="age" value="10" scope="request" ></c:set>
${name }
${requestScope.age }

<!--  -->
<%
  Student stu = new Student();
  request.setAttribute("student", stu);
  %>
<!-- target需要设置属性的对象
    property需要设置的属性
-->
<c:set target="${student }" property="name" value="lisi" ></c:set>
${student.name }
<!-- 通过表达式设置 -->
<c:set target="<%=stu %>" property="name" value="laowang" ></c:set>
<%=student.getName() %>

<!-- value   要输出的值
    default   值不存在时,对应的缺省值
    escapeXml   是否让html标签起作用,false起作用,true不起作用
-->
<c:out value="${age1 }" default="<h1>20</h1>" escapeXml="false" ></c:out>
条件判断
<!-- test 中给出判断条件,由EL表达式给出
    单条件判断
-->
<c:if test="${10 > 5}" >yes</c:if>

<!-- 相当于往域中写入值 -->
<c:set var="sex" value="男" ></c:set>
<c:if test="${sex == '男' }" >
    <input type="radio" chacked="checked" /><input type="radio" /></c:if>

<!--  -->
<input type="radio" <c:if test="${sex == '男' }">checked="checked"</c:if> />男
<input type="radio" <c:if test="${sex == '女' }">checked="checked"</c:if> />女

<c:set var="score" value="80"></c:set>
<!-- 多条件判断,相当于if(){...}else if(){...}...else{...} -->
<c:choose>
    <c:when test="${score >= 0 && score < 60 }">
        不及格
    </c:when>
    <c:when test="${score >= 60 && score < 80 }">
        良好
    </c:when>
    <c:when test="${score >= 80 && score <= 100 }">
        优秀
    </c:when>
    <c:otherwise>值不对</c:otherwise><!-- 其他条件 -->
</c:choose>
循环
<!--  -->
<%
  List<String> list = new ArrayList<String>();
  for(int i = 0; i < 10; i++){
    list.add("Tom" + i);
  }
  request.setAttribute("list", list);
  %>
<!-- 循环遍历
    items 表示循环遍历的对象
    var 表示每次遍历的元素在pageContext域中的name值
    begin/end 指定遍历开始和结束的索引
    step 步长 每遍历一个元素后,移动几个元素继续遍历 例似于自增(i++)
    varStatus 遍历的元素的状态,状态存在域中,比如,vs表示域中状态对象的name值
                                            setAttribute("vs", ...)
    count 数据的序号 从1开始
    index 数据在集合中的索引 从0开始
    first 判断是否是遍历的第一个元素
    last 判断是否是遍历的最后一个元素
-->
<c:forEach items="${list }" var="s" varStatus="vs" begin="2" end="8" step="" >
    ${s }
    ${vs.count }<!-- 数据的序号 从1开始 -->
    ${vs.index }<!-- 数据在集合中的索引 从0开始 -->
    ${vs.first }<!-- 判断是否是遍历的第一个元素 -->
    ${vs.last }<!-- 判断是否是遍历的最后一个元素 -->
</c:forEach>
属性名是否支持EL属性类型属性描述
varfalseString指定将当前迭代到的元素保存到page这个Web域中的属性名称
itemstrue任何支持的类型将要迭代的集合对象
varStatusfalseString指定将代表当前迭代状态信息的对象保存到page这个Web域中的属性名称
begintrueint如果指定items属性,就从集合中的第begin个元素开始进行迭代,begin的索引值从0开始编号;如果没有指定items属性,就从begin指定的值开始迭代,直到end值时结束迭代
endtrueint参看begin属性的描述
steptrueint指定迭代的步长,即迭代因子的迭代增量
其他
<!-- 遍历一些特殊写法的字符串
    delims 相当于拆分用的分隔符
    了解
-->
<c:forTokens items="java-c-php" delims="-" var="v" >
    ${v }
</c:forTokens>

<!-- 重定向 -->
<c:redirect url="http://www.baidu.com" ></c:redirect>

<!-- 设置url路径 -->
<c:url value="/xxx.jsp" var="url" >
    <!-- 设置参数 /xxx.jsp?id=10&name=lisi -->  
    <c:param name="id" value="10" ></c:param>
    <c:param name="name" value="lisi" ></c:param>
</c:url>

<!-- 获取定义的url路径 -->
<a href="${url }" >jstl</a>
格式化标签
<!-- 引入格式化标签库 -->
<%@ taglib uri="http://java.sun.com/jsp/jstl/fmt" prefix="fmt" %>
<!-- 数字的格式化标签
    value 要处理的数据
    type 数字的类型
        number 数字
        currency 货币
        percent 百分比
    pattern 指定格式
    currencySymbol 货币符号
    minFractionDigits 小数点后面最少多少位
-->
<fmt:formatNumber value="12345.123" type="number" pattern="###,###.##" ></fmt:formatNumbe>
<fmt:formatNumber value="1000" type="currency" currencySymbol="¥" ></fmt:formatNumber>
<fmt:formatNumber value="0.211421" type="percent" minFractionDigits="2" ></fmt:formatNumber>

<!-- 日期的格式化
    type
        time 时间
        date 年月日
        both 两者都显示
    dateStyle 日期风格
    timeStyle 时间的风格
    pattern 格式化的样式
-->
<%
  Date date = new Date();
  request.setAttribute("date", date);
  %>
<fmt:formatDate value="${date }" type="date" />
<fmt:formatDate value="${date }" type="time" />
<fmt:formatDate value="${date }" type="both" dateStyle="long" timeStyle="short" />
<fmt:formatDate value="${date }" type="both" pattern="yyyy/MM/dd HH:mm:ss.SSS" />
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值