??xml version="1.0" encoding="utf-8" standalone="yes"?>国产成人精品亚洲2020,亚洲国产成人精品女人久久久 ,99999久久久久久亚洲http://www.tkk7.com/ljc-java/模仿中成长,在创C成功Q?/description>zh-cnFri, 09 May 2025 21:57:28 GMTFri, 09 May 2025 21:57:28 GMT60Java中的内部c?/title><link>http://www.tkk7.com/ljc-java/articles/416442.html</link><dc:creator>罗</dc:creator><author>罗</author><pubDate>Fri, 01 Aug 2014 09:34:00 GMT</pubDate><guid>http://www.tkk7.com/ljc-java/articles/416442.html</guid><wfw:comment>http://www.tkk7.com/ljc-java/comments/416442.html</wfw:comment><comments>http://www.tkk7.com/ljc-java/articles/416442.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.tkk7.com/ljc-java/comments/commentRss/416442.html</wfw:commentRss><trackback:ping>http://www.tkk7.com/ljc-java/services/trackbacks/416442.html</trackback:ping><description><![CDATA[<ol> <li>什么是内部c?      <br /> <br /> <div>内部cL指在一个外部类的内部再定义一个类?/div> <div>内部cd以是静态static的,也可用publicQdefaultQprotected和private修饰。(而外部顶U类即类名和文g名相同的只能使用public和defaultQ?/div> <div><span style="color: red;">注意Q内部类是一个编译时的概念,一旦编译成功,׃成ؓ完全不同的两cR对于一个名为Outer的外部类和其内部定义的名为Inner的内部类。编译完成后出现Outer.class和Outer$Inner.class两类?/span><span style="color: #0000ff;">所以内部类的成员变?Ҏ名可以和外部cȝ相同?/span></div> <div>java内部cd为: 成员内部cR静态嵌套类、局部内部类、匿名内部类 ?/div> <br /> </li> <li>内部cȝ共?br /> <br /> <div>(1)、内部类仍然是一个独立的c,在编译之后内部类会被~译成独立的.class文gQ但是前面冠以外部类的类名和$W号 ?/div> <div>(2)、内部类不能用普通的方式讉K。内部类是外部类的一个成员,因此内部cd以自由地讉K外部cȝ成员变量Q无论是否是private??/div> <div>(3)、内部类声明成静态的Q就不能随便的访问外部类的成员变量了Q此时内部类只能讉K外部cȝ静态成员变??/div> </li> <li>成员内部c?br /> <div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> Outer {<br />     <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> a = 10;<br />     <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> b = 15;<br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> print() {<br />         System.out.println("Outer.a="+<span style="color: #0000FF; ">this</span>.a);<br />     }<br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">int</span> add(<span style="color: #0000FF; ">int</span> i,<span style="color: #0000FF; ">int</span> j) {<br />         <span style="color: #0000FF; ">return</span> i+j;<br />     }<br />     <br />     <span style="color: #0000FF; ">class</span> Inner {        <br />         <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> a = 20;<br />         <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> c = b;<br />         <br />         <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> print() {<br />             <span style="color: #008000; ">//</span><span style="color: #008000; ">内部c访问外部类中的同名成员变量</span><span style="color: #008000; "><br /> </span>            System.out.println("Outer.a="+Outer.<span style="color: #0000FF; ">this</span>.a);    <br />             System.out.println("Inner.a="+<span style="color: #0000FF; ">this</span>.a);<br />             System.out.println("a="+a);<br />             <span style="color: #008000; ">//</span><span style="color: #008000; ">内部cM可以直接讉K外部cȝ成员变量和方法(内部cd象持有指向外部类对象的引用。)</span><span style="color: #008000; "><br /> </span>            System.out.println("c="+c);<br />             System.out.println("c+1="+add(c,1));<br />         }<br />     }<br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />         Outer outer = <span style="color: #0000FF; ">new</span> Outer();<br />         outer.print();<br />         <span style="color: #008000; ">//</span><span style="color: #008000; ">内部cd象的创徏依赖于外部类对象Q?/span><span style="color: #008000; "><br /> </span>        outer.<span style="color: #0000FF; ">new</span> Inner().print();   <br />     }<br /> }</div> <font size="2"> <div></div> </font><font size="2"> <div> q个cȝ译后出现Outer.class和Outer$Inner.class两个class文g。编译后成ؓ两个独立的类Q?br /> 因此Q内部类中可以定义与外部cM同名的属性和Ҏ?br /> <br /> 成员内部c,是作ؓ外部cȝ成员Q与外部cȝ属性、方法ƈ列。可以直接用外部类的所有成员和ҎQ即使是private的?br /> 同时外部c要讉K内部cȝ所有成员变量和ҎQ则需要通过内部cȝ对象来获取?/div> <div>要注意的是,成员内部cM能含有static的变量和Ҏ。因为成员内部类需要先创徏了外部类Q才能创建它自己?/div> <br /> <div></div> </font></li> <li>局部内部类<br /> <div>局部内部类Q是指内部类定义在方法和作用域内?/div> (1)、定义在Ҏ?br />     <br /> <div style="font-size: 13px; border: 1px solid #cccccc; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all; background-color: #eeeeee;"><!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> Teacher {<br />     <br />     <span style="color: #0000FF; ">private</span> String name;<br />     <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> age;    <br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> teach() {<br />         <span style="color: #0000FF; ">final</span> String str = "I'm a teacher!";<br />         <span style="color: #0000FF; ">class</span> EnglishTeacher {<br />             <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> teachEnglish() {<br />                 System.out.println("My name is "+name);<br />                 System.out.println("I'm "+age);<br />                 System.out.println(str);<br />                 System.out.println("I teach English");<br />                 <br />             }<br />         }<br />         <br />         EnglishTeacher englishTeacher = <span style="color: #0000FF; ">new</span> EnglishTeacher();<br />         englishTeacher.teachEnglish();<br />     }<br /> <br />     <span style="color: #008000; ">/**</span><span style="color: #008000; "><br />      * </span><span style="color: #808080; ">@param</span><span style="color: #008000; "> args<br />      </span><span style="color: #008000; ">*/</span><br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />         <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>        Teacher teacher = <span style="color: #0000FF; ">new</span> Teacher();<br />         teacher.name = "张三";<br />         teacher.age = 35;<br />         teacher.teach();<br />     }<br /> }<span style="font-size: 14px;"> </span></div> <br /> <br /> (2)、定义在作用域内<br /> <!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><span style="color: #008080; "> </span> <div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><br /> <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> Teacher1 {<br /> <br />     <span style="color: #0000FF; ">private</span> String name;<br />     <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> age;    <br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> teach(String course) {<br />         <span style="color: #0000FF; ">final</span> String str = "I'm a teacher!";<br />         System.out.println(str);<br />         <span style="color: #0000FF; ">if</span>("English".equals(course)) {<br />             <span style="color: #0000FF; ">class</span> EnglishTeacher {<br />                 <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> teachEnglish() {<br />                     System.out.println("My name is "+name);<br />                     System.out.println("I'm "+age);<br />                     System.out.println("I teach English");<br />                 }<br />             }<br />             <br />             EnglishTeacher englishTeacher = <span style="color: #0000FF; ">new</span> EnglishTeacher();<br />             englishTeacher.teachEnglish();<br />         }        <br />     }<br />     <span style="color: #008000; ">/**</span><span style="color: #008000; "><br />      * </span><span style="color: #808080; ">@param</span><span style="color: #008000; "> args<br />      </span><span style="color: #008000; ">*/</span><br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />         <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>        Teacher1 teacher = <span style="color: #0000FF; ">new</span> Teacher1();<br />         teacher.name = "张三";<br />         teacher.age = 35;<br />         teacher.teach("English");<br />     }<br /> <br /> }</div>     <br /> <br /> <div> <div>(1)、局部内部类只能在定义该内部cȝҎ内实例化Q不可以在此Ҏ外对其实例化?/div> <div>(2)、局部内部类对象不能使用该内部类所在方法的非final局部变量?br /> (3)、局部内部类的地位和Ҏ内的局部变量的位置cMQ因此不能修饰局部变量的修饰W也不能修饰局部内部类Q?br />        譬如public、private、protected、static、transient{?/div> <div>因ؓҎ的局部变量位于栈上,只存在于该方法的生命期内。当一个方法结束,其栈l构被删除,局部变量成为历双Ӏ但是该Ҏl束之后Q在Ҏ内创建的内部cd象可能仍然存在于堆中Q例如,如果对它的引用被传递到其他某些代码Qƈ存储在一个成员变量内。正因ؓ不能保证局部变量的存活期和Ҏ内部cd象的一样长Q所以内部类对象不能使用它们?/div> </div> </li> <li>静态嵌套类<br /> <br /> <div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><br /> <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> StaticOuter {<br /> <br />     <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">int</span> a = 10;<br />     <span style="color: #0000FF; ">private</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">int</span> b = 15;<br />     <br />     <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">class</span> StaticInner {<br />         <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> print() {<br />             System.out.println("b="+b);<br />         }<br />         <br />         <span style="color: #0000FF; ">void</span> print1() {<br />             System.out.println("b="+b);<br />         }<br />     }<br />     <span style="color: #008000; ">/**</span><span style="color: #008000; "><br />      * </span><span style="color: #808080; ">@param</span><span style="color: #008000; "> args<br />      </span><span style="color: #008000; ">*/</span><br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />         <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>        StaticOuter.StaticInner.print();<br />         <span style="color: #0000FF; ">new</span> StaticOuter.StaticInner().print1();<br />     }<br /> <br /> }</div> <br /> <div>嵌套cd普通的内部c还有一个区别:普通内部类不能有static数据和static属性,也不能包含嵌套类Q但嵌套cd以?br /> 而嵌套类不能声明为privateQ一般声明ؓpublicQ方便调用?br /> <br /> <div>在静态方法中定义的内部类也是StaticNested ClassQ这时候不能在cd面加static关键字,静态方法中的StaticNested Class?br /> 普通方法中的内部类的应用方式很怼Q它除了可以直接讉K外部cM的static的成员变量,q可以访问静态方法中的局部变量,<br /> 但是Q该局部变量前必须加final修饰W?/div> </div> <br /> </li> <li>匿名内部c?/li> <br /> <div>匿名内部cd是没有名字的内部cR什么情况下需要用匿名内部类Q如果满下面的一些条Ӟ使用匿名内部cL比较合适的Q?/div> <div>·只用到类的一个实??/div> <div>·cd定义后马上用到?/div> <div>·c非常小QSUN推荐是在4行代码以下)</div> <div>·l类命名q不会导致你的代码更Ҏ被理解?/div> <div>在用匿名内部类Ӟ要记住以下几个原则:</div> <div>·匿名内部cM能有构造方法?/div> <div>·匿名内部cM能定义Q何静态成员、静态方法?/div> <div>·匿名内部cM能是public,protected,private,static?/div> <div>·只能创徏匿名内部cȝ一个实例?/div> <div>·一个匿名内部类一定是在new的后面,用其隐含实现一个接口或实现一个类?/div> ·因匿名内部类为局部内部类Q所以局部内部类的所有限刉对其生效?br /> <br /> (1)、承式的匿名内部类<br /> <div style="font-size: 13px; border: 1px solid #cccccc; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all; background-color: #eeeeee;"><!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><br /> <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> Singer {<br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> sing() {<br />         System.out.println("Sing a song");<br />     }<br /> <br />     <span style="color: #008000; ">/**</span><span style="color: #008000; "><br />      * </span><span style="color: #808080; ">@param</span><span style="color: #008000; "> args<br />      </span><span style="color: #008000; ">*/</span><br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />         <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span><br />         Singer singer = <span style="color: #0000FF; ">new</span> Singer() {<br /> <br />             @Override<br />             <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> sing() {<br />                 <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>                System.out.println("Sing a popular song");<br />             }<br />             <br />         };<br />         singer.sing();<br />     }<br /> <br /> }</div> <br /> 输出l果QSing a popular song<br /> <br /> (2)、接口式的匿名内部类<br /> <br /> <div style="background-color:#eeeeee;font-size:13px;border:1px solid #CCCCCC;padding-right: 5px;padding-bottom: 4px;padding-left: 4px;padding-top: 4px;width: 98%;word-break:break-all"><!--<br /> <br /> Code highlighting produced by Actipro CodeHighlighter (freeware)<br /> http://www.CodeHighlighter.com/<br /> <br /> --><br /> <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">interface</span> Programmer {<br />     <br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> code();<br /> <br /> }<br /> <br /> <br /> <br /> <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> TestProgrammer {<br /> <br />     <span style="color: #008000; ">/**</span><span style="color: #008000; "><br />      * </span><span style="color: #808080; ">@param</span><span style="color: #008000; "> args<br />      </span><span style="color: #008000; ">*/</span><br />     <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />         <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>        Programmer javaProgrammer = <span style="color: #0000FF; ">new</span> Programmer() {<br /> <br />             @Override<br />             <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> code() {<br />                 <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>                System.out.println("Java programmer");<br />             }<br />         };<br /> <br />         javaProgrammer.code();<br />         <br />         Programmer phpProgrammer = <span style="color: #0000FF; ">new</span> Programmer() {<br /> <br />             @Override<br />             <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> code() {<br />                 <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /> </span>                System.out.println("Php programmer");<br />             }<br />         };<br /> <br />         phpProgrammer.code();<br />     }<br /> <br /> }</div> <br /> (3)、参数式的匿名内部类<br /><br /><div style="font-size: 13px; border: 1px solid #cccccc; padding: 4px 5px 4px 4px; width: 98%; word-break: break-all; background-color: #eeeeee;"><!--<br /><br />Code highlighting produced by Actipro CodeHighlighter (freeware)<br />http://www.CodeHighlighter.com/<br /><br />--><br /><span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">interface</span> Programmer {<br />    <br />    <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> code();<br /><br />}<br /><br /><br /><br /><br /><span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">class</span> TestProgrammer1 {<br /><br />    <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> testCode(Programmer p) {<br />        p.code();<br />    }<br />    <br />    <span style="color: #008000; ">/**</span><span style="color: #008000; "><br />     * </span><span style="color: #808080; ">@param</span><span style="color: #008000; "> args<br />     </span><span style="color: #008000; ">*/</span><br />    <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">static</span> <span style="color: #0000FF; ">void</span> main(String[] args) {<br />        <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /></span>        TestProgrammer1 testProgrammer1 = <span style="color: #0000FF; ">new</span> TestProgrammer1();<br />        testProgrammer1.testCode(<span style="color: #0000FF; ">new</span> Programmer() {<br />            <br />            @Override<br />            <span style="color: #0000FF; ">public</span> <span style="color: #0000FF; ">void</span> code() {<br />                <span style="color: #008000; ">//</span><span style="color: #008000; "> TODO Auto-generated method stub</span><span style="color: #008000; "><br /></span>                System.out.println("testing code");<br />            }<br />        });<br />    }<br /><br />}</div><br /><br /><li>Z么需要内部类<br /><br /></li><div>典型的情冉|Q内部类l承自某个类或实现某个接口,内部cȝ代码操作创徏其的外围cȝ对象。所以你可以认ؓ内部cL供了某种q入其外围类的窗口?br />使用内部cL吸引人的原因是:</div><div>每个内部c都能独立地l承自一个(接口的)实现Q所以无论外围类是否已经l承了某个(接口的)实现Q对于内部类都没有媄响。如果没有内部类提供的可以承多个具体的或抽象的cȝ能力Q一些设计与~程问题很难解冟뀂从q个角度看,内部cM得多重承的解决Ҏ变得完整。接口解决了部分问题Q而内部类有效地实C“多重l承”?/div> </ol><img src ="http://www.tkk7.com/ljc-java/aggbug/416442.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.tkk7.com/ljc-java/" target="_blank">罗</a> 2014-08-01 17:34 <a href="http://www.tkk7.com/ljc-java/articles/416442.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>Java 设计模式http://www.tkk7.com/ljc-java/articles/415369.htmlWed, 02 Jul 2014 08:16:00 GMThttp://www.tkk7.com/ljc-java/articles/415369.htmlhttp://www.tkk7.com/ljc-java/comments/415369.htmlhttp://www.tkk7.com/ljc-java/articles/415369.html#Feedback0http://www.tkk7.com/ljc-java/comments/commentRss/415369.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/415369.htmlJava设计模式分ؓ创徏模式, l构模式, 行ؓ模式 3U类型:
Java设计模式?span style="color: #ff0000;">创徏模式包括Q?/div>
    Factory,                         工厂模式
    Singleton,                      单例模式
    Builder,                          建造模?/div>
    Prototype,                     原型模式
