EL表达式
1. 概念
EL:Expression Language
即表达式语言
作用?
- 主要是替代jsp页面中的表达式脚本在jsp页面中进行输出
因为EL表达式在输出数据的时候要比jsp的表达式脚本简洁很多。EL主要用于输出域对象中的数据
2. 使用
${ 表达式 }
(在输出null值的时候输出是空串)
<body>
<%
request.setAttribute("key", "值");
%>
表达式脚本输出:<%= request.getAttribute("key") %> <br/>
EL表达式输出:${key}
<!-- 当key不存在时,前者输出null。EL会输出空串,显然后者对用户更友好-->
</body>
EL表达式搜索域数据的顺序:
<body>
<%
// JSP中的四个域对象,往四个域中都保存了相同key的数据,那EL输出什么呢?
pageContext.setAttribute("key", "pageContext");
request.setAttribute("key", "request");
session.setAttribute("key", "session");
application.setAttribute("key", "application");
%>
${ key }
</body>
结论:会按照四个域的从小到大的顺序去进行搜索,找到就输出,和代码的先后顺序是没关系的
(域是范围从小到大顺序:pageContext -> request -> session -> application)
EL输出复杂的Bean对象:
${ personkey } <!-- 直接调用Person中的toString方法,整个都输出-->
${ personkey.name } <!-- 输出Person对象中的个别属性值,直接 key.属性 就行了,
即使属性是private也行,它只是调用get方法(get属性方法),
所以所有的属性都要写get方法,才能被获取到,否则报错了-->
<!-- 加入Person对象中有Map类型,我们要输出属性Map中的key对应的值,怎么办?-->
${ personkey.map.key } ${ personkey.map.get("key") } ${ personkey.map["key"] } 也行
3. EL表达式运算
Ⅰ 关系元素
${ 12 == 12 } 或者 ${ 12 eq 12 } // 结果是false或者true
${ 12 != 12 } 或者 ${ 12 ne 12 }
> gt
< lt
>= ge
<= le
Ⅱ 逻辑运算
${ 10 == 10 && 1 == 1 } 或者 ${ 10 == 10 and 1 == 1 } // 结果是false或者true
|| or
! not
Ⅲ 算术运算
${10 + 12} - *
/ div
% mod
Ⅳ empty运算
可以判断一个数据是否为空,空则返回true,反之false
一下几种情况为空:
- null
- 空串
- Object类型数组,且长度为零
- List/Set/Map 集合元素个数为 0
<%
pageContext.setAttribute("emptyNull", null);
%>
${ empty emptyNull }
Ⅴ 三元运算
Ⅵ .运算 []运算
.运算:可以输出Bean对象中某个属性的值
[]运算:可以输出有序集合中某个元素的值,还可以用于map,例如上面的 ${ personkey.map[“key”] }
4. EL中11个隐含对象
EL中11个隐含对象:是EL中自己定义的可以直接使用
pageContext
:可以获得jsp中的九大内置对象(类型:PageContextImpl)
四个域对象对应的map:
pageScope
:可以获取pageContext域中的数据(类型:Map<String, Object>)
requestScope
:可以获取Request域中的数据 (类型:Map<String, Object>)
sessionScope
:可以获取Session域中的数据 (类型:Map<String, Object>)
applicationScope
:可以获取ServletContext域中的数据 (类型:Map<String, Object>)
param
:可以获取请求参数的值(类型:Map<String, String>)
paramValues
:可以获取请求参数的值,可多个值 (类型:Map<String, String[]>)
header
:可以获取请求头的信息 (类型:Map<String, String>)
headerValues
:可以获取请求头的信息 ,可多个值 (类型:Map<String, String[]>)
cookie
: 可以获取当前请求的Cokkie信息 (类型:Map<String, Cookie>)
initParam
:可以获取在 web.xml中配置的 上下文参数 (类型:Map<String, String>)
pageContext 使用:
${pageContext.out}
${pageContext.session}
${pageContext.response}
....
作用:一般用来输出
协议,
<%= request.getScheme() %> <!-- jsp表达式脚本写法,输出http-->
${pageContext.request.scheme} <!-- EL表达式写法 .scheme就行了,因为在EL中,自动回去找.后面对应的get方法-->
服务器ip 端口,
<%= request.getServerName() %>
<%= request.getServerPort() %>
${pageContext.request.serverName}
${pageContext.request.serverPort}
工程路径,
<%= request.getContextPath() %>
${pageContext.request.contextPath}
请求方式,
<%= request.getMethod() %>
${pageContext.request.method}
客户端ip,
<%= request.getRemoteHost() %>
${pageContext.request.remoteHost}
会话的id
<%= session.getId() %>
${pageContext.session.id}
,等信息
<!-- 可以这样用EL更简单点,先把request放到域中,就不用,pageContext.request.scheme-->
<%
pageContext.setAttribute("req", request);
%>
${req.scheme}
四个域对象对应map:
<%
pageContext.setAttribute("key", "pageContext");
request.setAttribute("key", "request");
session.setAttribute("key", "session");
application.setAttribute("key", "application");
%>
${ key } <!-- 从小的范围开始找,找到就输出key输出-->
${ pageScope.key } <!-- 选择性key输出-->
下面六个的使用:
输出请求参数username的值:${param.username}
输出请求参数hobby的第一个值:${paramValues.hobby[0]}
输出请求参数hobby的第二个值:${paramValues.hobby[1]}
获取请求头的信息:${header["User-Agent"]} <!-- 因为key里面头特殊符合,所有要用[],-->
headerValues 多个值的请求头比较少
获取Cookie的名称:${cookie.JSESSIONID.name} <!-- Cookie后面学-->
获取Cookie的值:${cookie.JSESSIONID.value}
获取上下文参数值:${initParam.username}
<!-- 下面是web.xml中-->
<context-param>
<param-name>username</param-name>
<param-value>context</param-value>
</context-param>
JSTL标签库
1. 概念
JSTL : JSP Standard Tag Library
JSP的标准标签库,是不断完善的开源标签库
EL表达式主要是为了替代JSP中的表达式脚本,而JSTL则是替代JSP中的代码脚本
JSTL里面能直接写EL表达式和HTML标签
JSTL 由五个不同功能的标签库组成:
功能范围 | URL | 前缀 |
---|---|---|
核心标签库(重点) | http://java.sun.com/jsp/jstl/core | c |
格式化 | http://java.sun.com/jsp/jstl/fmt | fmt |
函数 | http://java.sun.com/jsp/jstl/function | fn |
数据库(不使用) | http://java.sun.com/jsp/jstl/sql | sql |
XML(不使用) | http://java.sun.com/jsp/jstl/xml | x |
2. 使用
Ⅰ 先导入jstl标签库的 jar 包
Ⅱ 首先需要在jsp页面中用 taglib 指定 引入标签库 (idea能帮我们)
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
3. 核心标签库
-
<c:set>
作用:可以往域中保存数据
<!-- scope属性设置往那个域存数据, 有page:Pagecontext域(默认值),request:Resquest域,session:Session域,application:ServletContext域 var属性是key,value是值--> <c:set scope="request" var="abc" value="abcValue"> </c:set> !!!! == <% request.setAttribute("abc","abcValue"); %>
-
<c:if>
<!-- test属性表示判断的条件(使用EL表达式),没有if else--> <c:if test="${12 == 12}"> <div>12等于12</div> </c:if>
-
<c:choose> <c:when> <c:otherwise>
作用:用来做多路判断,类似switch…case…default
<!-- choose表示开始判断,when表示每一种判断情况,otherwise表示剩下的情况 注意:里面不要使用html注释,使用jsp注释。 when的父标签一定要是choose,例如在otherwise还要做多路判断,不要只加when,还需要加上choose标签--> <% request.setAttribute("height", 178); %> <c:choose> <c:when test="${requestScope.height > 190}"> <h1>巨人</h1> </c:when> <c:otherwise> <h2>剩下的</h2> </c:otherwise> </c:choose>
-
<c:forEach>
作用:遍历输出
<!-- begin,end开始结束的索引,var表示循环变量,也是当前正在遍历到的数据。下面是输出1到10--> <!-- step属性是步长值,类似是i++,默认是1 !!! varStatus是当前遍历元素的状态,status是个内部类的对象, 有很多方法getCurrent()当前遍历的数据和var一样。getIndex()遍历的下标。getCount()遍历的个数第几个。 isFirst(),isLast()当前遍历是不是第一个或最后一个, 虽然方法名不是get开头但也能这样使用${status.first} 因为返回值是bolean类型,方法名可以is开头。 getBegin(),getEnd(),getStop(),获取forEach标签中begin,end,step的属性值 <c:forEach begin="1" end="10" step="2" varStatus="status" var="i"> --> <c:forEach begin="1" end="10" var="i"> ${ i } <br/> </c:forEach> <!-- 把它放到表格里也行,相较于jsp的语法简单可读性好多了--> <table> <c:forEach begin="1" end="10" var="i"> <tr> <td>第 ${i} 行</td> </tr> </c:forEach> </table> <!-- 遍历Object数组,类似增强for循环--> <% request.setAttribute("arr", new String[]{"123", "456", "789"}); %> <!-- items属性是遍历的数据源,--> <!-- <c:forEach begin="1" end="2" items="${requestScope.arr}" var="s"> 这个也能加区间arr[1, 2],加步长 --> <c:forEach items="${requestScope.arr}" var="s"> ${s} </c:forEach> <!-- 遍历Map集合,和上面一样,每一个entry都是键值对, 类型是Map.Entry,这个内部类有getKey(),getValue方法,所以可以使用EL表达式--> <c:forEach items="${requestScope.map}" var="entry"> ${entry} <br/> ${entry.key} ==> ${entry.value} </c:forEach>