教育行業(yè)A股IPO第一股(股票代碼 003032)

全國(guó)咨詢/投訴熱線:400-618-4000

JAVA培訓(xùn)之JSP原理

更新時(shí)間:2016年08月13日19時(shí)25分 來(lái)源:傳智播客JAVA培訓(xùn)學(xué)院 瀏覽次數(shù):

1.JSP原理分析

我們知道,jsp是動(dòng)態(tài)資源的一種,它包含HTML代碼,Java腳本以及jsp標(biāo)簽。在jsp入門(mén)中我們了解到,jsp彌補(bǔ)了Servlet和HTML的不足。其實(shí)jsp是一種特殊的Servle,后面我們會(huì)詳細(xì)介紹。動(dòng)態(tài)資源不能被瀏覽器直接顯示,需要翻譯成靜態(tài)資源后再發(fā)送給瀏覽器。下面,我們就來(lái)了解jsp是如何被翻譯成靜態(tài)資源。
分步驟解析jsp原理,如下所示:
  • 當(dāng)瀏覽器第一次訪問(wèn)jsp頁(yè)面時(shí),服務(wù)器會(huì)把jsp翻譯成一個(gè)Java文件,該Java類(lèi)是一個(gè)Servlet類(lèi);
  • 然后服務(wù)器再把Java文件編譯成class文件;
  • 接著創(chuàng)建該類(lèi)對(duì)象;
  • 最后調(diào)用該類(lèi)的service()方法;
  • 當(dāng)?shù)诙卧僭L問(wèn)該jsp頁(yè)面時(shí),直接調(diào)用jsp頁(yè)面對(duì)應(yīng)Java類(lèi)的service()方法。
由以上步驟可知,jsp被翻譯成Servlet后,服務(wù)器會(huì)為該Servlet類(lèi)創(chuàng)建對(duì)象,并常駐內(nèi)存,當(dāng)服務(wù)器關(guān)閉才銷(xiāo)毀。以后每次訪問(wèn)該jsp都會(huì)調(diào)用該jsp的Servlet類(lèi)的service()方法。如果jsp頁(yè)面被修改,那么再次訪問(wèn)時(shí),服務(wù)器會(huì)重新翻譯該jsp頁(yè)面。
下面,通過(guò)一張圖來(lái)了解第一次訪問(wèn)jsp頁(yè)面的流程圖,如圖1-1所示:

圖1-1 第一次訪問(wèn)jsp流程圖

2.jsp對(duì)應(yīng)Java文件分析

通過(guò)以上對(duì)jsp原理的理解,我們知道jsp文件會(huì)被服務(wù)器翻譯成對(duì)應(yīng)的Java文件,下面我們就對(duì)jsp對(duì)應(yīng)的Java文件進(jìn)行分析。在web應(yīng)用中,對(duì)index.jsp進(jìn)行編輯,如例1-1所示:
<%@ page language="java" import="java.util.*" pageEncoding="UTF-8"%>
<%
String path = request.getContextPath();
String basePath= request.getScheme()+"://"+request.getServerName()+":"
+request.getServerPort()+path+"/";
%>
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
  <head>
    <base href="<%=basePath%>">
    <title>My JSP 'index.jsp' starting page</title>
    <meta http-equiv="pragma" content="no-cache">
    <meta http-equiv="cache-control" content="no-cache">
    <meta http-equiv="expires" content="0">   
    <meta http-equiv="keywords" content="keyword1,keyword2,keyword3">
    <meta http-equiv="description" content="This is my page">
    <!--
    <link rel="stylesheet" type="text/css" href="styles.css">
    -->
  </head>
  <body>
    This is my JSP page. <br>
   <%
    int a = 10;
    %>
    <%
    out.print(a++);
    %>
    <br>
    使用Java腳本輸出a的值:  <%=a%>
    <br>
        <%!
    int a = 100;
    public void fun1() {
        System.out.println(a);
    }
       %>
    <%
    out.print(this.a++);
    fun1();
    %>
  </body>
</html>
當(dāng)?shù)谝淮卧L問(wèn)index.jsp后,服務(wù)器會(huì)將index.jsp翻譯成對(duì)應(yīng)的Java文件,文件名為index_jsp.java。該文件存放的目錄如圖1-2所示:

