Posts Tagged ‘一个’

重新认识表格和一个访问无障碍的数据表格例子

星期三, 06月 4th, 2008

除特别说明外,本站内容采用创作共用授权署名和非商业用途,请尊重劳动成果.

表格一直是网页设计制作过程中一个重要de组成部分,在没学习CSS布局前,大多是用来布局de,但到目前位置发现居然还没真正地了解和完全掌握表格,不得不需要重新认识表格……

在现代网页设计制作中,表格主要de用途应该是用来存放多元二维数据.和表格相关de标签有 table、tr、td、th、tbody、thead、tfoot、col、colgroup、caption,如何合理地应用这些标签呢?先从名词解释开始.

名词解释

table

显示二维数据

tr

表格中de一行

td

数据单元格

th

表头单元格,定义一行或者一列de表头信息,不能使用在布局表格里.

tbody

表格中de某一行或者多行编成组,要结合thead、tfoot一起使用

thead

将表格中de某一行或者多行编成组,要结合tbody、tfoot一起使用

tfoot

将表格中de某一行或者多行编成组,要结合tbody、thead一起使用

col

列,给某一列或者几列应用特定de属性,结合colgroup一起使用

colgroup

列de组合,结合col一起使用

caption

定义表格de标题,在表格开始de地方使用,仅一次

summary

说明表格de用途

例子:

<table summary=”这是一个具有亲和力de表格de演示” id=”demotab”>

<caption>

访问 <a href=”http://www.forest53.com”>www.forest53.com</a> 浏览器统计

</caption>

<thead>

<tr>

<th>浏览器 / 月 </th>

<th>2005 / 11 </th>

<th>2006 / 04 </th>

<th>2006 / 05 </th>

</tr>

</thead>

<tfoot>

<tr>

<th>总计</th>

<td>1,646 ( 98.45% )</td>

<td>6,978 ( 99.48% ) </td>

<td>5,366 ( 99.56% ) </td>

</tr>

</tfoot>

<tbody>

<tr>

<th>Internet Explorer</th>

<td>1,535 (91.81%)</td>

<td>5,905 (86.41%)</td>

<td>4,550 (84.42%)</td>

</tr>

<tr>

<th>Firefox</th>

<td>98 (5.86%)</td>

<td>746 (10.92%)</td>

<td>640 (11.87%)</td>

</tr>

<tr>

<th>Opera</th>

<td>13 (0.78%)</td>

<td>147 (2.15%)</td>

<td>176 (3.27%)</td>

</tr>

</tbody>

</table>

同一个页面用多个id有什么影响

星期三, 06月 4th, 2008

我知道在样式表定义一个样式de时候,可以定义id也可以定义class,例如:

ID方法:#test{color:#333333},在页面中调用内容


CLASS方法:.test{color:#333333},在页面中调用内容
id一个页面只可以使用一次,class可以多次引用.

有网友问,id和class好象没什么区别,我在页面中用了多个id在IE中显示也正常,用多个id有什么影响吗?

回答:第一影响就是不能通过W3de校验.

在页面显示上,目前de浏览器还都允许您犯这个错误,用多个相同ID“一般情况下”也能正常显示.但是当您需要用JavaScript通过id来控制这个div,那就会出现错误.

id是一个标签,用于区分不同de结构和内容,就象您de名字,如果一个屋子有2个人同名,就会出现混淆;
class是一个样式,可以套在任何结构和内容上,就象一件衣服;
概念上说就是不一样de:
id是先找到结构/内容,再给它定义样式;class是先定义好一种样式,再套给多个结构/内容.

web标准希望大家用严格de习惯来写相关代码,

例如:您可以用显示粗体,也可以用来显示,但W3C 建议大家用,因为更有语义

如果对这些细节问题不重视,觉得无所谓,
那么您就没必要向xml过渡了,也没必要学习web标准了,因为web标准应用就是从这些小细节上de改变开始,否则用现在dehtml不是也可以?

Asp.net中处理一个站点不同Web应用共享Session的问题

星期二, 06月 3rd, 2008

1、问题描述:

系统S中有M1,M2,M3,M4四个模块,每个模块都是一个web应用.其中一个模块中设置Session后在其他模块中无法读取.

2、问题原因:

一个WEB应用相当于一个站点,应用与应用之间不可能共享Session.

3、解决方法:

1) 将四个web应用包含在同一个解决方案中

(注:调整.webinfo文件使解决方案能构正常运行)

2) 新建一个web应用Main,该web应用包含在解决方案S中,并直接存放在S目录下(即与虚拟目录S相对应).

3) 在Main应用中添加其他四个应用de引用

4) 重新生成Main应用,此时,与Main模块相关deM1、M2、M3、M4四个模块dedll将生成于S\bin目录下.

5) 调整web.config文件

删除M1、M2、M3、M4四个模块web.config中除AppSetting节以外de所有节.(也可删除四个模块中deweb.config,只保留S目录下deweb.config文件.)

以下操作将影响开发环境

6) 删除goble.acax

删除M1、M2、M3、M4四个模块中degoble.acax文件.

7) 删除M1、M2、M3、M4四个模块对应de虚拟目录

8)大功告成

一个ASP.NET中使用的MessageBox类

星期二, 06月 3rd, 2008

/// <summary>
/// 自定义信息对话框
/// </summary>
public class MessageBox
{
/// <summary>
/// 定义一个web页面,用来显示用户自定错误提示信息
/// </summary>
System.Web.UI.Page p;
/// <summary>
/// 实例时,参数为:this 如:MessageBox MB=new MessageBox(this);
/// </summary>
/// <param name=”Page”>此参数为:this</param>
public MessageBox(System.Web.UI.Page Page)
{
p=Page; //创建页面
}
/// <summary>
/// 显示对话框
/// </summary>
/// <param name=”message”>提示信息</param>
public void Show(string message)
{
string script=”<script> alert(’” message “‘)</script>”;
p.Response.Write(script);
}
}

Java代码构建一个线程池

星期一, 06月 2nd, 2008