Java设计模式?span style="color: #ff0000;">l构模式包括Q?/div>
    Facade,                         门面模式
    Decorator,                     装饰模式
    Composite,                    合成模式
    Proxy,                           代理模式
    Adapter,                        适配器模?/div>
    Bridge,                          桥梁模式
    Flyweight,                      ׃n元类模式
Java设计模式?span style="color: #ff0000;">行ؓ模式包括Q?/div>
    Chain of responsibleif,    责Q链模?/div>
    Command,                    命o模式
    Strategy,                      {略模式
    Observer,                      观察模式
    Interpreter ,                  解释器模?/div>
    Iterator,                        q代模式
    Mediator,                       中介模式
    Memento,                      备忘录模?/div>
    State,                           状态模?/div>
    Template,                      模板模式
    Visitor,                         讉K者模?/div>

2014-07-02 16:16 发表评论
]]>jQuery操作radiohttp://www.tkk7.com/ljc-java/articles/401141.htmlTue, 02 Jul 2013 09:44:00 GMThttp://www.tkk7.com/ljc-java/articles/401141.htmlhttp://www.tkk7.com/ljc-java/comments/401141.htmlhttp://www.tkk7.com/ljc-java/articles/401141.html#Feedback0http://www.tkk7.com/ljc-java/comments/commentRss/401141.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/401141.html<input type="radio">如下Q?br />

<input type="radio" name="city" value="BeiJing">北京
<input type="radio" name="city" value="TianJin">天|
<input type="radio" name="city" value="NanJing">南京
<input type="radio" name="city" value="YangZhou">扬州
<input type="radio" name="city" value="SuZhou">苏州

    1、获取选中的radio的|

$("input[name='city']:checked").val();

  使用元素选择器,再用属性过滤器name='city'Q最后?checked选取被选中的元素?/span>

  2、给指定值的radio讄选中状态:

$("input[name='city'][value='YangZhou']").attr("checked",true);

  lname="city"而且value="YangZhou"的radio讄选中状态?/span>

  3、取消name="city"的radio的选中状态:

$('input[name="city"]:checked').attr("checked",false);

  4、获取name="city"的radio的个敎ͼ

$("input[name='city']").length;

  5、获取name="city"而且索引是偶数的radio:

$("input[name='city']:even");

  索引是从0开始的?/span>

  6、获取name="city"而且索引是奇数的radio:

$("input[name='city']:odd");

  索引是从0开始的?/span>

  7、P代radio:


$("input[name='city']").each(function(i,obj){
    //i,q代的下标,?开?br />    //obj,当前的对?HTMLInputElement),可以使用obj.value格式获取属性?br />    //$(this);当前jQuery对象,可以使用$(this).val()获取属性?br />});

  q代name="city"的radio?/span>

  8、禁用radio:

$("input[name='city']").attr("disabled",true);

  用name="city"的radio?/span>

  9、启用radio:

$("input[name='city']").attr("disabled",false);

  启用name="city"的radio?/span>



2013-07-02 17:44 发表评论
]]>
??/title><link>http://www.tkk7.com/ljc-java/archive/2011/12/05/365600.html</link><dc:creator>罗</dc:creator><author>罗</author><pubDate>Mon, 05 Dec 2011 07:57:00 GMT</pubDate><guid>http://www.tkk7.com/ljc-java/archive/2011/12/05/365600.html</guid><wfw:comment>http://www.tkk7.com/ljc-java/comments/365600.html</wfw:comment><comments>http://www.tkk7.com/ljc-java/archive/2011/12/05/365600.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.tkk7.com/ljc-java/comments/commentRss/365600.html</wfw:commentRss><trackback:ping>http://www.tkk7.com/ljc-java/services/trackbacks/365600.html</trackback:ping><description><![CDATA[<strong>? 架是Z解决一个又一个在Web开发中所遇到的问题而诞生的。不同的框架Q都是ؓ了解决不同的问题Q但是对于程序员而言Q他们只是jar包而已。框架的? ~点的评论,也完全取决于其对问题解决E度和解x式的优雅性的评论。所以,千万不要Z学习框架而学习框Ӟ而是要ؓ了解决问题而学习框Ӟq才是一? E序员的正确学习之道?/strong><img src ="http://www.tkk7.com/ljc-java/aggbug/365600.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.tkk7.com/ljc-java/" target="_blank">罗</a> 2011-12-05 15:57 <a href="http://www.tkk7.com/ljc-java/archive/2011/12/05/365600.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>JAVA事务,JTA,JDBC,JDO,DAO,JNDI概念(转蝲) http://www.tkk7.com/ljc-java/articles/365595.htmlMon, 05 Dec 2011 07:17:00 GMThttp://www.tkk7.com/ljc-java/articles/365595.htmlhttp://www.tkk7.com/ljc-java/comments/365595.htmlhttp://www.tkk7.com/ljc-java/articles/365595.html#Feedback0http://www.tkk7.com/ljc-java/comments/commentRss/365595.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/365595.html一、什么是Java事务