圖1-2 Java文件所在目錄
由圖1-2可知,jsp編譯后的Java文件都存放在tomcat安裝目錄的work/Catalina/localhos目錄中,其中Example15是項(xiàng)目名稱。
找到文件所在的目錄,點(diǎn)擊此處  查看index_jsp.java文件。下面來(lái)分析該文件的代碼,如下所示:
(1)在index.jsp文件中使用<%!%>腳本聲明了成員變量和成員方法,它們?cè)趇ndex_jsp.java中的位置如圖1-3所示:

圖1-3 成員所在位置
由圖1-3可知,該java文件的類(lèi)名就是index_jsp,它繼承了HttpJspBase類(lèi),這個(gè)類(lèi)是Tomcat定義的類(lèi)。該類(lèi)實(shí)現(xiàn)了Servlet接口,因此index_jsp類(lèi)也是Servlet類(lèi)。在index_jsp類(lèi)的成員位置定義了成員變量a,值為100,定義了成員方法fun1()。
(2)接著看index_jsp類(lèi)的service()方法,如圖1-4所示:

圖1-4 service方法
由圖1-4可知,在index_jsp類(lèi)中,service()方法的名字是_jspService。我們知道jsp有九大內(nèi)置對(duì)象,我們可以由圖1-4看出,在_jspService()方法中,定義了6個(gè)變量,分別是session,application,config,out,page,pageContext。由于在_jspService()方法中定義了,因此再jsp頁(yè)面中我們可以直接使用這些變量,另外,其他三個(gè)內(nèi)置對(duì)象:request、response是做為參數(shù)傳遞給了_jspService()方法,exceptionn在后面我們會(huì)講解。
(3)每次一請(qǐng)求,服務(wù)器都會(huì)調(diào)用_jspService()方法,那么瀏覽器中顯示的頁(yè)面信息必然和該放方法有關(guān),下面我們來(lái)了解如何將頁(yè)面中的信息顯示在瀏覽器,如圖1-5所示:

圖1-5 輸出頁(yè)面信息
圖1-5所示中,index.jsp頁(yè)面中<%%>里面的代碼在index_jsp.java文件中出現(xiàn)的位置是_jspService()方法中,并且按原樣顯示,而其他的HTML代碼都是以字符串的形式通過(guò)out對(duì)象調(diào)用write()方法輸出到瀏覽器端。其中:
<base href="<%=basePath%>">
<%= basePath%>被out.print(basePath)方法輸出在瀏覽器端。out對(duì)象的writer()方法和print()方法沒(méi)有什么區(qū)別,這樣用是為了區(qū)別HTML代碼和Java代碼的輸出。
(4)下面來(lái)看在jsp中使用for循環(huán),在index_jsp.java中是如何顯示的,如圖1-6所示:

圖1-6 for循環(huán)
由圖1-6可知,在for循環(huán)中,使用out.write()方法將HTML代碼輸出,對(duì)應(yīng)在頁(yè)面中的代碼如下所示:
<%
    for(int i = 0; i < 10; i++) {
%> 
    <tr>
       <td>張三</td>
       <td>29</td>
    </tr>
<% } %>
(5)在_jspService()方法中,有一個(gè)異常處理,如圖1-7所示:

圖1-7 異常處理
當(dāng)執(zhí)行_jspService()方法過(guò)程中,出現(xiàn)了異常,那么圖1-7中的代碼就會(huì)捕獲該異常,并進(jìn)行處理。出現(xiàn)異常之前的代碼不會(huì)被輸出在瀏覽器端,服務(wù)器會(huì)給瀏覽器端響應(yīng)500狀態(tài)碼。并且地址欄地址不變,可以理解為服務(wù)器在做轉(zhuǎn)發(fā),我們知道在進(jìn)行轉(zhuǎn)發(fā)時(shí),response響應(yīng)輸出流中的信息會(huì)被清空,因此之前的向response緩沖區(qū)存放的信息不會(huì)顯示在瀏覽器端。

本文版權(quán)歸傳智播客Java培訓(xùn)學(xué)院所有,歡迎轉(zhuǎn)載,轉(zhuǎn)載請(qǐng)注明作者出處。謝謝!
作者:傳智播客Java培訓(xùn)學(xué)院
首發(fā):http://m.8y3kgpwe.cn/javaee
0 分享到:
和我們?cè)诰€交談!