在现代de操作系统中,有一个很重要de概念――线程,几乎所有目前流行de操作系统都支持线程,线程来源于操作系统中进程de概念,进程有自己de虚拟地址空间以及正文段、数据段及堆栈,而且各自占有不同de系统资源(例如文件、环境变量等等).与此不同,线程不能单独存在,它依附于进程,只能由进程派生.如果一个进程派生出了两个线程,那这两个线程共享此进程de全局变量和相关代码段,但每个线程各拥有各自de堆栈,因此它们拥有各自de局部变量,线程在UNIX系统中还被进一步分为用户级线程(由进程自已来管理)和系统级线程(由操作系统de调度程序来管理).
  既然有了进程,为什么还要提出线程de概念呢?因为与创建一个新de进程相比,创建一个线程将会耗费小得多de系统资源,对于一些小型de应用,可能感觉不到这点,但对于那些并发进程数特别多de应用,使用线程会比使用进程获得更好de性能,从而降低操作系统de负担.另外,线程共享创建它de进程de全局变量,因此线程间de通讯编程会更将简单,完全可以抛弃传统de进程间通讯deIPC编程,而采用共享全局变量来进行线程间通讯.
  有了上面这个概念,我下面就进入正题,来看一下线程池究竟是怎么一回事?其实线程池de原理很简单,类似于操作系统中de缓冲区de概念,它de流程如下:先启动若干数量de线程,并让这些线程都处于睡眠状态,当客户端有一个新请求时,就会唤醒线程池中de某一个睡眠线程,让它来处理客户端de这个请求,当处理完这个请求后,线程又处于睡眠状态.可能您也许会问:为什么要搞得这么麻烦,如果每当客户端有新de请求时,我就创建一个新de线程不就完了?这也许是个不错de方法,因为它能使得您编写相关代码相对容易一些,但您却忽略了一个重要de问题――性能!就拿我所在de单位来说,我de单位是一个省级数据大集中de银行网络中心,高峰期每秒de客户端请求并发数超过100,如果为每个客户端请求创建一个新线程de话,那耗费deCPU时间和内存将是惊人de,如果采用一个拥有200个线程de线程池,那将会节约大量dede系统资源,使得更多deCPU时间和内存用来处理实际de商业应用,而不是频繁de线程创建与销毁.
  既然一切都明白了,那我就开始着手实现一个真正de线程池吧,线程编程可以有多种语言来实现,例如C、C++、java等等,但不同de操作系统提供不同de线程API接口,为了让您能更明白线程池de原理而避免陷入烦琐deAPI调用之中,我采用了JAVA语言来实现它,由于JAVA语言是一种跨平台de语言,因此您不必为使用不同de操作系统而无法编译运行本程序而苦恼,只要您安装了JDK1.2以上de版本,都能正确地编译运行本程序.另外JAVA语言本身就内置了线程对象,而且JAVA语言是完全面像对象de,因此能够让您更清晰地了解线程池de原理,如果您注意看一下本文de标题,您会发现整个示例程序de相关代码只有大约100行.
  本示例程序由三个类构成,第一个是TestThreadPool类,它是一个测试程序,用来模拟客户端de请求,当您运行它时,系统首先会显示线程池de初始化信息,然后提示您从键盘上输入字符串,并按下回车键,这时您会发现屏幕上显示信息,告诉您某个线程正在处理您de请求,如果您快速地输入一行行字符串,那么您会发现线程池中不断有线程被唤醒,来处理您de请求,在本例中,我创建了一个拥有10个线程de线程池,如果线程池中没有可用线程了,系统会提示您相应de警告信息,但如果您稍等片刻,那您会发现屏幕上会陆陆续续提示有线程进入了睡眠状态,这时您又可以发送新de请求了.
  第二个类是ThreadPoolManager类,顾名思义,它是一个用于管理线程池de类,它de主要职责是初始化线程池,并为客户端de请求分配不同de线程来进行处理,如果线程池满了,它会对您发出警告信息.
  最后一个类是SimpleThread类,它是Thread类de一个子类,它才真正对客户端de请求进行处理,SimpleThread在示例程序初始化时都处于睡眠状态,但如果它接受到了ThreadPoolManager类发过来de调度信息,则会将自己唤醒,并对请求进行处理.
   首先我来看一下TestThreadPool类de源码:

  //TestThreadPool.java
  1 import java.io.*;
  2
  3
  4 public class TestThreadPool
  5 {
  6 public static void main(String[] args)
  7 {
  8 try{
  9 BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
  10 String s;
  11 ThreadPoolManager manager = new ThreadPoolManager(10);
  12 while((s = br.readLine()) != null)
  13 {
  14 manager.process(s);
  15 }
  16 }catch(IOException e){}
  17 }
  18 }

  由于此测试程序用到了输入输入类,因此第1行导入了JAVAde基本IO处理包,在第11行中,我创建了一个名为managerde类,它给ThreadPoolManager类de构造函数传递了一个值为10de参数,告诉ThreadPoolManager类:我要一个有10个线程de池,给我创建一个吧!第12行至15行是一个无限循环,它用来等待用户de键入,并将键入de字符串保存在s变量中,并调用ThreadPoolManager类deprocess方法来将这个请求进行处理.
  下面我再进一步跟踪到ThreadPoolManager类中去,以下是它de源相关代码:

  //ThreadPoolManager.java
  1 import java.util.*;
  2
  3
  4 class ThreadPoolManager
  5 {
  6
  7 private int maxThread;
  8 public Vector vector;
  9 public void setMaxThread(int threadCount)
  10 {
  11 maxThread = threadCount;
  12 }
  13
  14 public ThreadPoolManager(int threadCount)
  15 {
  16 setMaxThread(threadCount);
  17 System.out.println(”Starting thread pool…”);
  18 vector = new Vector();
  19 for(int i = 1; i <= 10; i )
  20 {
  21 SimpleThread thread = new SimpleThread(i);
  22 vector.addElement(thread);
  23 thread.start();
  24 }
  25 }
  26
  27 public void process(String argument)
  28 {
  29 int i;
  30 for(i = 0; i < vector.size(); i )
  31 {
  32 SimpleThread currentThread = (SimpleThread)vector.elementAt(i);
  33 if(!currentThread.isRunning())
  34 {
  35 System.out.println(”Thread ” (i 1) ” is processing:”
  argument);
  36 currentThread.setArgument(argument);
  37 currentThread.setRunning(true);
  38 return;
  39 }
  40 }
  41 if(i == vector.size())
  42 {
  43 System.out.println(”pool is full, try in another time.”);
  44 }
  45 }
  46 }//end of class ThreadPoolManager

  我先关注一下这个类de构造函数,然后再看它deprocess()方法.第16-24行是它de构造函数,首先它给ThreadPoolManager类de成员变量maxThread赋值,maxThread表示用于控制线程池中最大线程de数量.第18行初始化一个数组vector,它用来存放所有deSimpleThread类,这时候就充分体现了JAVA语言de优越性与艺术性:如果您用C语言de话,至少要写100行以上de相关代码来完成vectorde功能,而且C语言数组只能容纳类型统一de基本数据类型,无法容纳对象.好了,闲话少说,第19-24行de循环完成这样一个功能:先创建一个新deSimpleThread类,然后将它放入vector中去,最后用thread.start()来启动这个线程,为什么要用start()方法来启动线程呢?因为这是JAVA语言中所规定de,如果您不用de话,那这些线程将永远得不到激活,从而导致本示例程序根本无法运行.
   下面我再来看一下process()方法,第30-40行de循环依次从vector数组中选取SimpleThread线程,并检查它是否处于激活状态(所谓激活状态是指此线程是否正在处理客户端de请求),如果处于激活状态de话,那继续查找vector数组de下一项,如果vector数组中所有de线程都处于激活状态de话,那它会打印出一条信息,提示用户稍候再试.相反如果找到了一个睡眠线程de话,那第35-38行会对此进行处理,它先告诉客户端是哪一个线程来处理这个请求,然后将客户端de请求,即字符串argument转发给SimpleThread类desetArgument()方法进行处理,并调用SimpleThread类desetRunning()方法来唤醒当前线程,来对客户端请求进行处理.
  可能您还对setRunning()方法是怎样唤醒线程de有些不明白,那我现在就进入最后一个类:SimpleThread类,它de源相关代码如下:
  //SimpleThread.java
  1 class SimpleThread extends Thread
  2 {
  3 private boolean runningFlag;
  4 private String argument;
  5 public boolean isRunning()
  6 {
  7 return runningFlag;
  8 }
  9 public synchronized void setRunning(boolean flag)
  10 {
  11 runningFlag = flag;
  12 if(flag)
  13 this.notify();
  14 }
  15
  16 public String getArgument()
  17 {
  18 return this.argument;
  19 }
  20 public void setArgument(String string)
  21 {
  22 argument = string;
  23 }
  24
  25 public SimpleThread(int threadNumber)
  26 {
  27 runningFlag = false;
  28 System.out.println(”thread ” threadNumber “started.”);
  29 }
  30
  31 public synchronized void run()
  32 {
  33 try{
  34 while(true)
  35 {
  36 if(!runningFlag)
  37 {
  38 this.wait();
  39 }
  40 else
  41 {
  42 System.out.println(”processing ” getArgument() “… done.”);
  43 sleep(5000);
  44 System.out.println(”Thread is sleeping…”);
  45 setRunning(false);
  46 }
  47 }
  48 } catch(InterruptedException e){
  49 System.out.println(”Interrupt”);
  50 }
  51 }//end of run()
  52 }//end of class SimpleThread
  如果您对JAVAde线程编程有些不太明白de话,那我先在这里简单地讲解一下,JAVA有一个名为Threadde类,如果您要创建一个线程,则必须要从Thread类中继承,并且还要实现Thread类derun()接口,要激活一个线程,必须调用它destart()方法,start()方法会自动调用run()接口,因此用户必须在run()接口中写入自己de应用处理逻辑.那么我怎么来控制线程de睡眠与唤醒呢?其实很简单,JAVA语言为所有de对象都内置了wait()和notify()方法,当一个线程调用wait()方法时,则线程进入睡眠状态,就像停在了当前相关代码上了,也不会继续执行它以下de相关代码了,当调用notify()方法时,则会从调用wait()方法de那行相关代码继续执行以下de相关代码,这个过程有点像编译器中de断点调试de概念.以本程序为例,第38行调用了wait()方法,则这个线程就像凝固了一样停在了38行上了,如果我在第13行进行一个notify()调用de话,那线程会从第38行上唤醒,继续从第39行开始执行以下de相关代码了.
  通过以上de讲述,我现在就不难理解SimpleThread类了,第9-14行通过设置一个标志runningFlag激活当前线程,第25-29行是SimpleThread类de构造函数,它用来告诉客户端启动de是第几号进程.第31-50行则是我实现derun()接口,它实际上是一个无限循环,在循环中首先判断一下标志runningFlag,如果没有runningFlag为falsede话,那线程处理睡眠状态,否则第42-45行会进行真正de处理:先打印用户键入de字符串,然后睡眠5秒钟,为什么要睡眠5秒钟呢?如果您不加上这句相关代码de话,由于计算机处理速度远远超过您de键盘输入速度,因此您看到de总是第1号线程来处理您de请求,从而达不到演示效果.最后第45行调用setRunning()方法又将线程置于睡眠状态,等待新请求de到来.
  最后还有一点要注意de是,如果您在一个方法中调用了wait()和notify()函数,那您一定要将此方法置为同步de,即synchronized,否则在编译时会报错,并得到一个莫名其妙de消息:“current thread not owner”(当前线程不是拥有者).
  至此为止,我完整地实现了一个线程池,当然,这个线程池只是简单地将客户端输入de字符串打印到了屏幕上,而没有做任何处理,对于一个真正de企业级运用,本例还是远远不够de,例如错误处理、线程de动态调整、性能优化、临界区de处理、客户端报文de定义等等都是值得考虑de问题,但本文de目de仅仅只是让您了解线程池de概念以及它de简单实现,如果您想成为这方面de高手,本文是远远不够de,您应该参考一些更多de资料来深入地了解它.

