随着引入MVC模式,JavaWeb项目的开发变得更加的合理。
根据MVC的规范,在作为V(视图)的JSP中,我们应该尽量少的参杂Java代码。
那么,JSP的展示数据,应该如何来完成?
有两种技术用来代替Java脚本:EL表达式和JSTL标签
EL表达式
1.概念:EL,即Expression Language,表达式语言
2.作用:替代JSP中的Java脚本
3.语法:${表达式}
4.注意:JSP默认支持EL表达式,如果想要不对EL表达式进行解析,即原样输出的话,有两种方法:
(1)page指令的isElIgnored="true",这样整个JSP页面的EL表达式都不会被解析
(2)在EL表达式前面加上一个\,表示转义
5.EL表达式的使用场景:
(1)运算:
EL中支持的运算符有:
- 算数运算符:+ - * /(div) %(mod)
- 比较运算符:> < >= <= == !=
- 逻辑运算符:&&(and) ||(or) !(not)
- 空运算符:empty,用于判断字符串、集合、数组是否为null或者长度是否为0,比如{empty list1},当list1为null或list1的长度为0时,EL表达式的结果为true
{not empty list1}表示对list1集合进行非空判断
<%@ page contentType="text/html;charset=UTF-8" language="java"%>
<html>
<head>
<title>Title</title>
</head>
<body>
${3>4}
\${3>4}
<hr>
<h3>算数运算符</h3>
5 + 3 = ${5+3}<br/>
5 - 3 = ${5-3}<br/>
5 * 3 = ${5*3}<br/>
6 / 3 = ${6/3}<br/>
<hr>
<h3>比较运算符</h3>
1 > 2 ? ${1>2}<br/>
5 != 4 ? ${5!=4}<br/>
<hr>
<h3>逻辑运算符</h3>
1 > 2 or 5 > 3 ? ${1>2 or 5>3}<br/>
1 < 3 and 5 > 4 ? ${1<3 and 5>4}<br/>
</body>
</html>
(2)获取值:
EL表达式只能从域对象中获取值
语法:
- 【1】${域名称.键名称}表示从指定域中获取指定键的值
域名称与域对象的对应关系:
pageScope --》pageContext
requestScope --》 request
sessionScope --》session
applicationScope --》application(即ServletContext)
如果取不到值,显示""空字符串,而不是null,这样不会打乱页面。
如果使用脚本输出,当获取不到时,页面会输出null,这样就不美观。
【2】${键名}表示从所有域中查找是否有该键对应的值。(从小到大)
【3】获取对象,List集合,Map集合的值
对象:${域名称.对象名.属性名}
<%@ page import="cn.itcast.User" %>
<%@ page import="java.text.SimpleDateFormat" %>
<%@ page import="java.util.Date" %>
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<%
User user = new User();
user.setAge(20);
user.setGender('男');
user.setName("张三");
request.setAttribute("user",user);
request.setAttribute("time",new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(new Date()));
%>
姓名:${user.name},年龄:${user.age},性别:${user.gender}
<br>
当前时间:${time}
</body>
</html>
List集合:${域名称.集合名[索引]}
<body>
<%
List<String> strs = new ArrayList<>();
strs.add("str1...");
strs.add("str2...");
strs.add("str3...");
request.setAttribute("strs",strs);
%>
第一个元素:${strs[0]}<br>
第二个元素:${strs[1]}<br>
第三个元素:${strs[2]}
</body>
Map集合:
第一种:${域名称.集合名.键名}
第二种:${域名称.集合名["键名"]}
这种需要加引号
<body>
<%
Map<String,Object> map = new HashMap<>();
map.put("age",18);
map.put("name","张三");
map.put("classes","三年一班");
request.setAttribute("map",map);
%>
<hr>
名字:${map.name}<br>
班级:${map.classes}<br>
年龄:${map.age}<br>
</body>
我们知道,EL表达式是根据对象的属性而不是成员来获取值,因此
${pageContext.request.contextPath}:获取项目根路径
pageContext是EL表达式11个隐式对象之一
${pageContext}获取到的是JSP内置对象的PageContext
而pageContext有getRequest方法,因此${pageContext.request}可以获取到request对象
request对象又有一个getContextPath()方法,因此可以获取到根路径。
JSTL标签
1.概念
JSTL:JavaServer Pages Tag Library,JSP标准标签库
是由Apache组织提供的开源免费JSP标签
2.作用:与EL一样,用于替换JSP页面中的Java脚本
3.使用步骤
(1)导入jstl的相关jar包
(2)在JSP页面中通过taglib指令引入标签库
(3)使用标签
4.常用的JSTL标签
(1)if
<%--
c:if标签
1.属性
* test 必须属性,接收布尔表达式,如果结果为true则显示if标签体内容
test属性值一般结合EL表达式一起使用
2.c:if标签没有else,如果想要else,可以写多个if来替代
--%>
<c:if test="${2>3}">hello</c:if>
<c:if test="true">hello</c:if>
<%
ArrayList<String> list = new ArrayList<>();
list.add("张三");
list.add("李四");
request.setAttribute("list",list);
%>
<c:if test="${not empty list}">
遍历集合。。。
</c:if>
(2)choose、when、otherwise
<body>
<%-- 完成数字编号对应星期几 --%>
<%--
使用choose取出数字
使用when判断数字
使用otherwise做其他情况声明
--%>
<%
request.setAttribute("num","3");
%>
<c:choose>
<c:when test="${num == 1}">
<h1>星期一</h1>
</c:when>
<c:when test="${num == 2}">
<h1>星期二</h1>
</c:when>
<c:when test="${num == 3}">
<h1>星期三</h1>
</c:when>
<c:when test="${num == 4}">
<h1>星期四</h1>
</c:when>
<c:when test="${num == 5}">
<h1>星期五</h1>
</c:when>
<c:when test="${num == 6}">
<h1>星期六</h1>
</c:when>
<c:otherwise>
<h1>星期天</h1>
</c:otherwise>
</c:choose>
</body>
(3)foreach
<body>
<%--
foreach相当于java代码的for循环
属性:
begin:开始角标
end:结束角标,开始角标和结束角标都是大(小)于等于
var:临时变量,注意要取到临时变量必须用EL表达式
step:步长
varStatus:循环状态对象,该对象有两个属性
varStatus.index:表示当前的角标
varStatus.count:表示当前遍历的次数
items:容器对象
--%>
<c:forEach begin="1" end="5" var="i" step="2" varStatus="s">
当前角标:${s.index},遍历次数:${s.count}<br>
</c:forEach>
<hr>
<%
ArrayList<String> list = new ArrayList<>();
list.add("aaa");
list.add("bbbb");
list.add("cc");
request.setAttribute("list",list);
%>
<c:forEach items="${list}" var="i" varStatus="s">
当前角标:${s.index},当前元素:${i},遍历次数:${s.count}<br>
</c:forEach>
</body>
案例
需求:在请求域中有一个存有User对象的List集合,需要使用jstl+el将list集合展示到jsp页面的表格中。
@WebServlet("/SendUserServlet")
public class SendUserServlet extends javax.servlet.http.HttpServlet {
protected void doPost(javax.servlet.http.HttpServletRequest request, javax.servlet.http.HttpServletResponse response) throws javax.servlet.ServletException, IOException {
List<User> users = new ArrayList<>();
User user1 = new User("独孤求败",999,'男');
User user2 = new User("令狐冲",19,'男');
User user3 = new User("东方不败",18,'女');
User user4 = new User("风清扬",666,'男');
users.add(user1);
users.add(user2);
users.add(user3);
users.add(user4);
request.setAttribute("users",users);
request.getRequestDispatcher("/practice/showUser.jsp").forward(request,response);
}
protected void doGet(javax.servlet.http.HttpServletRequest request, javax.servlet.http.HttpServletResponse response) throws javax.servlet.ServletException, IOException {
doPost(request, response);
}
}
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>
<html>
<head>
<title>练习</title>
</head>
<body>
<c:if test="${not empty users}">
<center>
<table border="1" bgcolor="#98fb98">
<tr>
<th>姓名</th>
<th>年龄</th>
<th>性别</th>
</tr>
<c:forEach items="${users}" var="u">
<tr>
<td>${u.name}</td>
<td>${u.age}</td>
<td>${u.gender}</td>
</tr>
</c:forEach>
</table>
</center>
</c:if>
</body>
</html>