﻿<?xml version="1.0" encoding="utf-8" standalone="yes"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:trackback="http://madskills.com/public/xml/rss/module/trackback/" xmlns:wfw="http://wellformedweb.org/CommentAPI/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/"><channel><title>BlogJava-小菜毛毛技术分享-随笔分类-struts2</title><link>http://www.blogjava.net/caizh2009/category/44465.html</link><description>与大家共同成长</description><language>zh-cn</language><lastBuildDate>Wed, 31 Mar 2010 03:17:26 GMT</lastBuildDate><pubDate>Wed, 31 Mar 2010 03:17:26 GMT</pubDate><ttl>60</ttl><item><title> OGNL表达式语言介绍</title><link>http://www.blogjava.net/caizh2009/archive/2010/03/31/317015.html</link><dc:creator>小菜毛毛</dc:creator><author>小菜毛毛</author><pubDate>Wed, 31 Mar 2010 02:52:00 GMT</pubDate><guid>http://www.blogjava.net/caizh2009/archive/2010/03/31/317015.html</guid><wfw:comment>http://www.blogjava.net/caizh2009/comments/317015.html</wfw:comment><comments>http://www.blogjava.net/caizh2009/archive/2010/03/31/317015.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.blogjava.net/caizh2009/comments/commentRss/317015.html</wfw:commentRss><trackback:ping>http://www.blogjava.net/caizh2009/services/trackbacks/317015.html</trackback:ping><description><![CDATA[<p>OGNL介绍<br />
OGNL是Object-Graph Navigation
Language的缩写，它是一种功能强大的表达式语言（Expression
Language，简称为EL），通过它简单一致的表达式语法，可以存取对象的任意属性，调用对象的方法，遍历整个对象的结构图，实现字段类型转化等功
能。它使用相同的表达式去存取对象的属性。<br />
XWork遵循&#8220;不要重复地发明同一个轮子&#8221;的理论，它的表达式语言核心用的就是这个OGNL。我们先
来看看一个简单的例子：<br />
还记得我们用户注册的那个例子吗？我们输入框的name用到的名字就是OGNL的表达式，比如：用户名的输入
框：&#8220;&lt;input type="text"
name="user.username"&gt;&#8221;，在用户注册成功之后我们要显示用户注册的信息，用了&#8220;&lt;ww:property
value="user.username"/&gt;&#8221;。Input输入框里的&#8220;user.username&#8221;，它解析成Java语句
为：getUser().setUsername();，property标签里的&#8220;user.username&#8221;解析为Java语
句：getUser.getUsername();。<br />
我们的两个表达式都是相同的，但前一个保存对象属性的值，后一个是取得对象属性的值。表达式
语言简单、易懂却又功能强大，关于OGNL更多的介绍可以去<a href="http://www.ognl.org/">http://www.ognl.org</a>，
那里有很详细的文档<br />
&nbsp;<br />
值堆栈－OgnlValueStack<br />
OGNL在框架中的应用，最主要是支持我们的值堆栈（Value
Stack）——OgnlValueStack，它主要的功能是通过表达式语言来存取对象的属性。用户界面输入数据，它会根据保存表达式将数据依次保存到
它堆栈的对象中，业务操作完成，结果数据会通过表达式被获取、输出。<br />
还记得我们用户注册的例子吗？下面我们用一段程序来演示它向
OgnlValueStack中保存、取得数据的步骤：<br />
&nbsp;<br />
// DemoRegisterValueStack<br />
package
example.register;<br />
import com.opensymphony.xwork.util.OgnlValueStack;<br />
&nbsp;<br />
public
class DemoRegisterValueStack {<br />
&nbsp;&nbsp;&nbsp; public void demo(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
RegisterAction action = new RegisterAction();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; OgnlValueStack
valueStack= new OgnlValueStack();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; valueStack.push(action);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; valueStack.setValue("user.username","Babydavic");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("username =
"+valueStack.findValue("user.username"));<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;<br />
&nbsp;&nbsp;&nbsp; public
static void main(String[] args) {<br />
DemoRegisterValueStack
demoValueStack = new DemoRegisterValueStack();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
demoValueStack.demo();<br />
&nbsp;&nbsp;&nbsp; }<br />
}<br />
&nbsp;<br />
我们来看一看它的demo()方法：<br />
1、&nbsp;&nbsp;
创建我们的Action（RegisterAction）类的对象action，将action对象压入堆栈valueStack中。在WebWrok中
Action的创建、入栈是在DefaultActionInvocation构造函数中进行的，详细介绍见：ServletDispatcher原理。<br />
2、&nbsp;&nbsp;
通过表达式语言，调用堆栈对象的get()、set()方法，设置该对象的值。<br />
&nbsp;&nbsp; public void setValue(String
expr, Object value)<br />
&nbsp;&nbsp;
语句：valueStack.setValue("user.username","Babydavic");<br />
&nbsp;&nbsp;
的作用等同于：action.getUser().setUsername("Babydavic");<br />
3、&nbsp;&nbsp;
通过表达式语言，去堆栈对象中查找我们前面保存的值，并在控制台打印。valueStack.findValue("user.username")等同
与语句：<br />
action.getUser().getUsername()<br />
最后控制台打印的结果：<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
username = Babydavic<br />
&nbsp;<br />
&nbsp;<br />
CompoundRoot<br />
在OgnlValueStack中，一个堆栈其
实是一个List。查看OgnlValueStack你会发现，堆栈就是
com.opensymphony.xwork.util.CompoundRoot类的对象：<br />
&nbsp;<br />
public class
CompoundRoot extends ArrayList {<br />
&nbsp;&nbsp;&nbsp; //~ Constructors
/////////////////////////////////////<br />
&nbsp;&nbsp;&nbsp; public CompoundRoot() {<br />
}<br />
&nbsp;<br />
&nbsp;&nbsp;&nbsp;
public CompoundRoot(List list) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; super(list);<br />
}<br />
&nbsp;<br />
&nbsp;&nbsp;&nbsp;
//~ Methods ////////////////////////////////////////////<br />
&nbsp;&nbsp;&nbsp; public
CompoundRoot cutStack(int index) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return new
CompoundRoot(subList(index, size()));<br />
}<br />
&nbsp;<br />
&nbsp;&nbsp;&nbsp; public Object
peek() {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return get(0);<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp; public Object pop() {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
return remove(0);<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp; public void push(Object o) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
add(0, o);<br />
&nbsp;&nbsp;&nbsp; }<br />
}</p>
<p>我们通过表达式向堆栈对象操作时，我们并不知道堆栈中有哪些对象。OgnlValueStack会根据堆栈由上向下的顺序（先入栈在下面，最后入栈
在最上面）依次去查找与表达式匹配的对象方法，找到即进行相应的存取操作。假设后面对象也有相同的方法，将不会被调用。<br />
下面我们看一个对
OgnlValueStack操作的程序，它主要演示了如何对Map对象的存取和OgnlValueStack堆栈的原理<br />
&nbsp;<br />
package
example.register;<br />
&nbsp;<br />
import
com.opensymphony.xwork.util.OgnlValueStack;<br />
&nbsp;<br />
public class
DemoGroupValueStack {<br />
&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp; public void demoAction(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
DemoGroupAction action = new DemoGroupAction();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
OgnlValueStack valueStack= new OgnlValueStack();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
valueStack.push(action);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; User zhao = new User();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
zhao.setUsername("zhao");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; zhao.setEmail("<a href="&#109;&#97;&#105;&#108;&#116;&#111;&#58;&#122;&#104;&#97;&#111;&#64;&#121;&#97;&#104;&#111;&#111;&#46;&#99;&#111;&#109;&#46;&#99;&#110;">zhao@yahoo.com.cn</a>");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
User qian = new User();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; qian.setUsername("qian");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
qian.setEmail("<a href="&#109;&#97;&#105;&#108;&#116;&#111;&#58;&#113;&#105;&#97;&#110;&#64;&#121;&#97;&#104;&#111;&#111;&#46;&#99;&#111;&#109;&#46;&#99;&#110;">qian@yahoo.com.cn</a>");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; valueStack.setValue("users['zhao']",zhao);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
valueStack.setValue("users['qian']",qian);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("users['zhao'] =
"+valueStack.findValue("users['zhao']"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("users['qian'] =
"+valueStack.findValue("users['qian']"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("users size = "+valueStack.findValue("users.size"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; System.out.println("allUserName[0] =
"+valueStack.findValue("allUserName[0]"));<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;
public void demoModels(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; User model_a = new
User();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; model_a.setUsername("model_a");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; User
model_b = new User();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; model_b.setUsername("model_b");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
User model_c = new User();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; model_c.setUsername("model_c");<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; OgnlValueStack valueStack= new OgnlValueStack();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
valueStack.push(model_a);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; valueStack.push(model_b);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
valueStack.push(model_c);<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("username = "+valueStack.findValue("username"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("[1].username =
"+valueStack.findValue("[1].username"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("[0].toString = "+valueStack.findValue("[0]"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("[1].toString = "+valueStack.findValue("[1]"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
System.out.println("[2].toString = "+valueStack.findValue("[2]"));<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp; public static void main(String[] args) {<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
DemoGroupValueStack demoValueStack = new DemoGroupValueStack();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
demoValueStack.demoAction();<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; demoValueStack.demoModels();<br />
&nbsp;&nbsp;&nbsp;
}<br />
}<br />
&nbsp;<br />
&nbsp;<br />
package example.register;<br />
&nbsp;<br />
import
java.util.ArrayList;<br />
import java.util.HashMap;<br />
import
java.util.List;<br />
import java.util.Map;<br />
&nbsp;<br />
public class
DemoGroupAction {<br />
&nbsp;&nbsp;&nbsp; <br />
&nbsp;&nbsp;&nbsp; private Map users = new HashMap();<br />
&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp; public Map getUsers(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return this.users;<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp;
<br />
&nbsp;&nbsp;&nbsp; public List getAllUserName(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return new
ArrayList(users.keySet());<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp; public String execute(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
//执行业务操作<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return null;<br />
&nbsp;&nbsp;&nbsp; }<br />
&nbsp;&nbsp;&nbsp; public String
toString(){<br />
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; return users.toString();<br />
&nbsp;&nbsp;&nbsp; }<br />
}<br />
注意：1、
Map属性的存取，它的表达式语言如：users['zhao']，注意它用&#8217;&#8217;来引用HashMap的key字符串。<br />
2、
demoModels（）方法演示了OgnlValueStack中堆栈的原理，请特别注意它的
[0].toString、[1].toString、[2].toString，它们依次调用堆栈中对象的toString()方法，并逐一的减少堆栈
最上面的对象。<br />
控制台输出的结果如下：<br />
users['zhao'] =
username=zhao;password=null;email=zhao@yahoo.com.cn;age=0<br />
users['qian']
= username=qian;password=null;email=qian@yahoo.com.cn;age=0<br />
users
size = 2<br />
allUserName[0] = qian<br />
&nbsp;<br />
username = model_c<br />
[1].username
= model_b<br />
[0].toString =
[username=model_c;password=null;email=null;age=0,
username=model_b;password=null;email=null;age=0,
username=model_a;password=null;email=null;age=0]<br />
[1].toString =
[username=model_b;password=null;email=null;age=0,
username=model_a;password=null;email=null;age=0]<br />
[2].toString =
[username=model_a;password=null;email=null;age=0]</p>
<img src ="http://www.blogjava.net/caizh2009/aggbug/317015.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.blogjava.net/caizh2009/" target="_blank">小菜毛毛</a> 2010-03-31 10:52 <a href="http://www.blogjava.net/caizh2009/archive/2010/03/31/317015.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item></channel></rss>