JSP转译成Servlet详细过程

JSP是Servlet的扩展,在没有JSP之前,就已经出现了Servlet技术。Servlet是利用输出流动态生成HTML页面,包括每一个HTML标签和每个在HTML页面中出现的内容。

由于包括大量的HTML标签、大量的静态文本及格式等,导致Servlet的开发效率极为低下。所有的表现逻辑,包括布局、色彩及图像等,都必须耦合在Java代码中,这的确让人不胜其烦。JSP的出现弥补了这种不足,JSP通过在标准的HTML页面中插入Java代码,其静态的部分无须Java程序控制,只有那些需要从数据库读取并根据程序动态生成信息时,才使用Java脚本控制。

从表面上看,JSP页面已经不再需要Java类,似乎完全脱离了Java面向对象的特征。事实上,JSP是Servlet的一种特殊形式,每个JSP页面就是一个Servlet实例——JSP页面由系统编译成Servlet,Servlet再负责响应用户请求。JSP其实也是Servlet的一种简化,使用JSP时,其实还是使用Servlet,因为Web应用中的每个JSP页面都会由Servlet容器生成对应的Servlet。对于Tomcat而言,JSP页面生成的Servlet放在work路径对应的Web应用下。

看下面一个简单的JSP页面:

<!-- 表明此为一个JSP页面 -->

<%@ page contentType="text/html; charset=gb2312" language="java" %>

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">

<HTML>

<HEAD>

<TITLE>第一个JSP页面</TITLE>

</HEAD>

<BODY>

<!-- 下面是Java脚本 Scriptlet-->

<%for(int i = 0 ; i < 10; i++)

{

out.println(i);

%>

<br>

<%}%>

</BODY>

</HTML>

当启动Tomcat之后,可以在Tomcat的Catalinalocalhostjsptestorgapachejsp目录下找到如下文件(假如Web应用名为jsptest,上面JSP页的名为test1.jsp):test1_jsp.java和test1_jsp.class。这两个文件都是Tomcat生成的,Tomcat根据JSP页面生成对应Servlet的Java文件及class文件。

下面是test1_jsp.java文件的源代码,这是一个特殊的Java类,是一个Servlet类:

//JSP页面经过Tomcat编译后默认的包(不同的servlet容器提供商生成的servlet文件是不同的)

package org.apache.jsp;

import javax.servlet.*;

import javax.servlet.http.*;

import javax.servlet.jsp.*;

//继承HttpJspBase类,该类其实是个HttpServlet的子类(jasper是tomcat的jsp engine)

public final class test1_jsp extends org.apache.jasper.runtime.HttpJspBase

implements org.apache.jasper.runtime.JspSourceDependent