通常的观念认为,事务仅与数据库相兟?/span> 
事务必须服从ISO/IEC所制定?/span>ACID原则?/span>

ACID是原子性(atomicityQ、一致性(consistencyQ、隔L(isolationQ和持久性(durabilityQ的~写?/span>

事务的原子性表CZ务执行过E中的Q何失败都导致事务所做的M修改失效?/span>

一致性表C当事务执行p|Ӟ所有被该事务媄响的数据都应该恢复到事务执行前的状态?/span>

隔离性表C在事务执行q程中对数据的修改,在事务提交之前对其他事务不可见?/span>

持久性表C已提交的数据在事务执行p|Ӟ数据的状态都应该正确?/span>


     
通俗的理解,事务是一l原子操作单元,从数据库角度_是一l?/span>SQL指oQ要么全部执行成功,若因为某个原因其中一条指令执行有错误Q则撤销先前执行q的所有指令。更{的说就是:要么全部执行成功Q要么撤销不执行?/span>


既然事务的概念从数据库而来Q那Java事务是什么?之间有什么联p?  实际上,一?/span>Java应用pȝQ如果要操作数据库,则通过JDBC来实现的。增加、修攏V删除都是通过相应Ҏ间接来实现的Q事务的控制也相应{UdJavaE序代码中。因此,数据库操作的事务习惯上就UCؓJava事务?/span>


二、ؓ什么需要事?/span>

事务是ؓ解决数据安全操作提出的,事务控制实际上就是控制数据的安全讉K。具一个简单例子:比如银行转帐业务Q̎?/span>A要将自己账户上的1000 元{?/span>B账户下面Q?/span>A账户余额首先要减?/span>1000元,然后B账户要增?/span>1000元。假如在中间|络出现了问题,A账户减去1000元已l结束,B因ؓ|络中断而操作失败,那么整个业务p|Q必d出控Ӟ要求A账户转帐业务撤销。这才能保证业务的正性,完成q个操走需要事务,?/span>A账户资金减少?/span>B账户资金增加方到一个事务里面,要么全部执行成功Q要么操作全部撤销Q这样就保持了数据的安全性?/span>


三?/span>
Java事务的类?/span> 
    Java 
事务的类型有三种Q?/span>JDBC事务?/span>JTA(Java Transaction API)事务、容器事务?/span> 
1
?/span>JDBC事务 
JDBC 
事务是用 Connection 对象控制的?/span>JDBC Connection 接口( java.sql.Connection )提供了两U事务模式:自动提交和手工提交?/span> java.sql.Connection 提供了以下控制事务的ҎQ?/span>

public void setAutoCommit(boolean) 
public boolean getAutoCommit() 
public void commit() 
public void rollback() 
使用 JDBC 事务界定Ӟ您可以将多个 SQL 语句l合C个事务中?/span>JDBC 事务的一个缺Ҏ事务的范围局限于一个数据库q接。一?/span> JDBC 事务不能跨越多个数据库?/span> 
2
?/span>
JTA(Java Transaction API)事务 
    JTA 
是一U高层的Q与实现无关的,与协议无关的APIQ应用程序和应用服务器可以?/span>JTA来访问事务?/span> 
JTA
允许应用E序执行分布式事务处?/span>--在两个或多个|络计算源上讉Kq且更新数据Q这些数据可以分布在多个数据库上?/span>JDBC驱动E序?/span>JTA支持极大地增Z数据讉K能力?/span> 
如果计划?/span> JTA 界定事务Q那么就需要有一个实?/span> javax.sql.XADataSource ?/span> javax.sql.XAConnection ?/span> javax.sql.XAResource接口?/span> JDBC 驱动E序。一个实Cq些接口的驱动程序将可以参与 JTA 事务。一?/span> XADataSource 对象是一?/span>XAConnection 对象的工厂?/span> XAConnection s 是参?/span> JTA 事务?/span> JDBC q接?/span> 
您将需要用应用服务器的理工具讄 XADataSource 。从应用服务器和 JDBC 驱动E序的文档中可以了解到相关的指导?/span> 
J2EE 
应用E序?/span> JNDI 查询数据源。一旦应用程序找C数据源对象,它就调用 javax.sql.DataSource.getConnection() 以获得到数据库的q接?/span> 
     XA 
q接与非 XA q接不同。一定要C XA q接参与?/span> JTA 事务。这意味着 XA q接不支?/span> JDBC 的自动提交功能。同Ӟ应用E序一定不要对 XA q接调用 java.sql.Connection.commit() 或?/span> java.sql.Connection.rollback() 。相反,应用E序应该使用 UserTransaction.begin()?/span> UserTransaction.commit() ?/span> serTransaction.rollback() ?/span>

3、容器事?/span> 
     
容器事务主要?/span>J2EE应用服务器提供的Q容器事务大多是ZJTA完成Q这是一个基?/span>JNDI的,相当复杂?/span>API实现。相对编码实?/span>JTA 事务理Q我们可以通过EJB容器提供的容器事务管理机ӞCMTQ完成同一个功能,q项功能?/span>J2EE应用服务器提供。这使得我们可以单的指定哪个方法加入事务,一旦指定,容器负责事务管理Q务。这是我们土建的解决方式Q因为通过q种方式我们可以事务代码排除在逻辑~码之外Q同时将所有困难交l?/span> J2EE容器去解冟뀂?/span>EJB CMT的另外一个好处就是程序员无需兛_JTA API的编码,不过Q理Z我们必须使用EJB?/span> 
四、三U事务差?/span> 
1
?/span>JDBC事务控制的局限性在一个数据库q接内,但是其用简单?/span> 
2
?/span>JTA事务的功能强大,事务可以跨越多个数据库或多个DAOQ用也比较复杂?/span> 
3
、容器事务,主要指的?/span>J2EE应用服务器提供的事务理Q局限于EJB应用使用?/span> 


JTA

Java事务APIQJTAQJava Transaction APIQ和它的同胞Java事务服务(JTSQJava Transaction Service)QؓJ2EEq_提供了分布式事务服务。一个分布式事务Qdistributed transactionQ包括一个事务管理器Qtransaction managerQ和一个或多个资源理?resource manager)。一个资源管理器Qresource managerQ是Lcd的持久化数据存储。事务管理器Qtransaction managerQ承担着所有事务参与单元者的怺通讯的责仅R下图显CZ事务理器和资源理的间的关pR?/span>


JTA事务比JDBC事务更强大。一个JTA事务可以有多个参与者,而一个JDBC事务则被限定在一个单一的数据库q接?/span>下列M个Javaq_的组仉可以参与C个JTA事务中:

JDBCq接

  • JDO PersistenceManager 对象
  • JMS 队列
  • JMS 主题
  • 企业JavaBeansQEJBQ?/span>
  • 一个用J2EE Connector Architecture 规范~译的资源分配器?/span>


DAO

DAO是Data Access Object数据讉K接口Q数据访问:֐思义是与数据库打交道。夹在业务逻辑与数据库资源中间。对数据库进行CURDQ增删查Ҏ作)?/span>

 

  在核?/span>J2EE模式中是q样介绍DAO模式的:Z建立一个健壮的J2EE应用Q应该将所有对数据源的讉K操作抽象装在一个公共API中。用E序设计的语a来说Q就是徏立一个接口,接口中定义了此应用程序中会用到的所有事务方法。在q个应用E序中,当需要和数据源进行交互的时候则使用q个接口Qƈ且编写一个单独的cL实现q个接口在逻辑上对应这个特定的数据存储?/span>


JDBC

JDBCQJava Data Base Connectivity,java数据库连接)是一U用于执行SQL语句的Java APIQ可以ؓ多种关系数据库提供统一讉KQ它׃l用Java语言~写的类和接口组成。JDBC为工?数据库开发h员提供了一个标准的APIQ据此可以构建更高的工具和接口Q数据库开发h员能够用U? Java API ~写数据库应用程序,同时QJDBC也是个商标名?/span>

 

有了JDBCQ向各种关系数据发送SQL语句是一件很Ҏ的事。换a之,有了JDBC APIQ就不必问Sybase数据库专门写一个程序,问Oracle数据库又专门写一个程序,或ؓ讉KInformix数据库又~写另一个程序等{,E序员只需用JDBC API写一个程序就够了Q它可向相应数据库发送SQL调用。同ӞJava语言和JDBCl合h使程序员不必Z同的q_~写不同的应用程序,只须写一遍程序就可以让它在Q何^Cq行Q这也是Java语言“~写一ơ,处处q行”的优ѝ?/span>


单地_JDBC 可做三g事:与数据库建立q接、发? 操作数据库的语句q处理结果?/span>


JDO

JDO(Java Data Object )是一个JAVA用于存取某种数据仓库中的对象的标准化API。JDO提供了透明的对象存储,因此对开发h员来_存储数据对象完全不需要额外的代码Q如JDBC API的用)。这些繁琐的例行工作已经转移到JDO产品提供商n上,使开发h员解脱出来,从而集中时间和_֊在业务逻辑上。另外,JDO很灵z,因ؓ它可以在M数据底层上运行。JDBC只是面向关系数据库(RDBMSQJDO更通用Q提供到M数据底层的存储功能,比如关系数据库、文件、XML以及对象数据库(ODBMSQ等{,使得应用可移植性更强?/span>


JNDI

英文全称?Java Naming and Directory Interface

术语解释Q一l帮助做多个命名和目录服务接口的API?/span>

JNDI(Java Naming and Directory Interface)是SUN公司提供的一U标准的Java命名pȝ接口QJNDI提供l一的客LAPIQ通过不同的访问提供者接口JNDI SPI的实玎ͼq理者将JNDI API映射为特定的命名服务和目录系l,使得Java应用E序可以和这些命名服务和目录服务之间q行交互。集JNDI实现了高可靠性JNDI[8]Q通过服务器的集群Q保证了JNDI的负载^衡和错误恢复。在全局׃n的方式下Q集中的一个应用服务器保证本地JNDI树的独立性,q拥有全局的JNDI树。每个应用服务器在把部v的服务对象绑定到自己本地的JNDI树的同时Q还l定C个共享的全局JNDI树,实现全局JNDI和自wJNDI的联pR?/span>


 

JNDI(Java Naming and Directory Interface)是一个应用程序设计的APIQؓ开发h员提供了查找和访问各U?/span>

 

命名和目录服务的通用、统一的接口,cMJDBC都是构徏在抽象层上?/span>

 

JNDI可访问的现有的目录及服务有:DNS、XNam 、Novell目录服务、LDAP(Lightweight Directory Access Protocol d目录讉K协议)? CORBA对象服务、文件系l、Windows XP/2000/NT/Me/9x的注册表、RMI?div>DSML v1&v2、NIS?/span>

 


JNDI与JDBC

JNDI提供了一U统一的方式,可以用在|络上查扑֒讉K服务。通过指定一个资源名Uͼ该名U对应于数据库或命名服务中的一个记录,同时q回数据库连接徏立所必须的信息?/span>

JNDI主要有两部分l成Q应用程序编辑接口和服务供应商接口。应用程序编E接口提供了Java应用E序讉K各种命名和目录服务的功能Q服务供应商接口提供了Q意一U服务的供应商用的功能?/span>



2011-12-05 15:17 发表评论
]]>jquery-autocompletehttp://www.tkk7.com/ljc-java/articles/363160.htmlTue, 08 Nov 2011 03:41:00 GMThttp://www.tkk7.com/ljc-java/articles/363160.htmlhttp://www.tkk7.com/ljc-java/comments/363160.htmlhttp://www.tkk7.com/ljc-java/articles/363160.html#Feedback0http://www.tkk7.com/ljc-java/comments/commentRss/363160.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/363160.html

jquery-autocomplete学习

一、用前必?/p>

官方|站Q?a rel="nofollow">http://bassistance.de/jquery-plugins/jquery-plugin-autocomplete/

当前版本Q?.0.2

需要JQuery版本Q?.2.6

二、?/p>

<script src="./jquery-1.3.2.js" type="text/javascript"></script>

<script src="./jquery.autocomplete.js" type="text/javascript"></script>

<link rel="stylesheet" href="./jquery.autocomplete.css" />

autocomplete( url or data, options ) Returns: jQuery

让一个input或textarea有autocomplete功能

例子

Js代码

var data = "Core Selectors Attributes Traversing Manipulation CSS Events Effects Ajax Utilities".split(" ");  

$("#example").autocomplete(data);

以上的例子就是ؓid为exampledautocomplete

var emails = [

    { name: "Peter Pan", to: "

    { name: "Molly", to: "

    { name: "Forneria Marconi", to: "

    { name: "Master <em>Sync</em>", to: "

    { name: "Dr. <strong>Tech</strong> de Log", to: "

    { name: "Don Corleone", to: "

    { name: "Mc Chick", to: "

    { name: "Donnie Darko", to: "

    { name: "Quake The Net", to: "

    { name: "Dr. Write", to: "

];

//emails的数l格式如上,formatItem代表的是昄的格式,formatMatch表示匚w的内容,formatResult表示l果的内?/p>

$("#suggest13").autocomplete(emails, {

    minChars: 0,

    width: 310,

    matchContains: true,

    autoFill: false,

    formatItem: function(row, i, max) {

        return i + "/" + max + ": \"" + row.name + "\" [" + row.to + "]";

    },

    formatMatch: function(row, i, max) {

        return row.name + " " + row.to;

    },

    formatResult: function(row) {

        return row.to;

    }

});

三、参数说明:

* minChars (Number):

    在触发autoComplete前用戯需要输入的字符?Default: 1Q如果设?Q在输入框内双击或者删除输入框内内Ҏ昄列表

* width (Number):

    指定下拉框的宽度. Default: input元素的宽?/p>

* max (Number):

    autoComplete下拉昄目的个?Default: 10

* delay (Number):

    击键后激zautoComplete的gq时?单位毫秒).Default: q程?00 本地10

* autoFill (Boolean):

    要不要在用户选择时自动将用户当前鼠标所在的值填入到input? Default: false

* mustMatch (Booolean):

    如果讄为true,autoComplete只会允许匚w的结果出现在输入?所有当用户输入的是非法字符时将会得不到下拉?Default: false

* matchContains (Boolean):

    军_比较时是否要在字W串内部查看匚w,如ba是否与foo bar中的ba匚w.使用~存时比较重?不要和autofillL.Default: false

* selectFirst (Boolean):

    如果讄成true,在用户键入tab或return键时autoComplete下拉列表的第一个值将被自动选择,管它没被手工选中(用键盘或鼠标).当然如果用户选中某个目,那么q用户选中的? Default: true

* cacheLength (Number):

    ~存的长?卛_从数据库中取到的l果集要~存多少条记?设成1Z~存.Default: 10

* matchSubset (Boolean):

    autoComplete可不可以使用Ҏ务器查询的缓?如果~存对foo的查询结?那么如果用户输入foo׃需要再q行索了,直接使用~存.通常是打开q个选项以减L务器的负担以提高性能.只会在缓存长度大?时有?Default: true

* matchCase (Boolean):

    比较是否开启大写敏感开?使用~存时比较重?如果你理解上一个选项,q个也就不难理解,好比foot要不要到FOO的缓存中L.Default: false

* multiple (Boolean):

    是否允许输入多个值即多次使用autoComplete以输入多个? Default: false

* multipleSeparator (String):

    如果是多选时,用来分开各个选择的字W? Default: ","

* scroll (Boolean):

    当结果集大于默认高度时是否用卷轴显C?Default: true

* scrollHeight (Number):

    自动完成提示的卷轴高度用像素大小表示 Default: 180  

* formatItem (Function):

    为每个要昄的项目用高U标{?卛_l果中的每一行都会调用这个函?q回值将用LI元素包含昄在下拉列表中. Autocompleter会提供三个参?row, i, max): q回的结果数l? 当前处理的行?即第几个目,是从1开始的自然?, 当前l果数组元素的个数即目的个? Default: none, 表示不指定自定义的处理函?q样下拉列表中的每一行只包含一个?

* formatResult (Function):

    和formatItemcM,但可以将要输入到input文本框内的D行格式化.同样有三个参?和formatItem一?Default: none,表示要么是只有数?要么是用formatItem提供的?

* formatMatch (Function):

    Ҏ一行数据用此函数格式化需要查询的数据格式. q回值是l内部搜索算法用的. 参数值row

* extraParams (Object):

    为后?一般是服务端的脚本)提供更多的参?和通常的作法一h使用一个键值对对象.如果传过ȝ值是{ bar:4 },会被autocompleter解析成my_autocomplete_backend.php?q=foo&bar=4 (假设当前用户输入了foo). Default: {}

* result (handler) Returns: jQuery

    此事件会在用户选中某一后触发Q参CؓQ?/p>

    event: 事g对象. event.type为result.

    data: 选中的数据行.

    formatted:formatResult函数q回的?/p>

    例如Q?/p>

    $("#singleBirdRemote").result(function(event, data, formatted) {

//如选择后给其他控g赋|触发别的事g{等

});

四、注意问题:

1.|上有h说对中文的检索时处理有问题,l过试此版本没有问题^-^

2.在用远E地址Ӟ它默认传入的参数是:qQ输入|QlimitQ返回结果的最大|Q可以用extraParams传入其他的参?/p>

3.autocomplete在用ajax传递参数时Q默认用了get方式传递,也实在是没有扑ֈ可以通过参数提交post方式的办法?/p>

解决方式1Q在使用ajax的get方式传递中文时Q用new String(request.getParameter("q").getBytes("iso8859-1"),"utf-8")获得参数?/p>

解决方式2Q修改jquery.autocomplete.js代码Q把get方式修改为post方式Q然后参见之前ajax解决中文q的问题的

 

转蝲Q?a rel="nofollow">http://blog.sina.com.cn/s/blog_608475eb0100g6qc.html



2011-11-08 11:41 发表评论
]]>软g工程师不可不知的10个概?/title><link>http://www.tkk7.com/ljc-java/archive/2011/08/31/357649.html</link><dc:creator>罗</dc:creator><author>罗</author><pubDate>Wed, 31 Aug 2011 08:40:00 GMT</pubDate><guid>http://www.tkk7.com/ljc-java/archive/2011/08/31/357649.html</guid><wfw:comment>http://www.tkk7.com/ljc-java/comments/357649.html</wfw:comment><comments>http://www.tkk7.com/ljc-java/archive/2011/08/31/357649.html#Feedback</comments><slash:comments>0</slash:comments><wfw:commentRss>http://www.tkk7.com/ljc-java/comments/commentRss/357649.html</wfw:commentRss><trackback:ping>http://www.tkk7.com/ljc-java/services/trackbacks/357649.html</trackback:ping><description><![CDATA[<div><span style="color: #323e32; font-family: Verdana, 宋体, sans-serif; font-size: 12px; font-style: normal; font-variant: normal; font-weight: normal; letter-spacing: normal; line-height: 18px; orphans: 2; text-align: left; text-indent: 0px; text-transform: none; white-space: normal; widows: 2; word-spacing: 0px; -webkit-text-decorations-in-effect: none; -webkit-text-size-adjust: auto; -webkit-text-stroke-width: 0px; background-color: #dceccc; ">的Y件工E师善用设计模式Q勤于代码重构,~写单元试Qƈ对简单有宗教般的q求。除了这些,优秀的Y件工E师q要通晓10个概念,q?0个概念超了~程语言与设计模式,软g工程师应当从更广的范围内明白q些道理?p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  10. 关系数据?(Relational Databases)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  关系数据库因为在大规?Web 服务上缺乏可扩充性而颇受微词,然而,关系数据库仍然是q?0q来计算机技术中最伟大的成。关pL据库对处理订单,公司数据斚w有着的表现?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  关系数据库的核心是以记录表示数据Q记录存攑֜数据库表Q数据库使用查询语言(SQL)Ҏ据进行搜索与查询Q同Ӟ数据库对各个数据表进行关联?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  数据库的标准化技?normalization)讲的是用正的方式Ҏ据进行分存以降低冗余Qƈ加快存取速度?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  9. 安全 (Security)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  随着黑客的崛起与数据敏感性的上升Q安全变得非帔R要。安全是个广义的概念Q涉及验证,授权与信息传输?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  验证是对用户的n份进行检查,如要求用戯入密码。验证通常需要结?SSL (secure socket layer)q行;授权在公怸务系l中非常重要Q尤其是一些工作流pȝ。最q开发的 OAuth 协议可以帮助 Web 服务相应信息向相应用户开放。Flickr 便用这U方式管理私人照片和数据的访问权限?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  另外一个安全领域是|络NQ这关系到操作系l,配置与监控。不仅网l危险重重,M软g都是。Firefox 被称为最安全的浏览器Q仍焉要频频发布安全补丁。要Z的系l编写安全代码就需要明白各U潜在的问题?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  8. 云计?(Cloud Computing)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  RWW 最q的关于云计的文章 Reaching For The Sky Through Compute Clouds 讲到了云计算如何改变大规?Web 应用的发布。大规模的ƈ行,低成本,与快速投入市场?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  q行法发明以来Q首先迎来的是网D,|格计算是借助I闲的桌面计机资源q行q行计算。最著名的例子是 Berkley 大学?nbsp;SETI@home 计划Q该计划使用I闲?CPU 资源分析太空数据。金融机构也大规模实施网D进行风险分析。空闲的资源Q加?J2EE q_的崛Pq来了云计算的概念:应用服务虚拟化。就是应用按需q行Qƈ可以随着旉和用戯模而实时改变?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  云计最生动的例子是 Amazon ?Web 服务Q一l可以通过 API q行调用的应用,如云服务(EC2)Q一个用来存储大型媒体文件的数据?S3)Q烦引服?SimpleDB)Q序列服?SQS)?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  7. q发 (Concurrency)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  q发是Y件工E师最Ҏ犯错的地方,q可以理解,因ؓ我们一直遵从线形思维Q然而ƈ发在Cpȝ中非帔R要?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  q发是程序中的ƈ行处理,多数C~程语言包含内置的ƈ发能力,?JavaQ指的是U程。关于ƈ发,最l典的例子是“生/消费”模式Q生产方生数据和Q务,q放入工作线E消Ҏ执行。ƈ发的复杂性在于,U程需要经常访问共同数据,每个U程都有自己的执行顺序,但需要访问共同数据。Doug Lea 曑ֆq一个最复杂的ƈ发类Q现在是 core Java 的一部分?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  6. ~存(Caching)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  ~存对现?Web E序不可或缺Q缓存是从数据库取回Qƈ存放在内存中的数据。因为数据库直接存取的代价非帔RQ将数据从数据库取回q放在缓存中讉K变得十分必要。比如,你有一个网站,要显CZ周的畅销书,你可以从数据畅销书榜一ơ性取回放在缓存中Q而不必在每次讉K旉L据库L据?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  ~存需要代P只有最常用的内Ҏ可以攑օ~存。很多现代程序,包括 FacebookQ依靠一U叫?Memcached 的分布式~存pȝQ该pȝ?Brad Firzpatrick 在工作于 LiveJournal 目时开发的QMemcached 使用|络中空闲的内存资源建立~存机制QMemcached cd在很多流行编E语aQ包?Java ?PHP 中都有?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  5. 散列?Hashing)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  Hashing 的目的是加速访问速度。如果数据是序列存储的,从中查询一个项的时间取决于数据列的大小。而散列法Ҏ一个项计算一个数字作为烦引,在一个好?Hashing 法下,数据查找的速度是一L?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  除了存储数据Q散列法对分布式pȝ也很重要。统一散列?uniform hash )用来在云数据库环境下Q在不同计算Z间分存数据。Google 的烦引服务就是这U方法的体现Q每一?URL 都被散列分布到特定计机?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  散列函数非常复杂Q但Ccd中都有现成的c,重要的是Q如何对散列法进行细调以获得最好的性能?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  4. 法的复杂?(Algorithmic Complexity)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  关于法的复杂性,软g工程师需要理解这样几件事。第一Q大O标记?big O notation);W二Q你永远都不应该使用嵌套式@?循环里面套@?Q你应该使用 Hash 表,数组或单一循环;W三Q如今优Ucd比比皆是Q我们不必过分纠~于q些库的效能的差别,我们以后q有Zq行l调;最后,</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">不要忽视法的优雅及性能Q编写紧凑的Q可ȝ代码可以让你的算法更单,更干净?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  3. 分层 (Layering)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  用分层来讨论软g架构是最Ҏ的。John Lakos 曑և版过一本关于大?C++ pȝ的书。Lakos 认ؓ软g包含了层Q书中介l了层的概念Q方法是Q对每个软glgQ数一下它所依赖的组件数目就可以知道它的复杂E度?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  Lakos 认ؓQ一个好的Y件拥有金字塔l构Q就是说QY件组件拥有层层积累的复杂度,但每个组件本w必ȝ单,一个优U的Y件包含很多小的,可重复用的模块Q每个模块有自己的职责。一个好的系l中Q组件之间的依赖性不可交叉,整个pȝ是各U各Llg堆积hQŞ成一个金字塔?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  Lakos 在Y件工E的很多斚w都是先驱Q最著名的是 Refactoring (代码重构)。代码重构指的是Q在~程q程中需要不断地对代码进行改造以保证其结构的健壮与灵zR?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  2. 惯例与模?(Conventions and Templates)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  命名惯例和基模板在编E模式中常被忽视Q然而它可能是最强大的方法。命名惯例软g自动化成为可能,如,Java Beans 框架?getter ?setter Ҏ中,使用单的命名惯例。del.icio.us |站?URL 命名也用统一的格式,如http://del.icio.us/tag/software 会将用户带到所有标{ؓ software 的页?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  很多C会|络均用简单命名,如,你的名字?johnsmith Q那你的头像可能命名?johnsmith.jpgQ而你?rss 聚合文g的命名很可能?johnsmith.xml ?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  命名惯例q用于单元测试,如,JUnit 单元试工具会L认所有以 test 开头的cR?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  我们q里说的模板(templates )指的q不?C++ ?Java 语言中的 constructsQ我们说的是一些包含变量的模板文gQ用户可以替换变量ƈ输出最l结果?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  Cold Fusion 是最先用模板的E序之一Q后来,Java 使用 JSP 实现模板功能。Apache q来?Java 开发了非常好用的通用模板, Velocity。PHP 本n是Z模板的,因ؓ它支?eval 函数?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  1. 界面(Interfaces)</p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  软g工程中最重要的概忉|界面。Q何Y仉是一个真实系l的模型?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; "><br /></p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">如何使用单的用户界面q行模型化至关重要。很多Y件系l走q样的极端,~Z抽象的冗长代码,或者过分设计而导致无谓的复杂?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  在众多Y件工E书c中QRobert Martin 写的《敏LE》值得一诅R?/p><p style="margin-top: 0px; margin-right: 0px; margin-bottom: 5px; margin-left: 0px; padding-top: 0px; padding-right: 0px; padding-bottom: 0px; padding-left: 0px; border-top-width: 0px; border-right-width: 0px; border-bottom-width: 0px; border-left-width: 0px; border-style: initial; border-color: initial; list-style-type: none; list-style-position: initial; list-style-image: initial; word-wrap: normal; word-break: normal; line-height: 18px; ">  关于模型化,以下Ҏ对你会有帮助。首先,L那些只有在将来才可能用得着的方法,代码精l越好。第二,不要总认Z前的东西是对的,要善于改变。第三,要有耐心qn受过E?/p></span></div><img src ="http://www.tkk7.com/ljc-java/aggbug/357649.html" width = "1" height = "1" /><br><br><div align=right><a style="text-decoration:none;" href="http://www.tkk7.com/ljc-java/" target="_blank">罗</a> 2011-08-31 16:40 <a href="http://www.tkk7.com/ljc-java/archive/2011/08/31/357649.html#Feedback" target="_blank" style="text-decoration:none;">发表评论</a></div>]]></description></item><item><title>介绍几种工作的模式(转蝲)http://www.tkk7.com/ljc-java/articles/356845.htmlFri, 19 Aug 2011 03:47:00 GMThttp://www.tkk7.com/ljc-java/articles/356845.htmlhttp://www.tkk7.com/ljc-java/comments/356845.htmlhttp://www.tkk7.com/ljc-java/articles/356845.html#Feedback1http://www.tkk7.com/ljc-java/comments/commentRss/356845.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/356845.html

原地址Q?a style="font-size: 12px; color: #6b6759; text-decoration: none; line-height: 20px; font-family: Georgia; ">http://gocom.primeton.com/modules/newbb/item40732_40732.htm?PHPSESSID=b3d40a5147b401adc250801cdef036cf&referer=csdn&utm_campaign=gocom&utm_source=csdn&utm_medium=lks

摘要Q介l几U工作流的模?/span>

作者:刘航

工作的基本模式

1、顺序(SequenceQ模?/span>

描述Q?/span>只有当前一个活动结束后Q后一个活动才会被触发Q即按照预定的Q务列表,有序的执行?/span>


            
 
举例Q?/span>对于一?/span>BUG的处理就满该模式?/span>

     
 
2、ƈ行(Parallel SplitQ模?/span>

描述Q?/span>一个活动的l束能够触发若干个活动的开始,q些被触发的zd能以q行的方式同时或按Q意顺序进行?/span>



                
 
举例Q?/span>当提交一?/span>BUG时会分别?/span>BUG信息表和BUG日志表中d相应记录

        

3、同步(SynchronizationQ模?/span>

描述Q?/span>如果不考虑时Q一般流E会讑֮d执行期限Q和异常{情况,程必须在聚合点{待所有的分支都执行完Q到?/span>And 汇聚点)才能ȀzdlQ务,才能正确的往下运行?/span>



举例Q?/span>支持人员分派的问题由开发h员修改,然后不仅要经q测试h员验证通过q要再次l支持h员验证通过才能Close?/span>BUG?/span>



独占式选择Q?/span>Exclusive ChoiceQ模?/span>

  该模式分为显式独占模型(explic Exclusive Choice Q和隐式独占选择模式Q?/span>implicit Exclusive ChoiceQ?/span>

  1Q显式独占选模型(explic Exclusive Choice Q?/span>

描述Q?/span>当一个活动处理完后,其后有若q个分支程可供选择Q但Ҏ工作控制数据(workflow control dataQ只允许选择其中某一个分支运行?/span>



  如上图所C,虽然在Q?/span>Task A 后可以三个不同的zd程可被选择Q但是仅Task D 满条gQ造成后箋的流E中Q走?/span>A——D 分支Q而另外的分支被抛弃?/span>

举例Q?/span>?/span>PSO人员提交一个问题时Q该问题的类型需要被定。如果是产品的错误而引L那么问题cd即ؓBUGQ如果是׃客户的操作失误而引L那么问题cd即ؓISSUEQ如是对产品的有价值的Q那么问题的cd即ؓADVICEQ由上可知,当确定问题类型时三种只能选其一?/span>

     
      
 
  2Q隐式独占选模型(implicit Exclusive Choice Q?/span>

描述Q?/span>同ؓXOR 模型Q隐式和昑ּ的区别不是太大。唯一的不同点是Q隐式独占选模型在可供选择的分支中存在存在若干个分支满xӞ但最l,依然仅有一个分支运行?/span>



  如上图所C,存在分支A—C 和分?/span>A—D 都满xӞ但最l也依然只能有一个分支被ȀzR至于哪一个分支被Ȁz,q可能是Zؓ的操作,也可能是某种随即的自动选择。不论哪U方式,人须保证一个分支被ȀzdQ其他分支被抛弃?/span>

举例Q?/span>PSO的h员在提交问题的时候,他会Ҏ问题的来源将它提交给负责相应区域的支持h员。但是,具体提交l负责该区域的哪一位支持者,qPSO的h员自己决定或pȝ随机产生。不如何选择都必L一位支持h员要接收该问题?/span>

     
 

  不管是显式独占模型(explic Exclusive Choice Q还是隐式独占选择模式Q?/span>implicit Exclusive ChoiceQ他们的执行程都是一L?/span>

  5、简单聚合(Simple MergeQ模?/span>

描述Q?/span>前面的若q个分支Q只要有一个活动被执行Q假定不存在两个分支同时被执行)Q后面的zd׃被触发。当Ӟ一旦某一个分支被通过。则余下的分支则被终止,或者运行到聚合点就l束?/span>


               
 
举例Q?/span>如果产品中存在某?/span>BUG那么可能会被不同地方的用户发玎ͼ但只要有一个地方的PSO人员提出q个问题BUG׃得到处理。当其它地方?/span>PSO再次提出该问题的时候就不会重复处理?/span>



2011-08-19 11:47 发表评论
]]>
lGrails开发者的10个徏?转蝲)http://www.tkk7.com/ljc-java/archive/2011/08/19/356844.htmlFri, 19 Aug 2011 03:43:00 GMThttp://www.tkk7.com/ljc-java/archive/2011/08/19/356844.htmlhttp://www.tkk7.com/ljc-java/comments/356844.htmlhttp://www.tkk7.com/ljc-java/archive/2011/08/19/356844.html#Feedback0http://www.tkk7.com/ljc-java/comments/commentRss/356844.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/356844.html

from InfoQ <http://www.infoq.com/cn/news/2009/02/grails-10-tips>

如果要列举近些年来Java领域中最令hȀ动的事gQGrails的诞生绝对应该榜上有名。在打开Grails官方|站<http://www.grails.org/>Ӟ 
你会在浏览器的标题栏上看到这L内容Q?#8220;Grails - L此l束”。虽然这句话不见得适用于所有场合,但对于不从事Java 
Web开发的人来_赞同者恐怕不在少数。由于具备Rails风格的框架、兼容绝大多数Java语法的Groovy动态语a、以业界口碑良好的框架ؓ?nbsp;
、对企业现有Java开发资产的保护、Plugin架构{特点,再加上SpringC֌的强力介入,Grails行情看涨应该是意料之中的?/p>

然而Grails却没有看上去那么单,在其包装的糖衣之下,有着许多作ؓJava Web开发者不得不了解的知识。最q,Peter 
Delahunty<http://blog.peterdelahunty.com/
发表了题为Grails开发者需要知道的10个技?lt;http://blog.peterdelahunty.com/2009/02/10-ten-tips-for-grails-develop...
的博文。不要被标题所qh了,q里所说的“技?#8221;可不是那些语a层面?#8220;技?#8221;Q把它们UCؓ“”恐怕更合适一些?/p>

技?Q把Grails的书c买来读诅R对此,Peter Delahunty推荐了已出版的《Definitive Guide to Grails 2nd 
edition》和《Groovy and Grails Recipes》,以及卛_出版的《Grails in Action》?/p>

技?Q学习GroovyQƈ按照Groovyq行思考。Peter Delahunty通过一个例子说明了Java思维和Groovy思维的不同?/p>

q儿有个好例子:

传播操作W(spread operatorQ:*

在Java中,要想遍历一lhq收集h名。我可能得这样写Q?/p>

List names = new ArrayList(); 
for (Iterator iterator = people.iterator(); iterator.hasNext();) { 
Person person = (Person) iterator.next(); 
names.add(person.getName());

}
System.out.println(names); 

用GroovyQ我会这么写Q?/p>

def names = people*.name 
println names

呵呵Q简单吧。我q可以这样写Q?/p>

def names = people.collect {it.name} 
println names

在这个徏议中Q他列D了一些资源:

- Groovy官方|站 <http://groovy.codehaus.org/
- PLEAC <http://pleac.sourceforge.net/pleac_groovy/index.html>

以及一些书c:

- Programming Groovy 
- Groovy Recipies 
- Groovy in action

技?Q了解Grails的各个插件。Peter 
Delahuntyl出的理由:Grails本n是个插gpȝQ而且现在已经有大量的插g可供下蝲。在自行实现之前Q不妨看看其中是否有U手的?/p>

技?Q学习Hibernate和Spring。这一点不隄解,既然Grails是徏立在q些工具之上的,了解q些工具本n的用,对于熟练使用Grails 自然大有脄?/p>

技?Q单元试、集成测试和一般测试的自动化。Peter Delahunty在这里推荐了两个Grails的插ӞTesting 
Plugin<http://www.grails.org/Testing+Plugin
和Functional testing plugin 
<http://www.grails.org/Grails+Functional+Testing>。前者将成ؓGrails 
1.1的内|插件?/p>

技?Q用好的IDE。Peter Delahunty表示Q他自己使用的是IntellijQ但对于Netbeans也寄予厚望?/p>

技?Q学习ƈ使用HTML W3C标准?#8220;遵@标准消除你90%的问?#8221;QPeter Delahunty如是说?/p>

技?Q看上去不错一定不错。这其实说的?#8220;面子工程”Q通过提高应用的外观设计来提高应用的竞争力。Peter Delahuntyl出?个资源:

- 99designs.com 
- 圆角矩Ş产生?<http://www.roundedcornr.com/>

技?Q用Firefox上的Firebug。对于浏览器端的调试工作QFirebugl对是一个必备工兗?/p>

技?0Q跟上Groovy和GrailsC֌的步伐。在q最后一个徏议中QPeter 
Delahuntyl出了获取Groovy和Grails信息的主要资源链接:

- Grails官方|站 <http://www.grails.org/
- Groovy和Grails相关的博?<http://groovyblogs.org/entries/recent
- Grails创始人Graeme Rocher的Twitter <http://twitter.com/graemerocher
- Groovy目领导人Guillaume Laforge的Twitter <http://twitter.com/glaforge
- Groovyblogs.org的创始hGlen Smith <http://twitter.com/glen_a_smith>

请务必阅读Peter Delahunty的原?lt;http://blog.peterdelahunty.com/2009/02/10-ten-tips-for-grails-develop...>。对于Grails的新老用者,你都可以从Peter 
Delahunty的徏议中有所收获。关于InfoQ中文站Groovy和Grails的其它内容,误问这?lt;http://www.infoq.com/cn/groovy
和这?<http://www.infoq.com/cn/grails>?/p>

2011-08-19 11:43 发表评论
]]>
实战 Groovy: for each 剖析(转蝲)http://www.tkk7.com/ljc-java/archive/2011/08/04/355737.htmlThu, 04 Aug 2011 03:50:00 GMThttp://www.tkk7.com/ljc-java/archive/2011/08/04/355737.htmlhttp://www.tkk7.com/ljc-java/comments/355737.htmlhttp://www.tkk7.com/ljc-java/archive/2011/08/04/355737.html#Feedback0http://www.tkk7.com/ljc-java/comments/commentRss/355737.htmlhttp://www.tkk7.com/ljc-java/services/trackbacks/355737.html

q代是编E的基础。您l常会遇到需要进行逐项遍历的内容,比如 List?code>File ?JDBC ResultSet。Java 语言几乎L提供了某U方法帮助您逐项遍历所需的内容,但o人沮丧的是,它ƈ没有l出一U标准方法。Groovy 的P代方法非常实用,在这一点上QGroovy ~程?Java ~程截然不同。通过一些代码示例,本文介l?Groovy 的万能的 each() ҎQ从而将 Java 语言的那些P代怪癖抛在脑后?

Java q代{略

假设您有一?Java ~程语言?java.util.List。清?1 展示了在 Java 语言中如何用编E实现P代:


清单 1. Java 列表q代
import java.util.*;  
public class ListTest{
 public static void main(String[] args){
 List<String> list = new ArrayList<String>();
 list.add("Java");
 list.add("Groovy");
 list.add("JavaScript");
 for(Iterator<String> i = list.iterator(); i.hasNext();){
 String language = i.next();
 System.out.println("I know " + language);
 }
 }
 }

׃提供了大部分集合c都可以׃n?java.lang.Iterable 接口Q您可以使用相同的方法遍?java.util.Set ?java.util.Queue?

关于本系?/h2>

Groovy 是一ƾ运行在 Java q_之上的现代编E语a。它能够与现?Java 代码无缝集成Q同时引入了闭包和元~程{出色的新特性。简而言之,Groovy cM?21 世纪?Java 语言?

如果要将新工具集成到开发工L中,最关键的是理解什么时候需要用它以及什么时候不适合使用它。Groovy 可以变得非常强大Q但前提是它被适当地应用到合适的场景中。因此, 实战 Groovy pd旨在展示 Groovy 的实际用,以及何时和如何成功应用它?

现在Q假设该语言存储?java.util.Map 中。在~译Ӟ试?Map 获取 Iterator 会导致失?— Map q没有实?Iterable 接口。幸q的是,可以调用 map.keySet() q回一?SetQ然后就可以l箋处理。这些小差异可能会媄响您的速度Q但不会妨碍您的前进。需要注意的是,List?code>Set ?Queue 实现?IterableQ但?Map 没有 — 即它们位于相同?java.util 包中?

现在假设该语a存在?String 数组中。数l是一U数据结构,而不是类。不能对 String 数组调用 .iterator()Q因此必M用稍微不同的q代{略。您再一ơ受到阻,但可以用如清单 2 所C的Ҏ解决问题Q?


清单 2. Java 数组q代
public class ArrayTest{
 public static void main(String[] args){
 String[] list = {"Java", "Groovy", "JavaScript"};
 for(int i = 0; i < list.length; i++){
 String language = list[i];
 System.out.println("I know " + language);
 }
 }
 }

但是{一?— 使用 Java 5 引入?for-each 语法怎么P它可以处理Q何实?Iterable 的类和数l,如清?3 所C:


清单 3. Java 语言?for-each q代
import java.util.*;
 public class MixedTest{
 public static void main(String[] args){
 List<String> list = new ArrayList<String>();
 list.add("Java");
 list.add("Groovy");
 list.add("JavaScript");
 for(String language: list){
 System.out.println("I know " + language);
 }
String[] list2 = {"Java", "Groovy", "JavaScript"};
 for(String language: list2){
 System.out.println("I know " + language);
 }
 }
 }

因此Q您可以使用相同的方法遍历数l和集合Q?code>Map 除外Q。但是如果语a存储?java.io.FileQ那该怎么办?如果存储?JDBC ResultSetQ或者存储在 XML 文档?code>java.util.StringTokenizer 中呢Q面Ҏ一U情况,必须使用一U稍有不同的q代{略。这样做q不是有什么特D目?— 而是因ؓ不同?API 是由不同的开发h员在不同的时期开发的 — 但事实是Q您必须了解 6 ?Java q代{略Q特别是使用q些{略的特D情c?

Eric S. Raymond 在他?The Art of Unix Programming 一书中解释? “最意外原?#8221;。他写道Q?#8220;要设计可用的接口Q最好不要设计全新的接口模型。新鲜的东西L难以入门Q会为用户带来学习的负担Q因此应当尽量减新?宏V?#8221;Groovy 对P代的态度正是采纳?Raymond 的观炏V在 Groovy 中遍历几乎Q何结构时Q您只需要?each() q一U方法?


Groovy 中的列表q代

首先Q我?清单 3 中的 List 重构?Groovy。在q里Q只需要直接对列表调用 each() Ҏq传递一个闭包,而不是将 List 转换?for 循环Q顺便提一句,q样做ƈ不是特别h面向对象的特征,不是吗)?

创徏一个名?listTest.groovy 的文件ƈd清单 4 中的代码Q?/p>
清单 4. Groovy 列表q代
def list = ["Java", "Groovy", "JavaScript"] list.each{language->   println language } 

清单 4 中的W一行是 Groovy 用于构徏 java.util.ArrayList 的便捯法。可以将 println list.class d到此脚本来验证这一炏V接下来Q只需对列表调?each()Qƈ在闭包体内输?language 变量。在闭包的开始处使用 language-> 语句命名 language 变量。如果没有提供变量名QGroovy 提供了一个默认名U?it。在命o行提C符中输?groovy listTest q行 listTest.groovy?/p>

清单 5 是经q简化的 清单 4 代码版本Q?/p>
清单 5. 使用 Groovy ?it 变量的P?/strong>
 // shorter, using the default it variable 
def list = ["Java", "Groovy", "JavaScript"]
 list.each{ println it }
 // shorter still, using an anonymous
list ["Java", "Groovy", "JavaScript"].each{ println it }

Groovy 允许您对数组?List 交替使用 each() Ҏ。ؓ了将 ArrayList 改ؓ String 数组Q必d as String[] d到行末,如清?6 所C:


清单 6. Groovy 数组q代
def list = ["Java", "Groovy", "JavaScript"] as String[] list.each{println it} 

?Groovy 中普遍?each() ҎQƈ?getter 语法非常便捷Q?code>getClass() ?class 是相同的调用Q,q您能够编写既z又富有表达性的代码。例如,假设您希望利用反显C给定类的所有公共方法。清?7 展示了这个例子:


清单 7. Groovy 反射
def s = "Hello World"
 println s
println s.class
 s.class.methods.each{println it}
 //output:
$ groovy reflectionTest.groovy
 Hello World
 class java.lang.String
 public int java.lang.String.hashCode()
 public volatile int java.lang.String.compareTo(java.lang.Object)
 public int java.lang.String.compareTo(java.lang.String)
 public boolean java.lang.String.equals(java.lang.Object) ...

脚本的最后一行调?getClass() Ҏ?code>java.lang.Class 提供了一?getMethods() ҎQ后者返回一个数l。通过这些操作串qv来ƈ?Method 的结果数l调?each()Q您只用了一行代码就完成了大量工作?

但是Q与 Java for-each 语句不同的是Q万能的 each() Ҏq不仅限?List 和数l。在 Java 语言中,故事到此l束。然而,?Groovy 中,故事才刚刚开始?

Map q代

从前文可以看刎ͼ?Java 语言中,无法直接q代 Map。在 Groovy 中,q完全不是问题,如清?8 所C:


清单 8. Groovy map q代
def map = ["Java":"server", "Groovy":"server", "JavaScript":"web"] map.each{ println it } 

要处理名U?值对Q可以用隐式的 getKey() ?getValue() ҎQ或在包的开头部分显式地命名变量Q如清单 9 所C:


清单 9. ?map 获得键和?/strong>
def map = ["Java":"server", "Groovy":"server", "JavaScript":"web"]
 map.each{
 println it.key
 println it.value
 }
map.each{k,v->
 println k
 println v
 }

可以看到QP?Map 和P代其它Q何集合一栯然?

在l研I下一个P代例子前Q应当了?Groovy 中有?Map 的另一个语法。与?Java 语言中调?map.get("Java") 不一P可以化对 map.Java 的调用,如清?10 所C:


清单 10. 获得 map ?/strong>
def map = ["Java":"server", "Groovy":"server", "JavaScript":"web"]
 //identical results
 println map.get("Java")
 println map.Java

不可否认QGroovy 针对 Map 的这U便捯法非帔RQ但q也是在?Map 使用反射时引起一些常见问题的原因。对 list.class 的调用将生成 java.util.ArrayListQ而调?map.class q回 null。这是因?map 元素的便h法覆盖了实际?getter 调用?code>Map 中的元素都不h class 键,因此调用实际会返?nullQ如清单 11 的示例所C:


清单 11. Groovy map ?null
def list = ["Java", "Groovy", "JavaScript"]
 println list.class
 // java.util.ArrayList
 def map = ["Java":"server", "Groovy":"server", "JavaScript":"web"]
 println map.class
 // null
 map.class = "I am a map element"
 println map.class
 // I am a map element
 println map.getClass()
 // class
 java.util.LinkedHashMap

q是 Groovy 比较|见的打?“最意外原?#8221; 的情况,但是׃?map 获取元素要比使用反射更加常见Q因此我可以接受q一例外?/p>


String q代

现在您已l熟?each() Ҏ了,它可以出现在所有相关的位置。假设您希望q代一?StringQƈ且是逐一q代字符Q那么马上可以?each() Ҏ。如清单 12 所C:


清单 12. String q代
def name = "Jane Smith" name.each{letter->
 println letter
 }

q提供了所有的可能性,比如使用下划U替代所有空|如清?13 所C:


清单 13. 使用下划U替代空?/strong>

def name = "Jane Smith"
 println "replace spaces"
name.each{
 if(it == " "){
 print "_"
 }else{
 print it
 }
 }
 // output Jane_Smith

当然Q在替换一个单个字母时QGroovy 提供了一个更加简z的替换Ҏ。您可以清?13 中的所有代码合qؓ一行代码:"Jane Smith".replace(" ", "_")。但是对于更复杂?String 操作Q?code>each() Ҏ是最佳选择?


Range q代

Groovy 提供了原生的 Range cdQ可以直接P代。用两个点分隔的所有内容(比如 1..10Q都是一?Range。清?14 展示了这个例子:


清单 14. Range q代
def range = 5..10 range.each{
 println it
 }
 //output: 5 6 7 8 9 10

Range 不局限于单的 Integer。考虑清单 15 在的代码Q其中P?Date ?RangeQ?


清单 15. Date q代
def today = new Date()
 def nextWeek = today + 7
 (today..nextWeek).each{
 println it
 }
//output: Thu Mar 12 04:49:35 MDT 2009
 Fri Mar 13 04:49:35 MDT 2009
Sat Mar 14 04:49:35 MDT 2009
Sun Mar 15 04:49:35 MDT 2009
Mon Mar 16 04:49:35 MDT 2009
Tue Mar 17 04:49:35 MDT 2009
Wed Mar 18 04:49:35 MDT 2009
Thu Mar 19 04:49:35 MDT 2009

可以看到Q?code>each() 准确地出现在您所期望的位|。Java 语言~Z原生?Range cdQ但是提供了一个类似地概念Q采?enum 的Ş式。毫不奇怪,在这?each() 仍然z־上用场?/p>


Enumeration cd

Java enum 是按照特定顺序保存的随意的值集合。清?16 展示?each() Ҏ如何自然地配?enumQ就好象它在处理 Range 操作W一P


清单 16. enum q代
enum DAY{
 MONDAY, TUESDAY, WEDNESDAY, THURSDAY,
 FRIDAY, SATURDAY, SUNDAY
 }
 DAY.each{
 println it
 }
 (DAY.MONDAY..DAY.FRIDAY).each{
 println it
 }

?Groovy 中,有些情况下,each() q个名称q未能表辑֮的强大功能。在下面的例子中Q将看到使用特定于所用上下文的方法对 each() Ҏq行修饰。Groovy eachRow() Ҏ是一个很好的例子?


SQL q代

在处理关pL据库表时Q经怼?“我需要针对表中的每一行执行操?#8221;。比较一下前面的例子。您很可能会?“我需要对列表中的每一U语a执行一些操?#8221;。根据这个道理,groovy.sql.Sql 对象提供了一?eachRow() ҎQ如清单 17 所C:


清单 17. ResultSet q代
import groovy.sql.*
 def sql = Sql.newInstance(
 "jdbc:derby://localhost:1527/MyDbTest;create=true",
 "username",
 "password",
 "org.apache.derby.jdbc.ClientDriver")
 println("grab a specific field")
 sql.eachRow("select name from languages"){ row ->
 println row.name
 }
 println("grab all fields")
 sql.eachRow("select * from languages"){ row ->
 println("Name: ${row.name}")
 println("Version: ${row.version}")
 println("URL: ${row.url}\n")
 }

该脚本的W一行代码实例化了一个新?Sql 对象Q设|?JDBC q接字符丌Ӏ用户名、密码和 JDBC 驱动器类。这Ӟ可以调用 eachRow() ҎQ传?SQL select 语句作ؓ一个方法参数。在闭包内部Q可以引用列名(name?code>version?code>urlQ,好像实际存?getName()?code>getVersion() ?getUrl() Ҏ一栗?

q显然要?Java 语言中的{效Ҏ更加清晰。在 Java 中,必须创徏单独?DriverManager?code>Connection?code>Statement ?JDBCResultSetQ然后必d嵌套?try/catch/finally 块中它们全部清除?

对于 Sql 对象Q您会认?each() ?eachRow() 都是一个合理的Ҏ名。但是在接下来的CZ中,我想您会认ؓ each() q个名称q不能充分表辑֮的功能?


文gq代

我从未想q用原始的 Java 代码逐行遍历 java.io.File。当我完成了所有的嵌套?BufferedReader ?FileReader 后(更别提每个流E末所有异常处理)Q我已经忘记最初的目的是什么?

清单 18 展示了?Java 语言完成的整个过E:


清单 18. Java 文gq代
import java.io.BufferedReader;
 import java.io.FileNotFoundException;
 import java.io.FileReader; import java.io.IOException;
 public class WalkFile {
 public static void main(String[] args) {
 BufferedReader br = null;
 try {
 br = new BufferedReader(new FileReader("languages.txt"));
 String line = null;
 while((line = br.readLine()) != null) {
 System.out.println("I know " + line);
 }
 }
 catch(FileNotFoundException e) {
 e.printStackTrace();
 }
 catch(IOException e) {
 e.printStackTrace();
 }
 finally {
 if(br != null) {
 try {
 br.close();
 }
catch(IOException e) {
 e.printStackTrace();
 }
 }
 }
 }
 }

清单 19 展示?Groovy 中的{效q程Q?


清单 19. Groovy 文gq代
def f = new File("languages.txt") f.eachLine{language->
 println "I know ${language}"
}

q正?Groovy 的简z性真正擅长的斚w。现在,我希望您了解Z么我?Groovy UCؓ “Java E序员的 DSL”?

注意Q我?Groovy ?Java 语言中同时处理同一?java.io.File cR如果该文g不存在,那么 Groovy 代码抛出和 Java 代码相同?FileNotFoundException 异常。区别在于,Groovy 没有已检的异常。在 try/catch/finally 块中装 eachLine() l构是我自己的爱?— 而不是一语a需求。对于一个简单的命o行脚本中Q我ƣ赏 清单 19 中的代码的简z性。如果我在运行应用服务的同时执行相同的P代,我不能对q些异常坐视不管。我在?Java 版本相同?try/catch 块中装 eachLine() 块?

File cd each() Ҏq行了一些修攏V其中之一是 splitEachLine(String separator, Closure closure)。这意味着您不仅可以逐行遍历文gQ同时还可以它分ؓ不同的标记。清?20 展示了一个例子:


清单 20. 分解文g的每一?
// languages.txt
 // notice the space between the language and the version Java 1.5 Groovy 1.6 JavaScript 1.x
 // splitTest.groovy
def f = new File("languages.txt")
 f.splitEachLine(" "){words->
 words.each{ println it
 }
 }
// output Java 1.5 Groovy 1.6 JavaScript 1.x

如果处理的是二进制文ӞGroovy q提供了一?eachByte() Ҏ?

当然QJava 语言中的 File q不L一个文?— 有时是一个目录。Groovy q提供了一?each() 修改以处理子目录?


目录q代

使用 Groovy 代替 shell 脚本Q或批处理脚本)非常ҎQ因为您能够方便地访问文件系l。要获得当前目录的目录列表,参见清单 21Q?/p>
清单 21. 目录q代
def dir = new File(".") dir.eachFile{file->
 println file
 }

eachFile() Ҏ同时q回了文件和子目录。?Java 语言?isFile() ?isDirectory() ҎQ可以完成更复杂的事情。清?22 展示了一个例子:


清单 22. 分离文g和目?/strong>
def dir = new File(".") dir.eachFile{file->
 if(file.isFile()){
 println "FILE: ${file}"
 }else if(file.isDirectory()){
 println "DIR: ${file}"
 }else{
 println "Uh, I'm not sure what it is..."
 }
 }

׃两种 Java Ҏ都返?boolean |可以在代码中d一?Java 三元操作W。清?23 展示了一个例子:


清单 23. 三元操作W?/strong>
def dir = new File(".")
 dir.eachFile{file->
 println file.isDirectory() ? "DIR: ${file}" : "FILE: ${file}"
 }

如果只对目录有兴,那么可以使用 eachDir() 而不?eachFile()。还提供?eachDirMatch() ?eachDirRecurse() Ҏ?

可以看到Q对 File 仅?each() Ҏq不能提供够的含义。典?each() Ҏ的语义保存在 File 中,但是Ҏ名更h描述性,从而提供更多有兌个高U功能的信息?


URL q代

理解了如何遍?File 后,可以使用相同的原则遍?HTTP h的响应。Groovy ?java.net.URL 提供了一个方便的Q和熟悉的)eachLine() Ҏ?

例如Q清?24 逐行遍历 ibm.com 主页?HTMLQ?


清单 24. URL q代
def url = new URL("http://www.ibm.com")
 url.eachLine{line->
 println line
 }

当然Q如果这是您的目的的话QGroovy 提供了一个只包含一行代码的解决办法Q这主要归功?toURL() ҎQ它被添加到所?StringsQ?code>"http://www.ibm.com".toURL().eachLine{ println it }?

但是Q如果希望对 HTTP 响应执行一些更有用的操作,该怎么办呢Q具体来Ԍ如果发出的请求指向一?RESTful Web 服务Q而该服务包含您要解析?XMLQ该怎么做呢Q?code>each() Ҏ在q种情况下提供帮助?


XML q代

您已l了解了如何Ҏ件和 URL 使用 eachLine() Ҏ。XML l出了一个稍微有些不同的问题 — 与逐行遍历 XML 文档相比Q您可能更希望对逐个元素q行遍历?

例如Q假设您的语a列表存储在名?languages.xml 的文件中Q如清单 25 所C:


清单 25. languages.xml 文g
<langs>
 <language>Java</language>
 <language>Groovy</language>
 <language>JavaScript</language>
 </langs>

Groovy 提供了一?each() ҎQ但是需要做一些修攏V如果用名?XmlSlurper 的原?Groovy c解?XMLQ那么可以?each() 遍历元素。参见清?26 所C的例子Q?


清单 26. XML q代
def langs = new XmlSlurper().parse("languages.xml")
 langs.language.each{
 println it
 }
 //output Java Groovy JavaScript

langs.language.each 语句从名?<language> ?<langs> 提取所有元素。如果同时拥?<format> ?<server> 元素Q它们将不会出现?each() Ҏ的输Z?/p>

如果觉得q还不够的话Q那么假设这?XML 是通过一?RESTful Web 服务的Ş式获得,而不是文件系l中的文件。用一?URL 替换文g的\径,其余代码仍然保持不变Q如清单 27 所C:


清单 27. Web 服务调用?XML q代
def langs = new XmlSlurper().parse("http://somewhere.com/languages")
 langs.language.each{
 println it
 }

q真是个好方法,each() Ҏ在这里用得很好,不是吗?


l束?/a>

在?each() Ҏ的整个过E中Q最妙的部分在于它只需要很的工作可以处理大?Groovy 内容。解?each() Ҏ之后QGroovy 中的q代易如反掌了。正?Raymond 所_q正是关键所在。一旦了解了如何遍历 ListQ那么很快就会掌握如何遍历数l?code>Map?code>String?code>Range?code>enum、SQL ResultSet?code>File、目录和 URLQ甚x XML 文档的元素?

本文的最后一个示例简单提C?XmlSlurper 实现 XML 解析。在下一期文章中Q我l讨个问题,q展CZ?Groovy q行 XML 解析有多么简单!您将看到 XmlParser ?XmlSlurper 的实际用,q更好地了解 Groovy Z么提供两个类g又略有不同的cd?XML 解析。到那时Q希望您能发?Groovy 的更多实际应用?



2011-08-04 11:50 发表评论
]]> վ֩ģ壺 ˵Ƶwww| һAVٸӰ| ѿֻվ| Ʒavɫ| ͼƬĻ| avպav| ԾþþӰԺ| ѲػɫëƬ| 뿴һëƬѵ| þþƷһ99| aëƬ˾þ| ѹվ߹ۿҪ| һͼƬ| ޻վwwwwww| ޳| ޾Ʒ³ĵӰ| ѹҹӰ| Ƭ51˿Ӱ| ëɫëƬѹۿ| ҹ18ѿ| ĻѸ| Ƶվ߹ۿ| ĻӰӰԺ߹ۿƵ| ĻֻѿӰ| һɫѴƬ| һëƬѲ| 2018Ƶ| ŮǿڸˬƵ | ձ޸߹ۿ| avԴվavַ| ޻ɫվ| ޹Ʒպ| һëƬ߹| Ļ| ŷһ| һ24޿| ޾ƷaĻ| ..ŷһ| Ʒպһ91| ˳߹ۿվ | ѿAVƬ|