成为一个成功Jsp程序员的九步

星期一, 06月 2nd, 2008

  如何成为一个成功deJsp程序员?一个普通de错误是把JSP当作简化de Java.它不是,(事实上, JSP 是简化de servlets .)程序员通常试着没有学习要求de支持技巧而 直接学习 JSP .JSP 是一个衔接技术,并且成功地连接您需要理解de另外de技术.如果您已经知道 Java,HTML 和 Javascript,这意味着 JSP 将确实是简单de.

  需要成为一个成功de JSP 程序员可以参考这个时间表.请注意下列:

  *忽略您已经熟悉de步骤.
  *训练de时间只是代表学习好足够de基础时间,这样才能转移到下一步.

  1、建立并且理解您deWeb Server.
  因为Apache 是免费de并且在大多数平台上工作,为训练目de推荐 Apache.
  安装时间:2 天.

  2、保证您理解 HTML / XHTML .
  您将需要了解html基础, 特别是 HTML 布局中detablede使用.XHTML 不久将代替 HTML ,学习 XHTML de基础是一个好主意.许多程序员通过 HTML IDE 学习 HTML ( 集成开发环境 ) .因为大多数 HTML IDE产生混乱deHTMl语法,所以花时间学习手工写作html是很有必要de.因 为您将会使用 JSP 和 HTML 混合编程,精通HTML语法是重要de.所以,您必须能流利地写 HTML .
  训练时间:2 ~ 4 个星期.

  3、开始学习 Java .
  开始学习 Java 1.4 理解 Java 基础是很重要de.不用担心学习Swing或 Java de图形方面,因为在JSP 中您不会使用这些特征.集中精力 在 Java 工作de细节,学习 Java de逻辑,也在 Java Bean上花时间.学习Applet是好de, 但是就象Swing, JSP de大多数应用将不使用小程 序.
  训练时间:3 ~ 6 个星期.

  4、学习 JavaScript
  学习怎么将 JavaScript在HTML中验证输入deForm元素.也学习 JavaScript怎么能在一 HTML 页以内修改Formde元素.最后要求您能从一
  HTML 页内de事件中触发 JavaScript Function.
  训练时间:一~ 2 个星期.

  5、学习并且理解您deWeb Serverde更好de细节.
  熟悉Web Serverde特征,这是很重要de.
  训练时间:2 天.

  6、建立您de JSP Server
  我推荐以Tomcat开始.它可以很好地运行JSP程序.当您不能在生产使用Tomcat时,学习尽可能多de知识以便于更好de运行程序.另外, 许多 JSP 程序员使用Tomcat.因此当您遇到一个问题时,您将容易发现帮助.
  安装时间:1~ 2 天.

  7、开始学习 JSP .
  基本de JSP 学习通过de步骤 1到步骤6可以完成, 然后使用 JSP 对象和脚本写 JSP 程序来联系.学习 JSP de另外一个方面可以学习怎么创建一个分布式de应用程序.
  训练时间:4 ~ 6 个星期.

  8、学习更多de JSP server.
  没有关于更多de JSP Server当然也可以运行jsp程序.然而, 许多 JSP server都由自己特殊de特征,可以让您更好de理解您deJSP 工程.
  学习更多deJsp server如何处理jsp程序是有必要de.同样也可以优化您de JSP 应用程序,并且使之运行得更快而不出任何问题.
  训练时间:2 ~ 7 天.

  9、 学习 JDBC .
  JSP 大多数应用将使用数据库,JDBC 被用于数据库连接.经常忽略de一个事实就是,每个 JDBC Driver 所支持de东西是相当不同de.了 解并熟悉在jsp工程上被使用de JDBC driverde细节是很重要de.(有时这部分de学习被包含在前面 Java 或JSPde学习中了 .)
  训练时间:1~ 2 个星期.

  到现在,您已经成为了熟练de JSP 程序员.仍然有很多需要学习,您可以考虑扩展您de知识比如 DHTML , XML ,java证书, JSP Tag Libraries 或 Servlets , 看您想要造什么类型de网站而决定了.

  这些训练是JSP de核心.您不必都学习上面所有de, 取决于您在工程中分配到什么任务和您已经有什么知识.但是这是我成功地训练程序员 de时间表.关键de单元是时间.平均de说, 5 个月时间确实能够训练一个人 ( 从开始到完成 ) 成为一个对jsp熟悉程序员.5 个月时间似乎很长,但要成为一个资深deWEB程序员所学de东西远远不止这一些.

  也许您认为这样学习一种语言花费de时间太长了,因为学 ASP 会更快、时间会更短. 但是学习 ASP 不需要学习javade.

用JSP实现的一个日历程序

星期一, 06月 2nd, 2008

<!– 显示任意年、月de日历,可选择不同de年、月.author:wildfield –>
<%@ page language=”java” import=”java.util.*” %>
<%! String year;
String month;
%>
<% month=request.getParameter(”month”);
year =request.getParameter(”year”);
%>
<html>
<head>
<meta http-equiv=”Content-Type” content=”text/html; charset=gb2312″>
<title>日</title>
<script Language=”JavaScript”>
<!–
function changeMonth()
{
var mm=”calendar.jsp?month=” document.sm.elements[0].selectedIndex “&year=”
<%=year%>;
window.open(mm,”_self”);
}
//–></script>
</head>
<%! String days[]; %>
<%
days=new String[42];
for(int i=0;i<42;i )
{
days[i]=”";
}
%>
<%
Calendar thisMonth=Calendar.getInstance();
if(month!=null&&(!month.equals(”null”)))
thisMonth.set(Calendar.MONTH, Integer.parseInt(month) );
if(year!=null&&(!year.equals(”null”)))
thisMonth.set(Calendar.YEAR, Integer.parseInt(year) );
year=String.valueOf(thisMonth.get(Calendar.YEAR));
month=String.valueOf(thisMonth.get(Calendar.MONTH));
thisMonth.setFirstDayOfWeek(Calendar.SUNDAY);
thisMonth.set(Calendar.DAY_OF_MONTH,1);
int firstIndex=thisMonth.get(Calendar.DAY_OF_WEEK)-1;
int maxIndex=thisMonth.getActualMaximum(Calendar.DAY_OF_MONTH);
for(int i=0;i<maxIndex;i )
{
days[firstIndex i]=String.valueOf(i 1);
}
%>
<body>
<FORM name=”sm” method=”post” action=”calendar.jsp”>
<%=year%>年 <%=Integer.parseInt(month) 1%>月
<table border=”0″ width=”168″ height=”81″>
<div align=center>
<tr>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″><font color=”red”>日</font>
</th>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″>一</th>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″>二</th>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″>三</th>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″>四</th>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″>五</th>
<th width=”25″ height=”16″ bgcolor=”#FFFF00″><font color=”green”>六</fon
t></th>
</tr>
<% for(int j=0;j<6;j ) { %>
<tr>
<% for(int i=j*7;i<(j 1)*7;i ) { %>
<td width=”15%” height=”16″ bgcolor=”#C0C0C0″ valign=”middle” align=”ce
nter”>
<a href=”jump.jsp?year=<%=year%>&month=<%=Integer.parseInt(month) 1%>&d
ate=<%=days[i]%>” target=”main”><%=days[i]%></a></td>
<% } %>
</tr>
<% } %>
</div>
</table>
<table border=”0″ width=”168″ height=”20″>
<tr>
<td width=30%><select name=”month” size=”1″ onchange=”changeMonth()” >
<option value=”0″>一月</option>
<option value=”1″>二月</option>
<option value=”2″>三月</option>
<option value=”3″>四月</option>
<option value=”4″>五月</option>
<option value=”5″>六月</option>
<option value=”6″>七月</option>
<option value=”7″>八月</option>
<option value=”8″>九月</option>
<option value=”9″>十月</option>
<option value=”10″>十一月</option>
<option value=”11″>十二月</option>
</select></td>
<td width=28%><input type=text name=”year” value=<%=year%> size=4 maxlength
=4></td>
<td>年</td>
<td width=28%><input type=submit value=”提交”></td>
</tr>
</table>
</FORM>
<script Language=”JavaScript”>
<!–
document.sm.month.options.selectedIndex=<%=month%>;
//–>
</script>
</body>
</html>

一个分页的类及调用的例子

星期一, 06月 2nd, 2008

//PageCt.java 分页de类
/*
*** @version ***********
*** Created on 2001年6月25日, 下午14:41
**************************************
*/
package vod;
import java.sql.*;
import java.util.*;