{

private static java.util.Vector _jspx_dependants;

public java.util.List getDependants() {

return _jspx_dependants;

}

//用于响应用户的方法

public void _jspService(HttpServletRequest request,

HttpServletResponse response)

throws java.io.IOException, ServletException

{   //built-in objects(variavles) are created here.

//获得页面输出流

JspFactory _jspxFactory = null;

PageContext pageContext = null;

HttpSession session = null;

ServletContext application = null;

ServletConfig config = null;

//获得页面输出流

JspWriter out = null; //not PrintWriter. JspWriter is buffered defautly.

Object page = this;

JspWriter _jspx_out = null;

PageContext _jspx_page_context = null;

//开始生成响应

try

{

_jspxFactory = JspFactory.getDefaultFactory();

//设置输出的页面格式

response.setContentType("text/html; charset=gb2312");

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;

//输出流,开始输出页面文档

out.write("rn");

//下面输出HTML标签

out.write("<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0

Transitional//EN">rn");

out.write("<HTML>rn");

out.write("<HEAD>rn");

out.write("<TITLE>first Jsp</TITLE>rn");

out.write("</HEAD>rn");

out.write("<BODY>rn");

//页面中的循环,在此处循环输出

for(int i = 0 ; i < 10; i++)

{

out.println(i);

out.write("rn");

out.write("<br>rn");

}

out.write("rn");

out.write("</BODY>rn");

out.write("</HTML>rn");

out.write("rn");

}

catch (Throwable t)

{

if (!(t instanceof SkipPageException))

{

out = _jspx_out;

if (out != null && out.getBufferSize() != 0)

out.clearBuffer();

if (_jspx_page_context != null) _jspx_page_context.handle

PageException(t);

}

}

finally

{

if (_jspxFactory != null) _jspxFactory.releasePageContext(_jspx_

page_context);

}

}

}

根据图2.1的执行效果,再次对比test1.jsp和test1_jsp.java文件,可得到一个结论:该JSP页面中的每个字符都由test1_jsp.java文件的输出流生成。

根据上面的JSP页面工作原理图,可以得到如下四个结论:

— JSP文件必须在JSP服务器内运行。

— JSP文件必须生成Servlet才能执行。

— 每个JSP页面的第一个访问者速度很慢,因为必须等待JSP编译成Servlet。

— JSP页面的访问者无须安装任何客户端,甚至不需要可以运行Java的运行环境,因为JSP页面输送到客户端的是标准HTML页面。

JSP和Servlet会有如下转换:

- JSP页面的静态内容、JSP脚本都会转换成Servlet的xxxService()方法,类似于自行创建Servlet时service()方法。

- JSP声明部分,转换成Servlet的成员部分。所有JSP声明部分可以使用private,protected,public,static等修饰符,其他地方则不行。

- JSP的输出表达式(<%= ..%>部分),输出表达式会转换成Servlet的xxxService()方法里的输出语句。

- 九个内置对象要么是xxxService()方法的形参,要么是该方法的局部变量,所以九个内置对象只能在JSP脚本和输出表达式中使用。// 不能在jsp Declaration中使用

JSP转译成Servlet详细过程【转】的更多相关文章

  1. JSP转译成Servlet详细过程

    很多人都会认为JSP的执行性能会和Servlet相差很多,其实执行性能上的差别只在第一次的执行.因为JSP在执行第一次后,会被编译成 Servlet的类文件,即.class,当再重复调用执行时,就直接 ...

  2. jsp页面编译成Servlet类文件

    package org.apache.jsp; import javax.servlet.*; import javax.servlet.http.*; import javax.servlet.js ...

  3. JSP编译成Servlet(三)JSP编译后的Servlet

    JSP编译后的Servlet类会是怎样的呢?他们之间有着什么样的映射关系?在探讨JSP与Servlet之间的关系时先看一个简单的HelloWorld.jsp编译成HelloWorld.java后会是什 ...

  4. JSP源码、改写Servlet为JSP、查看转译成为Servlet的文件、JSP字符编码设置

    概述 在Servlet中编写HTML太麻烦了,应该使用JSP.JSP中可以直接编写HTML,使用指示.声明.脚本(scriptlet)等元素来堆砌各种功能,但JSP最后还是会被容器转译为Servlet ...

  5. JSP九大内置对象详细介绍

    内置对象的特点: 1.由JSP规范提供,不用编写者实例化. 2.通过Web容器实现和管理 3. 所有JSP页面均可使用 4.只有在脚本元素的表达式或代码段中才可使用(<%=使用内置对象%> ...

  6. jsp页面转发到servlet

    一个简单的例子来了解一下jsp页面转发到servlet的过程,环境 eclipse.tomcat 1.工程目录结构如下 2.各部分代码如下 1>index.jsp <%@ page lan ...

  7. JSP编译成Servlet(四)JSP与Java行关系映射

    我们知道java虚拟机只认识class文件,要在虚拟机上运行就必须要遵守class文件格式,所以JSP编译成servlet后还需要进一步编译成class文件,但从JSP文件到java文件再到class ...

  8. IDEA搭建SSMM框架(详细过程)

    IDEA搭建SSMM框架(详细过程) 相关环境 Intellij IDEA Ultimate Tomcat JDK MySql 5.6(win32/win64) Maven (可使用Intellij ...

  9. Tomcat配置(三):tomcat处理连接的详细过程

    */ .hljs { display: block; overflow-x: auto; padding: 0.5em; color: #333; background: #f8f8f8; } .hl ...

随机推荐

  1. JAVA之旅(十一)——RuntimeException,异常的总结,Package,jar包,多线程概述

    JAVA之旅(十一)--RuntimeException,异常的总结,Package,jar包,多程序概述 继续JAVA之旅 一.RuntimeException 在Exception种有一个特殊的子 ...

  2. iOS开发的10个知识点

    1.关于关键字volatile 一个定义为volatile的变量是说这变量可能会被意想不到地改变,这样,编译器就不会去假设这个变量的值了.精确地说就是,优化器在用到这个变量时必须每次都小心地重新读取这 ...

  3. 【Android 应用开发】Android资源文件 - 使用资源存储字符串 颜色 尺寸 整型 布尔值 数组

    . 作者 : 万境绝尘 转载请注明出处 : http://blog.csdn.net/shulianghan/article/details/19913755 . 一. Android资源文件简介 1 ...

  4. 某公司基于FineBI数据决策平台的试运行分析报告

    一.数据平台的软硬件环境 二.组织机构和权限体系 组织机构:平台中已集成一套组织机构,可以建立部门.人员.也可以与现有系统的组织机构集成,将组织机构导入到平台中. 功能权限:通过配置功能点URL的方式 ...

  5. C++链表模板类

    思想和上篇文章差不多,只是换了层包装. 直接上代码: // linklist.h #include <iostream> #include <cstdio> using nam ...

  6. J2EE进阶(一)随堂笔记

    进公司搞研发,基本上用的都是J2EE框架.若想在公司混个不错的地位,首先技术上必须过关.由于需求所致,自己学习了J2EE一段时间,主要是Struts2,MyBatis(Hibernate的前身),远远 ...

  7. C语言颜色转换宏

    C语言颜色转换宏 #define COLOR_BPP16_RGB555 /* Win RGB */ #define COLOR_RGB(r,g,b) ((COLORREF)(((BYTE)(r)|(( ...

  8. -lt -gt -ge -le -eq的意义

    脚本如下:#!/bin/bashx=0while [ $x -lt 10 ]doecho $xx=`echo "$x+1" | bc`done 请问这里的-lt是什么意思,请大家指 ...

  9. Linux管线命令 - cut,grep,sort,uniq,wc,tee,tr,col,join,paste,expand,split,xargs

    在每个管线后面接的第一个数据必定是『命令』喔!而且这个命令必须要能够接受 standard input 的数据才行,这样的命令才可以是为『管线命令』,例如 less, more, head, tail ...

  10. thrift实现HDFS文件操作

    thrift 文件如下 namespace java com.pera.file.transform struct  File{     1:string path ,     2:string co ...