JSP九大內建物件解析、JSP指令(page、include)、靜態聯編概述

淺然_發表於2018-04-02

部落格目錄

1、JSP九大內建物件
2、JSP指令(page指令、include指令)
3、靜態聯編

一、JSP九大內建物件

這裡寫圖片描述

1、JSP內建物件特點

  • 由JSP規範提供,不由編寫者例項化
  • 通過Web容器實現和管理
  • 所以JSP頁面均可使用
  • 只有在JSP表示式塊和程式碼塊中才可以使用<%= %>,<% %>

2、九大內建物件位置——編譯後的Servlet檔案中

這裡寫圖片描述

public void _jspService(final javax.servlet.http.HttpServletRequest request, final javax.servlet.http.HttpServletResponse response)
        throws java.io.IOException, javax.servlet.ServletException {

final java.lang.String _jspx_method = request.getMethod();
if (!"GET".equals(_jspx_method) && !"POST".equals(_jspx_method) && !"HEAD".equals(_jspx_method) && !javax.servlet.DispatcherType.ERROR.equals(request.getDispatcherType())) {
response.sendError(HttpServletResponse.SC_METHOD_NOT_ALLOWED, "JSPs only permit GET POST or HEAD");
return;
}

    final javax.servlet.jsp.PageContext pageContext;
    javax.servlet.http.HttpSession session = null;
    final javax.servlet.ServletContext application;
    final javax.servlet.ServletConfig config;
    javax.servlet.jsp.JspWriter out = null;
    final java.lang.Object page = this;
    javax.servlet.jsp.JspWriter _jspx_out = null;
    javax.servlet.jsp.PageContext _jspx_page_context = null;


    try {
      response.setContentType("text/html; charset=UTF-8");
      pageContext = _jspxFactory.getPageContext(this, request, response,
                null, true, 8192, true);
      _jspx_page_context = pageContext;
      application = pageContext.getServletContext();
      config = pageContext.getServletConfig();
      session = pageContext.getSession();
      out = pageContext.getOut();
      _jspx_out = out;

在編譯頁面後,類Servlet一般都會有如上所示的結構,其中內建物件request和response是_jspService()方法的形參,當Tomcat呼叫該方法是會初始化這兩個物件。而page、pageContext、application、config、session、out都是方法_jspService()的區域性變數,由該方法完成初始化


3、pageContext物件

pageContext代表JSP頁面的上下文,功能是訪問JSP之間的所有共享資料。使用pageContext物件可以訪問page、request、session、application範圍的變數,還可以獲取其他內建物件如下

  • ServletRequest getRequest():獲取request物件
  • ServletResponse getResponse():獲取response物件
  • ServletConfig getServletConfig():獲取config物件
  • ServletContext getServletContext():獲取application物件
  • HttpSession getSession():獲取session物件

一旦JSP和Servlet程式設計中獲取了pageContext物件,就可以通過它提供的方法來獲取其他內建物件


4、request物件

內建物件request是JSP中最重要物件之一,每個request物件封裝了一次使用者請求,並且所有的請求引數都被封裝在request物件中,因此request物件是獲取請求引數的重要途徑

例(一個表單處理例子)

index.html

<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>Insert title here</title>
</head>
<body>
    <form id="form1" method="post" action="request.jsp">
    使用者名稱:<br>
    <input type="text" name="name"><hr>
    性別:<br>
    男:<input type="radio" name="gender" value="男">
    女:<input type="radio" name="gender" value="女">
    <br>
    喜歡的顏色:<br>
    紅:<input type="checkbox" name="color" value="紅">
    綠:<input type="checkbox" name="color" value="綠">
    藍:<input type="checkbox" name="color" value="藍">
    <br>
    來自的國家:<br>
    <select name="country">
        <option value="AA">AAA</option>
        <option value="BB">BBB</option>
        <option value="CC">CCC</option>
    </select>
    <hr>
    <input type="submit" value="提交">
    <input type="reset" value="重置">
    </form>
</body>
</html>

request.jsp

<%@page import="java.util.Enumeration"%>
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
    <%
        //獲取所有請求頭的名稱
        Enumeration<String> headerNames=request.getHeaderNames();
        while(headerNames.hasMoreElements())
        {
            String headerName=headerNames.nextElement();
            //獲取每個請求及其對應的值
            out.println(headerName+"-->"+request.getHeader(headerName)+"<br/>");
        }
        out.println("<hr>");
        //設定解碼方式,簡體中文使用gb2312解碼
        request.setCharacterEncoding("utf-8");

        //下面依次獲取表單域的值
        String name=request.getParameter("name");
        String gender=request.getParameter("gender");

        //如果某個請求引數有多個值,將使用該方法獲取多個值
        String[] color=request.getParameterValues("color");
        String national=request.getParameter("country");

    %>
        <!-- 下面依次輸出表單域的值 -->
        你的姓名:<%=name %><br>
        你的性別:<%=gender %><br>

        <!-- 輸出核取方塊獲取的陣列值 -->
        你喜歡的顏色:
        <%
            for(String c:color){out.println(c+" ");}
        %>
        <hr>
        你來自的國家:<%=national %><hr>
</body>
</html>
使用者請求方式及結果

這裡寫圖片描述



這裡寫圖片描述


5、session物件

JSP中的session是指一個終端使用者與互動系統進行通訊的時間間隔,通常指從註冊進入系統到登出退出系統之間所經過的時間,在JSP頁面中,session的會話是HttpSession類的例項


6、application物件

因為application物件代表Web應用本身,所以使用application來操作Web應用的相關資料。application物件實現了使用者間資料的共享,可以存放全域性變數。application開始於伺服器的啟動,直到伺服器關閉時結束,在這段時間內application物件一直存在。在使用者的前後連線或不同使用者之間的連線中,可以對此物件的同一屬性進行操作,在任何地方對此物件屬性的操作,都將影響到其他使用者的訪問。伺服器的啟動和關閉決定了application物件的生命。application物件是ServletContext類的例項


7、response物件

response物件把作為JSP頁面處理結果返回給使用者的響應儲存在該物件中,並提供了設定響應內容,響應頭以及重定向的方法,例如cookie、頭資訊等,在大多數情況下,程式無法使用response來響應客戶端請求,因為使用out響應物件的方法更簡單。但是out是JspWriter的例項,JspWriter是Writer的子類,Writer是字元流,無法輸出非字元內容,如果需要在JSP頁面動態生成一幅點陣圖,或者輸出一個pdf文件,使用out作為響應物件無法完成,此時必須使用response作為響應輸出


8、config物件

在JSP頁面中,物件config代表當前JSP配置資訊,該物件在JSP頁面中比較少用,常用在Servlet中


9、out物件

物件out代表一個頁面輸出流,功能是在頁面上輸出變數值及常量。通常使用在輸出表示式的地方都可以使用out物件來達到同樣的效果,輸出物件out中常用的方法如下

  • print或println:輸出資料
  • newLine:輸出換行字元
  • flush:輸出緩衝區資料
  • close:關閉輸出流
  • clear:清除緩衝區中資料,但不輸出到客戶端
  • clearBuffer:清除緩衝區中資料,輸出到客戶端
  • getBufferSize:獲得緩衝區大小
  • getRemaining:獲得緩衝區中沒有被佔用的空間
  • isAutoFlush:是否為自動輸出
<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
    <%
        int sum=5;
        out.println(5);
    %>
</body>
</html>
客戶瀏覽器顯示結果

這裡寫圖片描述


10、exception物件

物件exception是Throwable的例項

功能:表示JSP指令碼程式中產生的錯誤和異常。因為JSP指令碼包含的所有可能出現的異常都可以叫誒處理頁面處理,所以JSP程式設計師不要處理異常,即使該異常是checked異常

在JSP中,被呼叫的錯誤頁面的結果,只有在錯誤頁面中才可使用,也就是說在頁面指令中設定
<%@ page isErrorPage="true"%>
異常處理

index.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    errorPage="error.jsp"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>JSP異常機制</title>
</head>
<body>
    <%
        int a=9;
        int c=a/0;
    %>
</body>
</html>

error.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    isErrorPage="true"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>異常處理頁面</title>
</head>
<body>
    異常型別:<%out.println(exception.getClass()); %>
    異常資訊:<%out.println(exception.getMessage()); %>
</body>
</html>

瀏覽器異常結果

這裡寫圖片描述


二、JSP指令(page指令、include指令)

1、JSP指令分類

  • page指令:頁面指令
  • include指令:包含指令
  • taglib指令:標籤庫指令(之後的部落格再對該指令解析)

2、JSP指令作用

  • 為當前頁面做一些基本屬性設定
  • 為當前頁面的執行提供基本環境

3、語法格式

<%@ 指令名稱 屬性名=屬性值 屬性名=屬性值....%>

4、page指令

常用的屬性
<%@ page
 language="java"
 contentType="text/html; charset=UTF-8"
 errorPage="error.jsp"
 pageEncoding="UTF-8"
 import="java.util.*"
 session="true"
 buffer="none|8kb|size kb"
 autoFlush="true"
 isErrorPage="false" 
 %>
解析
  • language:宣告當前JSP頁面使用的指令碼語言,因為是JSP頁面,所以預設是Java,也只能是Java
  • contentType:用於設定生成的網頁的檔案格式和編碼字符集,即MIME型別和頁面字符集型別。預設的MIME是text/html,預設的字符集型別是ISO-8859-1
  • errorPage:設定錯誤處理頁面,如果出現異常,跳轉到指定錯誤頁面
  • pageEncoding:設定生成網頁的編碼字符集
  • import:用於匯入包,以下幾個包預設自動匯入,不用顯示匯入
    • java.lang.* \javax.Servlet.* \javax.Servlet.jsp.* \javax.Servlet.http.*
  • session:設定這些JSP頁面是否需要HTTPSession
  • buffer:設定輸出緩衝區的大小。輸出緩衝區的JSP內建物件out用於快取JSP頁面對客戶瀏覽器的輸出,預設值是8kb,也可以設定為none,也可為其他值,單位是kb
  • autoFlush:當輸出緩衝區即將溢位時,設定是否需要強制輸出緩衝區的內容。如果設定為true則表示正常輸出,如果設定為false,表示會在buffer溢位是產生一個異常
  • isErrorPage:設定本JSP頁面是否錯誤處理程式

5、include指令 <%@ include file=”/xxx.jsp”%>

  • JSP中使用include指令後,可以將一個外部檔案嵌入到當前的JSP檔案中,同時解析這個頁面的JSP語句
  • include指令是一個靜態的include語句,能夠把目標頁面的其他編譯指令也包含進來,兩個檔案的變數是通用的
  • include指定包含的檔案可以是JSP,也可以是HTML

index.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
    This is index.jsp<br>
    <%@include file="/other.jsp" %>
    <br>
    <%
        out.println(otherName);
    %>
</body>
</html>

other.jsp

<%@ page language="java" contentType="text/html; charset=UTF-8"
    pageEncoding="UTF-8"%>
<!DOCTYPE html PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>Insert title here</title>
</head>
<body>
    this is other.jsp
    <%
        String otherName="other99999";
    %>
</body>
</html>

客戶瀏覽器顯示結果

這裡寫圖片描述


三、靜態聯編

根據以上include指令後,檢視Tomcat的work下的相關子目錄,只生成了一個index_jsp.java的Servlet原始檔,並沒有生成other_jsp.java檔案

因為JSP翻譯引擎在翻譯時,會將include指令所指定的檔案內容直接翻譯到當前JSP對應的Servlet中,形成一個.java檔案。

這就說明一個問題,這個是包含操作,是在編譯之前完成的,在編譯之前由JSP翻譯引擎完成的,不是在程式執行期完成的,這種包含是一種靜態包含————靜態聯編

這裡寫圖片描述

使用include指令的優點

因為有些網站的頭部底部左側,在很多頁面都是相同的,使用include可以減少重複性工作,可以使用include指令,實現“一改全改”效果

相關文章