Java Server Pages与JavaBeans使用指南
1. 使用页面指令
页面指令是一种JSP元素,用于设置将JSP转换为Servlet的选项。其基本格式为:
<%@ page attribute=value %>
其中,属性可以是表1中列出的任何属性(还有一些其他属性,但很少使用)。
| 属性名称 | 描述 |
|---|---|
| import=”package.class” | 向Servlet添加导入语句,以便在其他JSP元素中使用类时无需完全限定类名。 |
| content-Type=”MIME-type“ | 指定Servlet创建的文档类型,默认值为text/html,很少需要更改。 |
| isThreadSafe=”boolean” | 如果为true,则假设Servlet是线程安全的;如果为false,则在Servlet类声明中添加implements SingleThreadModel,使线程以单线程模式运行,默认值为true。 |
| session=”boolean” | 如果为true,则Servlet使用会话管理,默认值为true。 |
| buffer=”size” | 指定out变量使用的缓冲区大小,默认值取决于服务器,但不小于8K。 |
| errorPage=”URL” | 指定当Servlet抛出未捕获的异常时显示的错误页面的名称。 |
| isErrorPage=”boolean” | 如果为true,则此页面是其他JSP页面的错误页面,默认值为false。 |
最常用的页面指令是import,它允许导入API类的包,以便在表达式、脚本片段和声明元素中使用这些类。例如,导入java.util包的页面指令如下:
<%@ page import=”java.util.*” %>
页面指令可以放在JSP文档的任何位置,但建议放在顶部或靠近顶部。
2. 使用表达式
JSP表达式是任何计算结果为字符串的Java表达式。实际上,表达式不必直接计算。例如,使用java.util.Date类显示当前日期和时间的表达式如下:
<%=new java.util.Date()%>
该表达式创建一个java.util.Date()类的新实例,它表示当前日期和时间。toString()方法会被隐式调用,将此对象转换为字符串。
如果包含页面导入指令,则可以省略表达式中的限定符。例如:
<%@ page import=”java.util” %>
<%=new Date()%>
为了使用表达式做更有趣的事情,可以使用预定义变量,也称为隐式对象。这些是在整个JSP页面的表达式、脚本片段或声明中可用的Java变量。表2列出了最常用的JSP隐式对象。
| 名称 | 描述 |
|---|---|
| out | 用于将数据写入响应,相当于Servlet中的response.getWriter()。 |
| request | 请求对象,相当于Servlet的doGet或doPost方法中的请求参数。 |
| response | 响应对象,相当于Servlet的doGet或doPost方法中的响应参数。 |
| session | 用于管理会话,相当于Servlet中的request.getSession()。 |
隐式对象的工作方式与Servlet中对应的对象相同。例如,响应对象实际上就是传递给doGet或doPost方法的响应参数。
在表达式中最常用的隐式对象是请求对象。特别是,可以使用其getParameter方法获取用户在表单中输入的值。例如,显示名为Name的输入字段中输入的值的表达式如下:
<%= request.getParameter(“Name”)%>
以下是一个简单的JSP示例,名为InputJSP.jsp,它显示一个输入文本框和一个按钮。当用户单击按钮时,输入字段中输入的任何文本将显示在按钮下方:
<html>
<head>
<title>Input JSP</title>
</head>
<body>
<form action=”InputJSP.jsp” method=”post”>
Enter some text:
<input type=”text” name=”Text”>
<br><br>
<input type=”submit” value=”Submit”>
</form><br>
<h3>You entered:
<%= request.getParameter(“Text”)%></h3>
</body>
</html>
这个JSP的HTML定义了一个表单,其中包含一个名为Text的输入文本字段和一个提交按钮。当用户单击提交按钮时,会向服务器发送一个HTTP POST请求,请求InputJSP.jsp。用户输入的任何文本都会随请求一起发送。当Servlet运行时,表达式request.getParameter(“Text”)会检索文本并显示在按钮下方。
3. 使用脚本片段
脚本片段是直接插入到Servlet中的一个或一组语句,插入位置是生成周围HTML的out.print语句所在的位置。简而言之,脚本片段允许将自己的代码添加到渲染页面的代码中。
脚本片段遵循以下基本形式:
<% statements... %>
例如,以下是一个名为DateJSP.jsp的JSP,它使用DateFormat类格式化日期并将其显示在页面上:
<html>
<%@ page import=”java.text.*” %>
<%@ page import=”java.util.*” %>
<head>
<title>Date JSP</title>
</head>
<body>
<h1>
Today is
<%
DateFormat df = DateFormat.getDateInstance(
DateFormat.FULL);
Date today = new Date();
String msg = df.format(today);
out.println(msg);
%>
</h1>
<h1>Have a nice day!</h1>
</body>
</html>
这个JSP以一对页面导入指令开始,导入java.text和java.util包。然后,以下Java语句被插入到生成文本“Today is”和“Have a nice day!”的行之间:
DateFormat df = DateFormat.getDateInstance(DateFormat.FULL);
Date today = new Date();
String msg = df.format(today);
out.println(msg);
这些行创建一个名为msg的字符串变量,然后使用out.println将字符串写入响应输出。结果,格式化的日期被插入到
<h1>Today is </h1>
和
<h1>Have a nice day!</h1>
之间。
脚本片段不必向HTML输出添加任何内容。在许多情况下,它们执行诸如将信息写入文件之类的功能。例如,假设有一个JSP从包含名为FirstName和LastName的输入文本字段的表单中获取数据。假设有一个名为CustFile的类,其中有一个名为writeCustomer的静态方法,该方法接受名字和姓氏作为参数,并将它们写入文件。以下是一个获取名字和姓氏并调用writeCustomer方法将姓名写入客户文件的脚本片段:
<% String firstName =
request.getParameter(“FirstName”);
String lastName = request.getParameter(“LastName”);
CustFile.writeCustomer(firstName, lastName);
%>
如果愿意,可以巧妙地使用脚本片段。没有规则规定必须在单个脚本片段中完成块语句(如if或while语句)。如果在脚本片段的末尾保留一个块打开状态,则后续的任何HTML都由包含在该块中的out.print语句生成。唯一的限制是最终必须用另一个脚本片段结束该块。
例如,以下是一个名为LoopyJSP.jsp的脚本片段,它通过将一行文本包含在for循环的块中,在页面上重复该行12次:
<html>
<head>
<title>Can’t you see I’m trying to work here?</title>
</head>
<body>
<% for (int i = 0; i < 12; i++)
{
%>
All work and no play makes Jack a dull boy.<br>
<%
}
%>
</body>
</html>
4. 使用声明
声明是包含在Servlet中但在任何方法之外的代码。声明用于创建可以在表达式、脚本片段或其他声明中使用的类变量或方法。声明遵循以下格式:
<%! statements... %>
声明可以放在JSP的任何位置。
例如,以下是一个声明一个静态类字段count的Servlet,每次显示页面时该字段都会递增:
<html>
<%@ page import=”java.text.*” %>
<%@ page import=”java.util.*” %>
<head>
<title>Counter JSP</title>
</head>
<body>
<h1>
This JSP has been displayed <%= count++ %>
time.</h1>
</body>
</html>
<%!
private static int count = 1;
%>
在这个Servlet中,count变量由JSP文档末尾的声明元素声明:
<%!
private static int count = 1;
%>
然后,文档主体中的表达式显示并递增count变量:
<%= count++ %>
运行时,JSP会显示自服务器启动以来页面显示的次数。
另一个例子是声明一个在表达式中调用的方法:
<html>
<%@ page import=”java.text.*” %>
<%@ page import=”java.util.*” %>
<head>
<title>Date JSP</title>
</head>
<body>
<h1>
Today is <%= getDate() %></h1>
<h1>Have a nice day!</h1>
</body>
</html>
<%!
private String getDate()
{
DateFormat df =
DateFormat.getDateInstance(DateFormat.FULL);
Date today = new Date();
return df.format(today);
}
%>
文档末尾的声明声明了一个返回当前日期字符串的方法。然后,表达式
<%= getDate() %>
用于将日期插入到文档中。
5. 使用类
大多数JSP应用程序都足够复杂,需要额外的类来管理代码。例如,可能需要创建处理应用程序文件或数据库I/O的类,还可能需要创建表示业务对象(如产品或客户)的类。
设置Tomcat以使用类可能有点棘手,但遵循以下简单准则就很容易:
1. 将所有类包含在包中。为应用程序选择一个合适的包名,然后在每个类文件的开头添加包语句。
2. 将类文件(不一定是源文件)存储在JSP页面所在目录下的WEB-INF\classes\package\目录中。例如,如果将JSP页面存储在c:\tomcat\webapps\ROOT\Movies中,使用的包名是movie,则将类文件保存在以下目录中:
C:\tomcat\webapps\ROOT\Movies\WEB-INF\classes\movie
- 如果愿意,可以将类文件保存在c:\tomcat\shared\classes\package中,其中package是包的名称。这样,这些类对任何JSP或Servlet都可用。
- 任何使用这些类的JSP都必须包含一个导入该包的页面指令。例如:
<%@ page import=”movie.*” %>
- 将保存包的目录添加到ClassPath环境变量中。注意,要添加包含包的目录,而不是包含类本身的目录。这是因为Java编译器使用包名来查找包目录。因此,如果将类放在shared\classes目录中,则需要将c:\tomcat\shared\classes添加到ClassPath中。
为了说明JSP如何使用类,下面展示一个列出movies.txt文件中电影的JSP示例。
<!doctype html public “-//W3C//DTD HTML 4.0 Transitional//EN”>
<%@ page import=”movie.*” %>
<%@ page import=”java.util.*” %>
<html>
<head>
<title>List Movies: The Servlet</title>
</head>
<body>
<h1>Some of My Favorites</h1>
<h3>
<%= getMovieList() %>
</h3>
</body>
</html>
<%!
private String getMovieList()
{
String msg = “”;
ArrayList movies = MovieIO.getMovies();
for (int i = 0; i < movies.size(); i++)
{
Movie m = (Movie)movies.get(i);
msg += m.year + “: “;
msg += m.title + “<br>”;
}
return msg;
}
%>
以下是这个JSP的关键行解释:
- 第3行:JSP包含两个页面指令,导入movie和java.util包。
- 第12行:使用表达式调用getMovieList方法,该方法返回要显示的电影列表的字符串。
- 第18行:getMovieList方法在声明中定义。
- 第21行:调用MovieIO类的getMovies方法,以检索包含movies.txt文件中所有电影的ArrayList。
- 第22行:使用老式的for循环而不是增强for循环从ArrayList中获取电影,以避免使用Java 1.5的特性。
- 第24行:从ArrayList中检索Movie对象,并将年份和标题添加到msg字符串中。注意,从ArrayList中检索的对象必须强制转换为Movie对象。
- 第28行:返回完成的msg字符串。
Movie类的代码如下:
package movie;
public class Movie
{
public String title;
public int year;
public double price;
public Movie(String title, int year, double price)
{
this.title = title;
this.year = year;
this.price = price;
}
}
MovieIO类的代码如下:
package movie;
import java.io.*;
import java.util.*;
public class MovieIO
{
public static ArrayList<Movie> getMovies()
{
ArrayList<Movie> movies = new ArrayList<Movie>();
BufferedReader in =
getReader(“g:\\data\\movies.txt”);
Movie movie = readMovie(in);
while (movie != null)
{
movies.add(movie);
movie = readMovie(in);
}
return movies;
}
private static BufferedReader getReader(String name)
{
BufferedReader in = null;
try
{
File file = new File(name);
in = new BufferedReader(
new FileReader(file) );
}
catch (FileNotFoundException e)
{
System.out.println(“The file doesn’t exist.”);
System.exit(0);
}
catch (IOException e)
{
System.out.println(“I/O Error”);
System.exit(0);
}
return in;
}
private static Movie readMovie(BufferedReader in)
{
String title;
int year;
double price;
String line = “”;
String[] data;
try
{
line = in.readLine();
}
catch (IOException e)
{
System.out.println(“I/O Error”);
System.exit(0);
}
if (line == null)
return null;
else
{
data = line.split(“\t”);
title = data[0];
year = Integer.parseInt(data[1]);
price = Double.parseDouble(data[2]);
return new Movie(title, year, price);
}
}
}
6. JavaBeans的概念
JavaBean是一种特殊类型的Java类,可以以多种有趣的方式使用,以简化程序开发。一些Bean(如Swing组件)被设计为可视化组件,可在GUI编辑器中快速构建用户界面。其他Bean(称为Enterprise JavaBeans)被设计为在特殊的EJB服务器上运行,并可以运行大型Web应用程序的数据访问和业务逻辑。
这里关注的是一种更简单的JavaBean,旨在简化构建Java Server Pages的任务。简而言之,可以使用简单的JavaBeans构建Java Server Pages,而无需在JSP本身中编写任何Java代码。JavaBeans允许通过在JSP页面中使用类似HTML的特殊标签来访问Java类。
7. 什么是JavaBean
简单地说,JavaBean是任何符合以下规则的Java类:
- 必须有一个空构造函数,即不接受任何参数的构造函数。如果类根本没有构造函数,则符合条件,因为默认构造函数没有参数。但如果类至少有一个接受一个或多个参数的构造函数,则必须还有一个无参数的构造函数才能符合JavaBean的条件。
- 不能有公共实例变量。类定义的所有实例变量必须是私有或受保护的。
- 必须提供名为getProperty和setProperty的方法,以获取和设置类提供的任何属性的值,但布尔属性使用isProperty来获取属性值。
属性这个术语实际上不是官方的Java术语。简而言之,属性是对象的任何可以通过get方法(如果属性是布尔类型,则使用is方法)检索或通过set方法设置的值。例如,如果一个类有一个名为lastName的属性,它应该使用名为getLastName的方法来获取姓氏,使用setLastName的方法来设置姓氏。或者,如果类有一个名为taxable的布尔属性,设置它的方法称为setTaxable,检索它的方法称为isTaxable。
注意,一个类不必有任何属性才能成为JavaBean,但如果有属性,则必须按照这种命名模式访问这些属性。此外,并非所有属性都必须同时有get和set访问器。只读属性可以只有get访问器,只写属性可以只有set访问器。
属性名在访问它的方法中是大写的,但属性名本身不是。因此,setAddress设置的是名为address的属性,而不是Address。
更高级的Bean还可以有其他特性,允许它们有可视化界面,以便在IDE中以拖放方式使用。有些Bean实现了一个接口,允许将它们的状态写入输出流,以便以后重新创建。但这些特性是可选的;任何满足上述三个条件的类都是Bean,并且可以在JSP页面中作为Bean使用。
8. 示例Bean分析
以下是一个名为Triangle的示例JavaBean类,它计算勾股定理,即如果知道直角三角形的两条短边的长度,则可以计算出长边的长度。
package calculators;
public class Triangle
{
private double sideA;
private double sideB;
public Triangle()
{
this.sideA = 0.0;
this.sideB = 0.0;
}
public String getSideA()
{
return Double.toString(this.sideA);
}
public void setSideA(String value)
{
try
{
this.sideA = Double.parseDouble(value);
}
catch (Exception e)
{
this.sideA = 0.0;
}
}
public String getSideB()
{
return Double.toString(this.sideB);
}
public void setSideB(String value)
{
try
{
this.sideB = Double.parseDouble(value);
}
catch (Exception e)
{
this.sideB = 0.0;
}
}
public String getSideC()
{
if (sideA == 0.0 || sideB == 0.0)
return “Please enter both sides.”;
else
{
Double sideC;
sideC = Math.sqrt(
(sideA * sideA) + (sideB * sideB));
return Double.toString(sideC);
}
}
}
这个Bean类的要点如下:
- 第1行:与大多数Servlet类一样,这个Bean是一个包的一部分。在这种情况下,包名为calculators。
- 第5行:这个类使用一对实例变量来跟踪两条短边。根据JavaBeans的规则,这些实例变量被声明为私有。
- 第8行:声明了一个无参数的构造函数。(严格来说,这里不必显式编写这个构造函数,因为默认构造函数就可以完成任务,并且两个实例变量会自动初始化为默认值零。)
- 第14行:getSideA方法以字符串形式返回sideA属性的值。
- 第19行:setSideA方法允许使用字符串设置sideA属性的值。该方法使用try/catch语句捕获如果字符串无法解析为双精度数时抛出的异常。如果字符串无效,则sideA属性设置为零。
- 第31行:getSideB方法以字符串形式返回sideB属性的值。
- 第36行:setSideB方法从字符串设置sideB属性的值。同样,try/catch语句捕获任何异常,并在字符串无法解析为双精度数时将属性设置为零。
通过以上内容,可以了解到Java Server Pages和JavaBeans的基本使用方法,包括页面指令、表达式、脚本片段、声明、类的使用以及JavaBeans的定义和示例。这些技术可以帮助开发者更高效地构建Web应用程序。
Java Server Pages与JavaBeans使用指南
9. 在JSP页面中使用JavaBeans
在JSP页面中使用JavaBeans可以简化代码编写,提高代码的可维护性。下面介绍几种在JSP中使用JavaBeans的常见方式。
9.1 使用
<jsp:useBean>
标签
<jsp:useBean>
标签用于在JSP页面中实例化或查找一个JavaBean对象。其基本语法如下:
<jsp:useBean id="beanName" class="package.ClassName" scope="scope">
<!-- 可以包含 <jsp:setProperty> 标签来设置属性 -->
</jsp:useBean>
-
id:指定JavaBean对象的名称,在JSP页面中可以通过这个名称来引用该对象。 -
class:指定JavaBean类的全限定名。 -
scope:指定JavaBean对象的作用域,可选值有page、request、session和application,默认为page。
例如,使用前面的
Triangle
Bean:
<jsp:useBean id="triangle" class="calculators.Triangle" scope="page">
<jsp:setProperty name="triangle" property="sideA" value="3"/>
<jsp:setProperty name="triangle" property="sideB" value="4"/>
</jsp:useBean>
<h3>Side C: <%= triangle.getSideC() %></h3>
在这个例子中,首先使用
<jsp:useBean>
标签实例化了一个
Triangle
Bean对象,然后使用
<jsp:setProperty>
标签设置了
sideA
和
sideB
属性的值,最后通过表达式输出
sideC
的值。
9.2 使用
<jsp:setProperty>
标签
<jsp:setProperty>
标签用于设置JavaBean对象的属性值。其基本语法有以下几种形式:
- 设置单个属性值:
<jsp:setProperty name="beanName" property="propertyName" value="value"/>
- 从请求参数中设置属性值:
<jsp:setProperty name="beanName" property="propertyName" param="requestParameterName"/>
- 设置所有属性值(根据请求参数名与属性名匹配):
<jsp:setProperty name="beanName" property="*"/>
例如,假设有一个包含
sideA
和
sideB
输入字段的表单:
<form action="triangle.jsp" method="post">
Side A: <input type="text" name="sideA"><br>
Side B: <input type="text" name="sideB"><br>
<input type="submit" value="Submit">
</form>
在
triangle.jsp
中可以这样使用JavaBean:
<jsp:useBean id="triangle" class="calculators.Triangle" scope="request">
<jsp:setProperty name="triangle" property="*"/>
</jsp:useBean>
<h3>Side C: <%= triangle.getSideC() %></h3>
10. 创建简单的购物车
使用JavaBeans和会话作用域可以创建一个简单的购物车。下面是实现步骤:
10.1 定义商品类
首先,定义一个表示商品的JavaBean类,例如
Product
类:
package shopping;
public class Product {
private String name;
private double price;
public Product() {}
public Product(String name, double price) {
this.name = name;
this.price = price;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public double getPrice() {
return price;
}
public void setPrice(double price) {
this.price = price;
}
}
10.2 定义购物车类
创建一个
ShoppingCart
类来管理购物车中的商品:
package shopping;
import java.util.ArrayList;
import java.util.List;
public class ShoppingCart {
private List<Product> products;
public ShoppingCart() {
products = new ArrayList<>();
}
public void addProduct(Product product) {
products.add(product);
}
public List<Product> getProducts() {
return products;
}
public double getTotalPrice() {
double total = 0;
for (Product product : products) {
total += product.getPrice();
}
return total;
}
}
10.3 在JSP页面中使用购物车
以下是一个简单的JSP页面示例,用于展示如何使用购物车:
<jsp:useBean id="cart" class="shopping.ShoppingCart" scope="session">
<!-- 可以在这里根据需要添加商品 -->
<jsp:setProperty name="cart" property="products" param="productList"/>
</jsp:useBean>
<form action="addProduct.jsp" method="post">
Product Name: <input type="text" name="productName"><br>
Product Price: <input type="text" name="productPrice"><br>
<input type="submit" value="Add to Cart">
</form>
<h3>Cart Items:</h3>
<ul>
<%
List<Product> products = cart.getProducts();
for (Product product : products) {
out.println("<li>" + product.getName() + " - $" + product.getPrice() + "</li>");
}
%>
</ul>
<h3>Total Price: $<%= cart.getTotalPrice() %></h3>
在
addProduct.jsp
页面中,可以将用户输入的商品添加到购物车中:
<jsp:useBean id="cart" class="shopping.ShoppingCart" scope="session"/>
<%
String productName = request.getParameter("productName");
double productPrice = Double.parseDouble(request.getParameter("productPrice"));
Product product = new Product(productName, productPrice);
cart.addProduct(product);
response.sendRedirect("shoppingCart.jsp");
%>
10. 总结
通过以上介绍,我们全面了解了Java Server Pages和JavaBeans的使用方法。从JSP的基本元素如页面指令、表达式、脚本片段和声明,到类的使用和JavaBeans的定义与应用,这些技术为开发高效、可维护的Web应用程序提供了强大的支持。
在实际开发中,可以根据具体需求灵活运用这些技术。例如,使用页面指令来导入必要的包,使用表达式和脚本片段来动态生成页面内容,使用JavaBeans来封装业务逻辑和数据。同时,通过合理设置JavaBean的作用域,可以实现数据在不同页面和请求之间的共享。
下面是一个简单的流程图,展示了在JSP中使用JavaBeans的基本流程:
graph LR
A[创建JavaBean类] --> B[在JSP中使用<jsp:useBean>标签实例化Bean]
B --> C{是否需要设置属性?}
C -- 是 --> D[使用<jsp:setProperty>标签设置属性]
C -- 否 --> E[直接使用Bean对象]
D --> E
E --> F[通过表达式或脚本片段使用Bean的方法和属性]
总之,掌握Java Server Pages和JavaBeans的使用技术,能够帮助开发者更轻松地构建功能丰富、性能优良的Web应用程序。
超级会员免费看
69

被折叠的 条评论
为什么被折叠?