public class PageCt
{
private long l_start; //开始纪录
private long l_end; //结束纪录
private long l_curpage; //当前页数
private long l_totalnum;//总记录数
private int int_num=5; //每页10条
private long l_totalpage; //总de页数

public void Init(long currentpage,long totalnum)
{
l_curpage = currentpage;
l_totalnum = totalnum;

if (currentpage>=0)
{
if (currentpage>=(long)Math.ceil((double)l_totalnum/(double)int_num))
l_curpage = (long)Math.floor((double)l_totalnum/(double)int_num);
else
l_curpage = currentpage;
}
else
{
l_curpage = 0;
}
l_start = l_curpage * int_num;
l_end = l_start int_num;
if (l_end > l_totalnum)
l_end = l_totalnum;
l_totalpage = (long)Math.ceil((double)l_totalnum/(double)int_num);
}
public long getCurpage()
{
return l_curpage;
}
public long getPrepage()
{
if (l_curpage-1>=0)
{
return l_curpage-1;
}
else
{
return 0;
}
}
public long getNextpage()
{
if (l_curpage 1<=l_totalpage)
{
return l_curpage 1;
}
else
{
return l_totalpage;
}
}
public long getTotalnum()
{
return l_totalnum;
}
public long getTotalpage()
{
return l_totalpage;
}
public long getStart()
{
return l_start;
}
public long getEnd()
{
return l_end;
}

};
===============================================
//调用例子
<%
/*
*** @author 马毅 ***********
*** @version ***********
*** Created on 2001年6月12日, 下午17:13
**************************************
*/
<%@ page import=”java.sql.*”%>
<%@ page import=”java.lang.*”%>
<%@ page contentType=”text/html;charset=gb2312″ %>
<jsp:useBean id=”PageCount” scope=”page” class=”kstest.PageCt” />
<jsp:useBean id=”sqlbean” scope=”page” class=”vod.sql_data” />
<html>
<head>
<TITLE>测试</TITLE>
<STYLE>
body,table{font-size:9pt}
A:link {
COLOR: #000084; TEXT-DECORATION: none
}
A:visited {
COLOR: #000084; TEXT-DECORATION: none
}
A:hover {
COLOR: black; TEXT-DECORATION: underline
}
.ourfont {
FONT-SIZE: 9pt
}
</STYLE>
</head>
<body bgcolor=#eff3ff>
<center>
<font color=#000084><h3>Test for Test</h3></font>
<hr width=600 color=#b5dbff>
<br>
<%
ResultSet rs0 = sqlbean.executeQuery(”select count(*) from UserList );
rs0.next();
long data_num=rs0.getLong(1);
long Current_Page = 0;
String currentpage=(String)request.getParameter(”currentpage”);
if (currentpage != null && !currentpage.equals(”"))
{
Current_Page = Integer.parseInt(request.getParameter(”currentpage”));
}
String Query_Page=(String)request.getParameter(”Query_Page”);
if (Query_Page!=null && !Query_Page.equals(”"))
{
Current_Page = Integer.parseInt(request.getParameter(”Query_Page”))-1;
}
PageCt.Init(Current_Page,data_num);
long l_start = PageCt.getStart();
long l_end = PageCt.getEnd();
//查询记录
ResultSet rs = sqlbean.executeQuery(”select * from UserList ” );
long i=0;
while((i<l_start) && rs.next())
{
i ;
}
//输出查询结果
long j=0;
while(rs.next() && (i<l_end))
{
j=i 1;
String col2 = rs.getString(2);
String col3 = rs.getString(3);
String col4 = rs.getString(4);
String col5 = rs.getString(5);
String col6 = rs.getString(6);
String col7 = rs.getString(7);
String col8 = rs.getString(8);
//打印所显示de数据
out.println(”<table border=0 width=600>”);
out.println(”<tr><td colspan=2><font color=#000084>” j “、” (col2==null?”":col2) “</font></td></tr><tr><td colspan=2>答案:” (col3==null?”":col3) “</td></tr>”);
out.println(”<tr><td> 选项1:” (col4==null?”":col4) “</td><td> 选项2:” (col5==null?”":col5) “</td></tr>”);
out.println(”<tr><td> 选项3:” (col6==null?”":col6) “</td><td> 选项4:” (col7==null?”":col7) “</td></tr>”);
if (col8!=null && !col8.equals(”"))
{
out.println(”<tr><td colspan=2>备注:” col8 “</td></tr>”);
}
out.println(”</table><br>”);
i ;
}
%>
<table width=600>
<tr bgcolor=#b5dbff>
<form method=GET action=index.jsp>
<td width=80 align=center valign=bottom>共 <%=PageCt.getTotalnum()%> 条</td>
<td width=80 align=center valign=bottom><%=PageCt.getCurpage() 1%>/<%=PageCt.getTotalpage()%> 页</td>
<td width=120 align=center>查看第 <input type=text name=Query_Page size=3> 页</td>
<td width=50 align=center valign=bottom><a href=index.jsp?currentpage=<%=PageCt.getPrepage()%>>上页</a></td>
<td width=50 align=center valign=bottom><a href=index.jsp?currentpage=<%=PageCt.getNextpage()%>>下页</a>
</td>
</tr>
</table>
<br><br><br>
<table cellspacing=20>
<tr>
<td>问题包含<input type=text name=question_str size=10 value=<% if (question_str != null) out.println(question_str); %> ></td>
<td>答案包含<input type=text name=answer_str size=10 value=<% if (answer_str != null) out.println(answer_str); %> ></td>
<td>选项包含<input type=text name=sel_str size=10 value=<% if (sel != null) out.println(sel); %> ></td>
</tr>
<tr>
<td colspan=3 align=center><input type=submit value=查询></td>
</tr>
</form>
</table>
<br><br>
<a href=”insert.jsp”>添加</a>
<center>
</body>
</html>

指南:想成为一个JSP网站程序员吗?

星期一, 06月 2nd, 2008

任何Web开发人员需要必备de技巧主要有以下这些技术.
开发Web应用程序de技术已经变得更成熟、更复杂了.现在,构建一个Web应用程序不仅仅需要简单deHTML技术了.数据库访问、脚本语言和管理都是一个Web程序员需要具备de技术.让我来看看要成为一个市场上受欢迎deWeb开发人员都需要些什么技能吧.

自从CERN(欧洲粒子物理研究所),日内瓦附近de高能物理研究中心,在1991年发布了Web以来,Web技术已经从静态de内容和Common Gateway Interface(CGI)发展成servlet技术和JavaServer Pages了.然而,在这个竞争更激烈de社会中,一个Web程序员需要更多de知识.例如,如果在面试中,您提到您熟悉XML并在JNDI方面有些经验(这两种技术初看似乎同Web编程没有很紧密de关系),那么您就会给您未来de老板留下更深de印象.设想您已经了解了Java编程语言和面向对象de编程,下面还有两组技术是一个Web开发人员日常工作中所需要de.第一组包括每个Web程序员必须具备de技术.第二组包含要想成为一个高级程序员所应该掌握de技术.

基本技能
如果想称自己是个Web开发人员,下面就是必须具备de技术.

HTML(HyperText Markup Language)
HTML几乎是显示在浏览器上所有内容de语言.难怪HTML就好像是一个Web程序员de生存本能一样.如果您仍需要在您deHTML中查找<tr>或<b>,那么您真de需要提高您deHTML技术了.HTMLde当前版本是4.01,您可以从http://www.w3.org/TR/1999/REC-html401-19991224/了解更多关于它de内容.

Servlets和JSP
Java servlet技术是开发Java Web应用程序de主要技术.它是由Sun Microsystems在1996年开发de,当前de版本是2.3,但人们正在为版本2.4做准备.

JSP是servlet技术de扩展,现在de版本是1.2(2.0版将很快定下来).有人认为JSP是servletsde替代,但实际并不是这样de.Servlets和JSP是一起用于复杂deWeb应用程序de.

用Java进行Web编程de一个好de开端就是学习servlet技术.即使您打算在您deWeb应用程序中只运用JSP页面,您仍需要学习servlet技术.在更复杂deWeb应用程序中,JSP页面只用于显示,而JavaBeans和自定义标签库用来嵌入商业逻辑.即:您也必须精通JavaBeans和自定义标签库.


JavaScript
JavaScript是运行于所有de主要de浏览器中de脚本语言.您用JavaScript来进行客户端de编程.客户端编程中最重要de工作就是确认用户输入.运用客户端输入验证de好处是减少服务器de工作量并提高响应时间.另外,JavaScript可以用于重新定向(redirection)、cookie处理、控制applets、创建导航树、打开一个浏览器de一个新de实例、等等.

SQL(Strutured Query Language)和JDBC(Java Database Connectivity)
如今,大多数Web应用程序都包括访问关系数据库中de数据.作为一个Web程序员,您需要知道如何存储、得到并操作数据库中de数据.有时侯,您也需要设计数据库,构建数据库中de表和其它结构.SQL就是用来操作数据库中数据de语言.您通常需要编写SQL语句(常常是动态de),把它们传递到数据库服务器,并得到返回de数据(如果有de话).

运用Java语言,您需要用JDBC来帮助Web应用程序和数据库服务器进行通讯.JDBC有两部分:JDBC Core API(Application Programming Interface)和JDBC Optional Package API.第一组用来执行基本de数据操作,如创建一个连接或读取、更新并删除一个表中de记录.第二组提供更高级de数据库连接功能,如连接池、事务和RowSet.JDBCde当前版本是3.0,API包含在J2SE v. 1.4中.

Web Container管理和应用程序部署
您deservlets和JSP页面在一个叫做servlet/JSP container或Web containerde引擎中运行.您至少需要知道如何为测试以及生产运行部署您deWeb资源.例如,如果您运用Tomcat,您需要了解de一件事就是如何映射配置文件(server.xml)中de应用程序,使Tomcat知道如何调用您deJSP页面.另外,您需要知道在哪里保存您de库以及如何创建应用程序部署描述符.

XML(eXtensible Markup Language)
XML是计算机领域中一个成功de后起之秀.由World Wide Web Consortium在1996年开发,XML现在已经是用于数据交换和可扩展数据结构de一个广泛de、公认de标准了.XML在Java Web开发中扮演着一个重要de角色.例如,每个应用程序de部署描述符都是XML格式de.而且,如果您在开发Web servies,您就会用到SOAP(Simple Object Access Protocol),它主要是基于HTTP和XMLde.

另外,在Web应用程序中,XML也可能用于存储分等级de数据.

Model 2结构
这种技术在该类别中是最先进de.建议用这种结构来构建相当复杂deJava Web应用程序.Model 2结构是基于Model-View-Controller设计例子de.

高级技术
下面这些技术可以将您同初学者区别开来.

JSTL(JSP Standard Tag Libraries)、Jakarta Taglibs项目和其它库
为了加速应用程序de开发,您应该经常重用相关代码.简单地说,相关代码重用就是,如果有人已经编写了用来执行某些功能de相关代码,您最好就去用那些相关代码,而不要自己编写了.因此,JSP可以让您运用自定义标签.您可以运用几个库,最受欢迎de是ApachedeJakarta Taglibs项目中de库.从http://jakarta.apache.org/taglibs/index.html可以下载这个包,您在开始创建新类前,可以运用在这个包中找到de任何现成de东西.

JSTL最近已经成为了一个标准.其它标签库可以免费或以商业方式得到.

ApachedeStruts项目
Struts是一个Apache赞助de公共资源项目,它为构建Model 2 Java Web应用程序提供了一个构架.Struts为MVC结构提供它自己deController组件,将EJB、JDBC和JNDI用于Model,将JSP和其它技术用于View.您可以从它de网站找到更多关于这个项目de更详细de信息:http://jakarta.apache.org/struts/index.html.

XHTML(Extensible HyperText Markup Language)
XHTML是努力将HTML和XML结合起来de一种技术.您可以把XHTML当作下一代deHTML.其当前de版本是1.0(第二版是于2002年8月1日发布de),XHTML还没有像HTML那么流行,但它在将来会发挥更重要de作用.根据Web设计专家Molly Holzschlagde观点,推动各个公司转向XHTMLde主要原因是美国de关于公开访问(accessibility)de法律.更多关于XHTMLde信息,参阅Holzschlag访谈.

DHTML(动态HTML)
DHTML可以允许人们在您de网站上进行更多de交互.例如,运用DHTML,当用户移动鼠标到一个链接上时,您就可以很容易地创建并显示子菜单.运用DHTMLde最大de挑战是创建跨浏览器de页面.de确,在理论上,页面设计应该是由美工处理de,其中动态deHTML是通过运用一个工具而产生de.然而,一个Web程序员通常要负责集成所有de部分,如果在页面中生成de相关代码被破坏了,您就需要了解DHTML来修理它.

Applet 编程
Applets曾经在提供交互性方面很重要,尤其在DHTML出现前.现在,appletsde作用被削减了,更多de程序员已经不用applets了.Microsoft决定在它de新浏览器中不为applets提供缺省de支持极大地削减了applets在Web应用程序中de作用.然而,applets并没有消亡.对于某些任务,如显示新闻标题,applets仍然是不可替代de,而且applets不会产生另人头痛de跨浏览器兼容方面de问题.

HTTP协议
Java Web程序员通常运用比HTTP更高de协议,如运用servlet和JSP APIs.这些APIs隐藏了HTTP协议de复杂性.因此,您仍可以构建重要de应用程序而不需要知道多少关于HTTP协议de知识.只有当您需要处理原始数据,比如将文件作为附件上载或传送时,您才需要更多关于协议de知识.

EJB(Enterprise JavaBeans)
EJB是J2EEde一部分,当可扩展性和强大性是您deWeb应用程序de主要需求时,EJB就很重要.在当前规范(EJB 2.0)中有三种类型deEJBs:会话(session)EJBs、实体(entity)EJBs和消息驱动de(message driven)EJBs.新de规范,2.1版,正在设计中.

JNDI(Java Naming and Directory Interface)
当您在开发企业beans时,JNDI很重要,因为对一个EJBde访问是通过JNDIde命名服务完成de.运用一个命名服务来查找与一个特定名字相关de一个对象.在EJB context中,一个命名服务找到一个企业bean,给定这个beande名字.因此,了解JNDI在开发一个EJB应用程序中是至关重要de.另外,JDBC可以用JNDI来访问一个关系数据库.

其它工具
了解在哪里可以找到特定de支持工具通常有助于de您de事业de发展.例如,如果您碰巧被分配去做关于基准de任务,那么您如果知道您可以从ApachedeJakarta Project下载Jmeter,您就会很高兴.另外,如果您需要以PDF格式发送输出结果,建议您从http://www.lowagie.com/iText/运用可以免费下载deJava-PDF库.Internet技术范围很广而且发展很快.这就是说,作为一个Web程序员,您应该时时留心业界出现了什么新技术,发生了什么大事.在这个方面,没有什么比Internet本身更伟大de资源了.


关于作者:
Java for the Web
with Servlet, JSP, and EJB
Budi Kurniawan是位IT顾问,他专门从事Internet和面向对象de编程,并教授Java和Microsoft技术.他是销量很好deJava for the Web with Servlets, JSP, and EJB: a Developer’s Guide to Scalable Solutions (New Riders)一书de作者,他还开发了最受欢迎deJava Upload Bean,您可以从BrainySoftware.com得到它,许多重要de公司都得到许可并将它用于项目中了.Budide联系方式是budi@brainysoftware.com.

使用JSP JAVABEAN XML 开发的一个例子

星期一, 06月 2nd, 2008

本例子是参考了一些网站上有关JSP 对 XML de操作de相关文档,又结合了一些个人de体会.例子涉及de内容是,开发de一个企业内部定餐系统后台管理端de部分相关代码,功能主要集中在对于餐馆基本信息de管理.
该例子本身开发de起因是我在原公司和同事们一个玩笑de一部分.特此也表达对那些一起共事de朋友们de想念.
例子本身是在TOMCAT4.01 平台下运行deB/S结构de程式.有关TOMCAT de配置,这里不做说明.只讲解一下相关文件及文件夹de目录结构.
目录结构说明:
/tomcat/webapps/canyin/ —–主目录
/tomcat/webapps/canyin/jsp/ —–JSP 文件目录
/tomcat/webapps/canyin/jsp/admin/ —–实现后台管理deJSP 文件de存放目录
/tomcat/webapps/canyin/WEB-INF/classes/canyin/ ——javabean 文件de存放目录
/tomcat/webapps/canyin/data/ —–xml 文件存放目录
/tomcat/webapps/ROOT/ —–tomcat 启动文件存放文件夹,只存放了index.html 文件
文件简单说明:
/tomcat/webapps/canyin/data/users.xml —–记录用户信息
/tomcat/webapps/canyin/data/restaurants.xml —–记录餐馆de基础信息

/tomcat/webapps/ROOT/index.html —–首页,页面出现输入框,要求用户输入用户名,密码

/tomcat/webapps/canyin/jsp/loginjudge.jsp —–用户身份判断页面,根据用户名称和密码决定页面是转入后台管理端,还是前台客户端.本例子中,用户身份一旦确认为有管理权限,可以进入后台管理端,就直接跳到餐馆基本信息管理页面,简化说明de流程.
/tomcat/webapps/canyin/jsp/admin/admin_rest.jsp —–餐馆基本信息管理页面,管理餐馆de名称,电话,地址等信息
/tomcat/webapps/canyin/WEB-INF/classes/canyin/checkSessionBean.class —– 后台管理端检测标志用户身份desession de值,如果不是管理员de话,跳回登陆页面.
/tomcat/webapps/canyin/WEB-INF/classes/canyin/connXmlBean.class —–连接xml 文件
/tomcat/webapps/canyin/WEB-INF/classes/canyin/writeXmlBean.class —–写入xml文件
文件详细介绍及附带相关代码说明.
/tomcat/webapps/canyin/data/users.xml
相关代码:
<?xml version=”1.0″ encoding=”UTF-8″ ?>
- <users>
<user name=”joard” password=”joard” roles=”admin” />
<user name=”joard01″ password=”joard01″ roles=”user” />
<user name=”joard02″ password=”joard02″ roles=”user” />
</users>
说明:字段含义是用户名,密码以及用户de身份
/tomcat/webapps/canyin/data/restaurants.xml
相关代码:
<?xml version=”1.0″ encoding=”UTF-8″ ?>
- <restaurants num=”10″>
- <restaurant id=”1″>
<name>上海亭快餐店</name>
<phone>021-76546726</phone>
<address>百老汇广场B座</address>
</restaurant>
- <restaurant id=”8″>
<name>香格里拉大饭店</name>
<phone>021-2312134</phone>
<address>南京路1023号</address>
</restaurant>
</restaurants>
说明:<num>属性是记录在restaurants.xml 文件中总共有过多少条记录,每新增一条,无论以后删除是否,该值都会增加1,就好象数据库中习惯使用de自动增加1deid 项.用来给新增de <restaurant>de属性<id>赋一个唯一de值.其它de字段意思比较明显.
/tomcat/webapps/ROOT/index.html (单纯deHTML相关代码)
相关代码:
<html>
<head>
<title>oddWorld 餐饮系统</title>
<meta http-equiv=”Content-Type” content=”text/html; charset=gb2312″>
</head>
<body onload=”javascript:dataform.username.focus()”>
<div align=”center”>
<table width=”100%” border=”0″ cellspacing=”0″ cellpadding=”0″ height=”22″>
<tr>
<td width=”1″><img src=”images/top_r1.GIF” width=”62″ height=”22″></td>
<td width=150 align=”center”> 餐饮系统登录 </td>
<td><img src=”images/top_r2.GIF” width=”294″ height=”22″></td>
</tr>
</table>
<br>
<br>
<table width=”300″ border=”0″ cellspacing=”1″ cellpadding=”0″ >
<tr>
<td height=”200″ valign=”top” align=”center”>
<p align=”center”>
<table width=”100%” border=”0″ cellspacing=”1″ cellpadding=”5″ bgcolor=#999999 class=a9px>
<tr>
<td bgcolor=”#efefef”>餐饮系统登录</td>
</tr>
<tr>
<td bgcolor=”#FFFFFF” valign=”top” align=”center”>
<table width=”100%” border=”0″ cellspacing=”0″ cellpadding=”0″>
<form name=dataform method=post action=”canyin/jsp/loginjudge.jsp”>
<tr>
<td width=”100″><b>登录名:</b></td>
<td>
<input maxlength=16
name=”username” class=stedit value=”joard”>
</td>
</tr>
<tr>
<td width=”100″><b>密码:</b></td>
<td>
<input class=stedit maxlength=16
name=”userpass” type=password value=”oddworld”>
</td>
</tr>
</form>
</table>
<br>
<table border=0 cellpadding=0 cellspacing=0>
<tbody>
<tr>
<td>
<input class=stbtm name=update onClick=”javascript:if (checkform()==false);” type=button value=”登 录”>
</td>
<td> </td>
<td>
<input class=stbtm name=Submit onClick=”javascript:window.location.href=”index.asp?myjoke=1”;” type=button value=”修改密码”>
</td>
<td> </td>
</tr>
</tbody>
</table>
<br>
</td>
</tr>
</table>
</td>
</tr>
</table>
</div>
</body>
</html>
<SCRIPT language=javascript>
<!–
function checkform()
{
var Checkblank = /^(\s*|(\ )|(\.))*$/;
if (Checkblank.test(dataform.username.value))
{
alert(”登录名不能为空!”);
return false;
}
if (Checkblank.test(dataform.userpass.value))
{
alert(”密码不能为空!”);
return false;
}

window.dataform.submit();
}
–>
</SCRIPT>
说明:把用户名称和用户密码提交到/tomcat/webapps/canyin/jsp/loginjudge.jsp
/tomcat/webapps/canyin/WEB-INF/classes/canyin/checkSessionBean.class (相关代码是相应dejava 文件)
package canyin;
import javax.servlet.http.HttpSession;
import javax.servlet.http.HttpServletRequest;
public class checkSessionBean {
private boolean bolCheckPass=false;
private HttpServletRequest request = null;
public boolean checkSessionBean(HttpServletRequest request,String strSessionName,String strCheckValue){
public boolean checkSessionBean(HttpServletRequest request){
HttpSession session = request.getSession(false);
return(bolCheckPass);
if (strSessionName==null || strCheckValue==null){
return(bolCheckPass);
}else{
if (session!=null && session.getValue(strSessionName)!=null){
bolCheckPass=session.getValue(strSessionName).equals(strCheckValue);
}
return(bolCheckPass);
}
}
}
说明:检验参数传入desession 名称de数值和参数传入de字段de数值是否相等.
/tomcat/webapps/canyin/WEB-INF/classes/canyin/connXmlBean.class
相关代码:
package canyin;
import javax.xml.parsers.*;
import javax.xml.transform.*;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import org.w3c.dom.*;
public class connXmlBean {
private DocumentBuilderFactory factory=null;
private DocumentBuilder builder=null;
private Document doc=null;
public connXmlBean(){}
public String connXml(String xmlFileName){
String strExc=”";
try{
factory = DocumentBuilderFactory.newInstance();
builder=factory.newDocumentBuilder();
doc=builder.parse(xmlFileName);
doc.normalize();
}catch(Exception e){
strExc=e.toString();
}
return(strExc);
}
public Document getXmlDoc(){
return(doc);
}
}
说明:打开一个指定xml 文件
/tomcat/webapps/canyin/WEB-INF/classes/canyin/writeXmlBean.class
相关代码:
package canyin;
import javax.xml.parsers.*;
import javax.xml.transform.*;
import javax.xml.transform.dom.DOMSource;
import javax.xml.transform.stream.StreamResult;
import java.io.File;
import org.w3c.dom.*;
public class writeXmlBean {
public writeXmlBean(){}
public String writeXml(Document doc,String xmlFileName){
String strExc=”";
try{
TransformerFactory tfactory = TransformerFactory.newInstance();
Transformer transformer = tfactory.newTransformer();
DOMSource source = new DOMSource(doc);
StreamResult result = new StreamResult(new File(xmlFileName));
transformer.transform(source,result);
}catch(Exception e){
strExc=e.toString();
}
return(strExc);
}
}
说明:写入dom de内容到一个指定dexml 文件.
/tomcat/webapps/canyin/jsp/loginjudge.jsp
相关代码:
<%– oddWorld 餐饮管理系统(简体中文版) 2002年12月1日
copy right by joard ast
loginjudge.jsp 功能:用户身份校验,根据 /data/user.xml 文件内标示de用户不同de身份
决定转入后台管理页面,还是客户点菜页面.
–%>
<%@ page contentType=”text/html;charset=gb2312″ %>
<%@ page language=”java” import=”javax.xml.parsers.*” %>
<%@ page import=”org.w3c.dom.*” %>
<%@ page import=”canyin.*” %>
<jsp:useBean id=”xmlBean” class=”canyin.connXmlBean” scope=”page” />
<%
session.setMaxInactiveInterval(1800);

Document doc;
NodeList users;
String strExc=”";
String strUsername,strPassword;
strUsername=(String)request.getParameter(”username”);
strPassword=(String)request.getParameter(”userpass”);
//校验数据是否为空
if (strUsername==”" || strPassword==”" ){
out.println(”<script language=”javascript”>”);
out.println(”alert(”用户名或密码有空值!”);”);
out.println(”window.location.href=”/index.html”;”);
out.println(”</script>”);
return;
}
xmlBean.connXml(”webapps/canyin/data/users.xml”);
doc=xmlBean.getXmlDoc();
try{
users =doc.getElementsByTagName(”user”);
for (int i=0;i<users.getLength();i ){
Element user=(Element) users.item(i);
String strAtrNameValue=user.getAttributeNode(”name”).getNodeValue();
String strAtrPassWordValue=user.getAttributeNode(”password”).getNodeValue();
String strAtrRoleValue=user.getAttributeNode(”roles”).getNodeValue();

if (strAtrNameValue.equals(strUsername) && strAtrPassWordValue.equals(strPassword)){
if (strAtrRoleValue.equals(”admin”)){
out.println(”<script language=”javascript”>”);
out.println(”alert(”欢迎管理员登陆系统!”);”);
out.println(”</script>”);
//设置标示用户身份de session(sesUserRole) ,管理员身份为 admin
session.setAttribute(”sesUserRole”,”admin”);
//跳转到管理页面
response.sendRedirect(”admin/admin_rest.jsp”);
return;
}else{
//设置标示用户身份de session(sesUserRole) ,管理员身份为 user
session.setAttribute(”sesUserRole”,”user”);
//跳转到普通用户页面
response.sendRedirect(”index.jsp”);
return;
}
}else{
out.println(”<script language=”javascript”>”);
out.println(”alert(”用户名或密码错误!”);”);
out.println(”history.go(-1);”);
out.println(”</script>”);
return;
}
}
}catch(Exception e){
strExc=e.toString();
}
%>
说明:…….
/tomcat/webapps/canyin/jsp/admin/admin_rest.jsp
相关代码:
<%– oddWorld 餐饮管理系统(简体中文版) 2002年12月1日
copy right by joard ast
admin_rest.jsp 功能:后台管理页面,餐馆管理页面.
–%>
<%@ page contentType=”text/html;charset=gb2312″ %>
<%@ page language=”java” import=”javax.xml.parsers.*” %>
<%@ page import=”javax.xml.transform.*” %>
<%@ page import=”org.w3c.dom.*” %>
<%@ page import=”canyin.*” %>
<%@ include file=”../../include/sys_dialog.jsp” %>
<jsp:useBean id=”checkSessionBean” class=”canyin.checkSessionBean” scope=”page” />
<jsp:useBean id=”xmlBean” class=”canyin.connXmlBean” scope=”page” />
<jsp:useBean id=”writeXmlBean” class=”canyin.writeXmlBean” scope=”page” />
<%//校验可户身份,判断是不是管理员
if(!checkSessionBean.checkSessionBean(request,”sesUserRole”,”admin”)){
out.print(showDialog(”您没有管理de权限!”,”/index.html”));
return;
}
//从餐馆资料文件 rest.xml 中得到相关数据
Document doc;
NodeList restaurants;
String strAct;
int intId=0;
String strOperation=”show”;
//接受外部传入de参数
strAct=(String)request.getParameter(”act”);
xmlBean.connXml(”webapps/canyin/data/restaurants.xml”);
doc=xmlBean.getXmlDoc();
restaurants =doc.getElementsByTagName(”restaurant”);
//根据外部传入de参数来决定对 restaurant.xml 文件de操作
if (strAct!=null){
if(strAct.equals(”addnewDo”)){
String strName;
String strPhone;
String strAddress;
Text textseg;
strName=(String)request.getParameter(”name”).trim();
strPhone=(String)request.getParameter(”phone”).trim();
strAddress=(String)request.getParameter(”address”).trim();
//数据校验
if(strName==null){
out.print(showDialog(”餐馆名称不能为空!”));
return;
}
if(strPhone==null){
out.print(showDialog(”餐馆电话不能为空!”));
return;
}
/*if(strAddress==null){
out.print(showDialog(”餐馆地址不能为空!”));
return;
}*/
//校验数据de唯一性
for(int i=0;i<restaurants.getLength();i ){
Element restaurant=(Element) restaurants.item(i);
if(((String)restaurant.getElementsByTagName(”name”).item(0).getFirstChild().getNodeValue()).equals(strName)){
out.print(showDialog(”餐馆名称重复!”));
return;
}else{
if(((String)restaurant.getElementsByTagName(”name”).item(0).getFirstChild().getNodeValue()).equals(strPhone)){
out.print(showDialog(”餐馆电话重复!”));
return;
}
}
}

//得到已有de记录数,给新增de餐馆记录设定唯一de递增deid 属性
int intNum=0;
Element restNum=(Element)doc.getElementsByTagName(”restaurants”).item(0);
intNum=Integer.parseInt(restNum.getAttributeNode(”num”).getNodeValue());
intNum =1;
//为restaurantsde属性num de数值加1
restNum.getAttributeNode(”num”).setNodeValue(String.valueOf(intNum));
//新增节点
Element newRestaurant=doc.createElement(”restaurant”);
Attr newArrId=doc.createAttribute(”id”);
//Attribute newArrId = new Attribute(”id”,String.valueOf(intNum));
textseg=doc.createTextNode(String.valueOf(intNum));
newArrId.setValue(String.valueOf(intNum));
newRestaurant.setAttributeNode(newArrId);
Element newName=doc.createElement(”name”);
textseg=doc.createTextNode(strName);
newName.appendChild(textseg);
newRestaurant.appendChild(newName);
Element newPhone=doc.createElement(”phone”);
textseg=doc.createTextNode(strPhone);
newPhone.appendChild(textseg);
newRestaurant.appendChild(newPhone);
Element newAddress=doc.createElement(”address”);
textseg=doc.createTextNode(strAddress);
newAddress.appendChild(textseg);
newRestaurant.appendChild(newAddress);
doc.getDocumentElement().appendChild(newRestaurant);
//调用bean 写入相应dexml文件
writeXmlBean.writeXml(doc,”webapps/canyin/data/restaurants.xml”);
response.sendRedirect(request.getRequestURI());
return;
}
if(strAct.equals(”modiDo”)){
String strName;
String strPhone;
String strAddress;
Text textseg;
int modiId;
//记录要修改de记录是item(i)de哪一项
int intI=0;
strName=(String)request.getParameter(”name”).trim();
strPhone=(String)request.getParameter(”phone”).trim();
strAddress=(String)request.getParameter(”address”).trim();
modiId=Integer.parseInt(request.getParameter(”recordId”).trim());
//数据校验
if(strName==null){
out.print(showDialog(”餐馆名称不能为空!”));
return;
}
if(strPhone==null){
out.print(showDialog(”餐馆电话不能为空!”));
return;
}
if(modiId==0){
out.print(showDialog(”您要修改餐馆de记录不存在!”));
return;
}
/*if(strAddress==null){
out.print(showDialog(”餐馆地址不能为空!”));
return;
}*/
//标志显示记录存在
boolean recordExist=false;
//校验数据de唯一性
for(int i=0;i<restaurants.getLength();i ){
Element restaurant=(Element) restaurants.item(i);
if(Integer.parseInt(restaurant.getAttributeNode(”id”).getNodeValue())==modiId){
recordExist=true;
intI=i;
}
if(((String)restaurant.getElementsByTagName(”name”).item(0).getFirstChild().getNodeValue()).equals(strName) && Integer.parseInt(restaurant.getAttributeNode(”id”).getNodeValue())!=modiId ){
out.print(showDialog(”餐馆名称重复!”));
return;
}else{
if(((String)restaurant.getElementsByTagName(”name”).item(0).getFirstChild().getNodeValue()).equals(strPhone) && Integer.parseInt(restaurant.getAttributeNode(”id”).getNodeValue())!=modiId ){
out.print(showDialog(”餐馆电话重复!”));
return;
}
}
}

if(!recordExist){
out.print(showDialog(”您要修改餐馆de记录不存在!”));
return;
}else{
//进行记录更改de操作
try{
Element modiRestaurant=(Element) restaurants.item(intI);
modiRestaurant.getElementsByTagName(”name”).item(0).getFirstChild().setNodeValue(strName);
modiRestaurant.getElementsByTagName(”phone”).item(0).getFirstChild().setNodeValue(strPhone);
modiRestaurant.getElementsByTagName(”address”).item(0).getFirstChild().setNodeValue(strAddress);
//调用bean 写入相应dexml文件
writeXmlBean.writeXml(doc,”webapps/canyin/data/restaurants.xml”);
response.sendRedirect(request.getRequestURI());
return;
}catch(Exception e){}
}
}
//进行删除操作
if(strAct.equals(”del”)){
int delId;
//记录要修改de记录是item(i)de哪一项
int intI=0;
delId=Integer.parseInt(request.getParameter(”recordId”).trim());
if(delId==0){
out.print(showDialog(”您要修改餐馆de记录不存在!”));
return;
}
file://标志显示记录存在
boolean recordExist=false;
//校验数据de唯一性
for(int i=0;i<restaurants.getLength();i ){
Element restaurant=(Element) restaurants.item(i);
if(Integer.parseInt(restaurant.getAttributeNode(”id”).getNodeValue())==delId){
recordExist=true;
intI=i;
}
}
if(!recordExist){
out.print(showDialog(”您要删除餐馆de记录不存在!”));
return;
}else{
//进行记录删除de操作
try{
Node delNode=(Node)restaurants.item(intI);
doc.getElementsByTagName(”restaurants”).item(0).removeChild(delNode);
//调用bean 写入相应dexml文件
writeXmlBean.writeXml(doc,”webapps/canyin/data/restaurants.xml”);
response.sendRedirect(request.getRequestURI());
return;
}catch(Exception e){}
}
}
}
//由外部传入参数决定页面相应de处理状态
if (strAct==null){
strOperation=”show”;
}else{
if (strAct.equals(”modi”)){
strOperation=”modi”;
intId=Integer.parseInt(request.getParameter(”recordId”));
}else{
if(strAct.equals(”addnew”)){
strOperation=”addnew”;
}else{
strOperation=”show”;
}
}
}

//如果为空记录,则变更页面状态为“新增”
if (restaurants.getLength()==0){
strOperation=”addnew”;
}
%>
<html>
<head>
<title>oddWorld 餐饮系统</title>
<meta http-equiv=”Content-Type” content=”text/html; charset=gb2312″>
<meta http-equiv=”expires” content=”0″>
<link rel=”stylesheet” href=”../../include/itsp.css” type=”text/css”>
</head>
<body >
<div align=”center”>
<table width=”100%” border=”0″ cellspacing=”0″ cellpadding=”0″ height=”22″>
<tr>
<td width=”1″><img src=”../../images/top_r1.GIF” width=”62″ height=”22″></td>
<td width=150 align=”center”> 餐饮系统管理–餐馆管理</td>
<td><img src=”../../images/top_r2.GIF” width=”294″ height=”22″></td>
<td width=100 align=”center”><a href=”/index.html”>[ 退出系统 ]</a></td>
</tr>
</table>
<br>
<br>
<table bgcolor=”#999999″ align=center border=0 cellpadding=1 cellspacing=1
width=”90%”>
<tbody>
<tr bgcolor=”#efefef” align=”center” valign=”middle”>
<td class=ttTable height=30 width=”20″> </td>
<td class=ttTable height=30 width=”0″>餐馆名称</td>
<td class=ttTable height=30 width=”0″>餐馆电话</td>
<td class=ttTable height=30 width=”0″>
<div align=”center”>餐馆地址</div>
</td>
<td class=ttTable height=30 width=”30″>
<div align=”center”>修改</div>
</td>
<td class=ttTable height=30 width=”30″>
<div align=”center”>删除</div>
</td>
</tr>
<%
for(int i=0;i<restaurants.getLength();i )
{
Element restaurant=(Element) restaurants.item(i);
if (strOperation==”modi” && Integer.parseInt(restaurant.getAttributeNode(”id”).getNodeValue())==intId){
%>
<%//显示修改de格式%>
<tr align=”center” bgcolor=”#ffffff” valign=”middle”>
<form name=dataform action=”<%=request.getRequestURI()%>?act=modiDo” method=”post” onSubmit=”return checkform(this);” >
<td class=tdsmall height=25 width=”20″>
<input type=”hidden” name=”recordId” value=”<%=restaurant.getAttributeNode(”id”).getNodeValue()%>”>
<%=(i 1)%></td>
<td class=tdsmall height=25>
<input name=”name” class=stedit
style=”HEIGHT: 22px; WIDTH: 150px” value=”<%if(restaurant.getElementsByTagName(”name”).item(0).hasChildNodes()){
out.print(restaurant.getElementsByTagName(”name”).item(0).getFirstChild().getNodeValue());
}%>
” maxlength=”40″ >
</td>
<td class=tdsmall height=25>
<input name=”phone” class=stedit
style=”HEIGHT: 22px; WIDTH: 100px” value=”<%if(restaurant.getElementsByTagName(”phone”).item(0).hasChildNodes()){
out.print(restaurant.getElementsByTagName(”phone”).item(0).getFirstChild().getNodeValue());
}%>” maxlength=”20″ >
</td>
<td class=tdsmall height=25>
<input name=”address” class=stedit
style=”HEIGHT: 22px; WIDTH: 200px” value=”<%
if(restaurant.getElementsByTagName(”address”).item(0).hasChildNodes()){
out.print(restaurant.getElementsByTagName(”address”).item(0).getFirstChild().getNodeValue());
}%>” maxlength=”100″ >
</td>
<td class=tdsmall height=25 width=”25″><a href=”javascript:if (checkform()==false);”><img border=0
height=15 src=”../../images/editok.gif” width=15></a></td>
<td class=tdsmall height=25 width=”25″> </td>
</form>
</tr>
<% }else{
//显示正常de格式 %>
<tr align=”center” bgcolor=”#ffffff” valign=”middle”>
<td class=tdsmall height=25 width=”20″><%=(i 1)%></td>
<td class=tdsmall height=25 width=”0″><%if(restaurant.getElementsByTagName(”name”).item(0).hasChildNodes()){
out.print(restaurant.getElementsByTagName(”name”).item(0).getFirstChild().getNodeValue());
}%>
</td>
<td class=tdsmall height=25 width=”0″><%if(restaurant.getElementsByTagName(”phone”).item(0).hasChildNodes()){
out.print(restaurant.getElementsByTagName(”phone”).item(0).getFirstChild().getNodeValue());
}%></td>
<td class=tdsmall height=25 width=”0″>
<%
if(restaurant.getElementsByTagName(”address”).item(0).hasChildNodes()){
out.print(restaurant.getElementsByTagName(”address”).item(0).getFirstChild().getNodeValue());
}%>
</td>
<td class=tdsmall height=25 width=”30″><a href=”<%=request.getRequestURI()%>?act=modi&recordId=<%=restaurant.getAttributeNode(”id”).getNodeValue()%>”><img border=0
height=15 src=”../../images/edit.gif” width=15></a></td>
<td class=tdsmall height=25 width=”30″><img border=0
height=15
onClick=”javascript:if(confirm(”您是否确定删除本记录,删除后将导至记录无法使用?”)){window.location.href=”<%=request.getRequestURI()%>?act=del&recordId=<%=restaurant.getAttributeNode(”id”).getNodeValue()%>”;}”
src=”../../images/delete.gif” style=”CURSOR: hand” width=15> </td>
</tr>
<% }
}%>
<% if (strOperation==”addnew”){
//显示新增de格式%>
<tr align=”center” bgcolor=”#ffffff” valign=”middle”>
<form name=dataform2 action=”<%=request.getRequestURI()%>?act=addnewDo” method=”post” onSubmit=”return checkform2(this);” >
<td class=tdsmall height=25 width=”20″></td>
<td class=tdsmall height=25>
<input name=”name” class=stedit
style=”HEIGHT: 22px; WIDTH: 150px” value=”" maxlength=”40″ >
</td>
<td class=tdsmall height=25>
<input name=”phone” class=stedit
style=”HEIGHT: 22px; WIDTH: 100px” value=”" maxlength=”20″ >
</td>
<td class=tdsmall height=25>
<input name=”address” class=stedit
style=”HEIGHT: 22px; WIDTH: 200px” value=”" maxlength=”100″ >
</td>
<td class=tdsmall height=25 width=”25″><a href=”javascript:if (checkform2()==false);”><img border=0
height=15 src=”../../images/editok.gif” width=15></a></td>
<td class=tdsmall height=25 width=”25″> </td>
</form>
</tr>
<% } %>
</tbody>
</table>
<br>
<table align=center border=0 cellpadding=0 cellspacing=2 width=”95%”>
<tbody>
<tr valign=center>
<td align=middle> <br>
<table border=0 cellpadding=0 cellspacing=0>
<tr>
<td>
<% if (strOperation==”addnew”){
%>
<input class=stbtm name=update onClick=”javascript:if (checkform2()==false);” type=button value=”更新记录”>
<% }else{
if(strOperation==”modi”){
%>
<input class=stbtm name=update onClick=”javascript:if (checkform()==false);” type=button value=”更新记录”>
<%
}else{
%>
<input class=stbtm type=”button” name=”Button” value=”新 增” onClick=”javascript:window.location.href=”<%=request.getRequestURI()%>?act=addnew”;”><%
}
} %>
</td>
<td>
<input class=stbtm type=”button” name=”Button” value=”返 回” onClick=”javascript:window.location.href=”index.jsp”;”>
</td>
</tr>
</table>
</td>
</tr>
</table>
<p> </p>
</div>
</body>
</html>
<SCRIPT LANGUAGE=javascript>
<!–
function checkform2()
{
var Checkblank = /^(\s*|(\ )|(\.))*$/;
if (Checkblank.test(dataform2.name.value))
{
alert(”餐馆名称不能为空!”);
dataform2.name.focus();
return false;
}
if (Checkblank.test(dataform2.phone.value))
{
alert(”餐馆电话不能为空!”);
dataform2.phone.focus();
return false;
}
window.dataform2.submit();
}
function checkform()
{
var Checkblank = /^(\s*|(\ )|(\.))*$/;
if (Checkblank.test(dataform.name.value))
{
alert(”餐馆名称不能为空!”);
dataform.name.focus();
return false;
}
if (Checkblank.test(dataform.phone.value))
{
alert(”餐馆电话不能为空!”);
dataform.phone.focus();
return false;
}

window.dataform.submit();
}
–>
</SCRIPT>
说明:本文件de书写有很多地方并不简练,因为在程式de开发过程中,过分简练de程序往往会带来后期维护de困难.
开发心得:
doc.getElementsByTagName(”restaurants”).item(int i)de返回值是node 型,如果不是要调用它de属性值,没有必要强制转型为 Element型.可以直接操作.本系统因为开发de参考资料de错误,所以全都采用了强制转型.可以在以后de开发中考虑使用node 直接进行操作.
trim() 和 Interger.parseInt() 函数都不可以接受null 型de数值
在tomcat 下左右de文件都是目录从TOMCAT 算起,具体情况请参见\webapps\canyin\jsp\userjudge.jsp 里关于xml 路径de写法.

对原相关代码感兴趣de朋友请通过如下信箱和我联系,joard@163.com