Tapestry入门

Apache Tapestry入门教程:构建后端开发的自学指南 Apache Tapestry是一个基于组件的Web应用程序框架,它使用Java编程语言,并通过强大的模板引擎和组件化的开发模式来简化Web应用程序的开发过程。它提供了丰富的功能,包括依赖注入、表单验证、事件处理等,使得开发者可以更专注于业务逻辑的实现。Apache Tapestry是一个基于组件的Web应用程序框架,使用Java编程语言。它通过强大的模板引擎和组件化的开发模式来简化Web应用程序的开发过程。它提供了丰富的功能,包括依赖注入、表单验证、事件处理等,使得开发者可以更专注于业务逻辑的实现。 阅读详情

 

简介

Jakarta Tapestry是一个开源的Java Web应用框架。你或许会说:"大同小异的东西罢了."多数

情况下,我同意你的观点,然而,只要花上些许时间研究一下,你会发现Tapestry跟别的框架大为不同,它是值得严肃对待的。

Tapestry是一个基于控件的框架以致于用它开发Web应用类似开发传统的GUI应用。你用Tapestry开发Web应用时你无需关注以操作为中心的(operation-centric) Servlet API.引用Tapestry网站上的一句话:"Tapestry用对象(objects),方法(methods),属性(properties)替代以往的URLs和查询参数, 重新诠释Web应用开发.Tapestry 3.0即将发布,它有大量的改进和新的特性。

Tapestry的目标

简单性

Tapestry应用与传统的Servlet应用相比代码量更少。大多数传统的Servlet应用包含如下厌烦和

重复的任务:解析查询参数,处理HttpSession对象,构建URLs。Tapestry消除了传统Servelt应用中许多无趣的"衔接"代码("plumbing" code)使开发者把精力集中到应用逻辑上来。

一致性

Tapestry为开发Web应用的页面提供了一致的方式。这样有助于消除传统Servlet应用开发中臆测。由于所有Tapestry应用中的页面都是用相同的可复用的控件组织而成,所以工作方式是相似的。

效率

Tapestr应用拥有高度的可升级性,它利用缓存和对象池使每个请求的处理时间最小化。Tapestry应用拥有跟传统Servlet应用相仿的性能。

错误反馈

任何开发过Servlet/JSP应用的人毫无质疑有类似经历:为了找出Web.xml文件有什么错误,不得不花费大量时间察看浏览器中的堆栈信息。Tapestry拥有优秀的错误报告方式,最值得一提的是它会指出哪个文件以及那一行导致了错误。

与Struts比较

既然Apache Struts可能是当今应用最广泛的Web应用框架,拿Tapestry与它比较是唯一公平的。以下是一些观察比较,它们来源于为这篇文章开发的几个简单的Tapestry应用和为几个Struts工程的工作经历。

Struts的优点

1 一个Servlet/JSP开发者熟悉Struts无需太久。然而Tapestry的学习曲线会长一点,因为它与流行的Web应用框架不太相同 。

2 Struts在Java社区里被广泛接受和使用。为你的项目找一个好的Struts开发人员并非难事,Tapestry近来在开发者社区里 赢得一些关注,然而仍有许多Java老手不知道Tapestry为何物。

3 既然Struts被如此广泛的使用,所以有很多Struts资源可供参考。相比大多数开源软件,Tapestry拥有非常可观的资源和文档,但跟Struts相比仍有差距。

Tapestry的优点

1 你开发一个Tapestry应用无需关注Servlet API,你也无须为你的Servlet应用写一些典型的"衔接"代码。虽然Struts简化了工作,然而Servlet API 仍是你需面对的。

2 Tapestry的页面模板除了几个特别属性和标识就是一个标准的HTML文件。 如果你是一个开发小组中的HTML设计高手,然而你不懂Java或JSP,这就给你带来很大方便。

3 因为Tapestry页面是标准的HTML,所以可以用HTML所见即所得(WYSIWYG)编辑器编辑和预览该页。当一个页需要修改它的外观并不需要通知服务器让它重新编译JSP.

4 Tapestry不需要一个至高的,整个应用范围的配置文件。Tapestry应用中的每一页是独立的,改变一页不会影响开发其他 页面的开发者,因为并没有一个配置文件把所有页面的浏览粘连在一起。

5 Tapestry拥有极好的错误报告。如果你在一个页的模板或页面规范犯了一个错误,Tapestry会指出导致错误的行号。

6 用Tapestry开发是种乐趣。这样说听上去似乎老调,然而用Tapestry开发一个Web应用相比应用其他流行的框架更为自然有趣。用Tapestry开发是应用了一种基于控件的架构,与开发传统的GUI应用非常相似。

Tapestry 架构

Tapestry框架是标准Servlet API的一种扩展。它需要J2SDK1.2或更高版本的J2SDK和一个与Servlet API 2.2(或更高)兼容的应用服务器/Servlet容器。

一个Tapestry应用由许多拥有唯一名称的页面组成。一个页面由一个模板和一些可复用的控件构成。模板由标准的HTML标签和一些额外的属性和标签构成,这些额外的属性和标签是为了告诉Tapestry框架这个页面的那些部分是由Tapestry控件组成。

简单的Tapestry应用

为了最好的描述构建一个Tapestry页面的方方面面,我们可以看看这个Pig Latin翻译器应用的代码。这个应用只有一个页面,在这页里输入一个text值把它翻译成Pig Latin,然后把翻译好的值显示给用户。

在Tapestry应用中每个页由3个部分组成:一个HTML模板,一个页面规范文件,一个Java类。

这里有这个页面屏幕抓图:

 


页面模板由标准的HTML标签和一些额外的属性和标签构成,这些额外的属性和标签是为了告诉Tapestry框架这个页面的那些部分是由Tapestry控件组成。页面模板存放在Web应用的根context目录下。通常,Tapestry在启动时会寻找和呈现一个名叫"Home"的页。虽然我们可以改变这种行为,但依照Tapestry的惯例会更简单。

Home.html
    <html>
    <head>
      <title>Tapestry Pig Latin Translator</title>
    </head>
    <body>
      <h1>Pig Latin Translator</h1>
      <form jwcid="@Form"① listener="ognl:listeners.submit"②>
      <table border="1">
        <tr>
          <td>Value to Translate:</td>
          <td>
            <input type="text" jwcid="@TextField"③ value="ognl:inputValue"/>
          </td>
        </tr>
        <tr>
          <td>Pig Latin:</td>
          <td>
            <jwcid="@Insert"④ value="ognl:pigLatinValue"/>
          </td>
        </tr>
      </table>
      <input type="submit" jwcid="@Submit"⑤ value="Translate"/>
      </form>
    </body>
    </html>
   

页面模板的绝大部分是普通的HTML,只有少部分Tapestry特有的属性和标签。这种模板机制的优势就是Tapestry页面模板可以在一个可见即所得的编辑器里创建和预览。描述Tapestry控件部分的标识是有限的和突出的。

标识里的jwcid所指是被应用的Tapestry控件的Java Web Component ID.在上面代码断里,我们是隐式地使用控件。隐式的控件是指直接在页面模板里声明使用的控件,。jwcid的前缀 '@ '符号就是通知Tapestry这里声明使用了一个隐式控件。

在上面的Pig Latin Translator页面模板里用了四个控件:Form①, TextField③, Insert④ 和Submit⑤。它们只是Tapestry框架提供的包含超过40个控件的控件库里的四个。在后面的范例中,我们将会看到如何使用显式控件。显式控件是指控件在页面规范文件里声明后再使用的控件。

在前面的HTML模板里,使用控件的同时,也为控件指定了参数。例如控件Form①有一个listener②参数它指定了当表单提交时对应的页面类调用的方法名称。那个ognl:前缀的使用贯穿页面的HTML模板,指向的是Object Graph Navigation Language (OGNL)。OGNL是一个强大的开源的表达式语言,用于将页面内控件的属性绑定到页面类的属性。

现在我们看看页面规范文件。页面规范文件是一个扩展名为page的XML文件,这个文件有许多职责,在众多职责中最基本是指定页面对应的Java类。页面规范文件存放在webapp的WEB_INF目录。

Home.page
    <?xml version="1.0"?>
    <!DOCTYPE page-specification PUBLIC
        "-//Apache Software Foundation//Tapestry Specification 3.0//EN"
        "http://jakarta.apache.org/tapestry/dtd/Tapestry_3_0.dtd>
    <page-specification class="Home">
        <property-specification name="inputValue" type="java.lang.String"/>
        <property-specification name="pigLatinValue" type="java.lang.String"/>
    </page-specification>

   
页面规范文件的根元素有一个class的属性,它指定了这个页对应的Java类。这个类必须要实现org.apache.tapestry.Ipage接口。页面规范同时页定义了两个属性(property)元素,以便Tapestry在页面类里创建新的属性。

Tapestry框架提供了org.apache.tapestry.html.BasePage class,它实现了Ipage接口。页面类被存放在Web-INF/classes目录下,跟你的Web应用的所需要的其他类放在一起。

Home.java
    import org.apache.tapestry.html.BasePage;
    import org.apache.tapestry.IRequestCycle;

    public abstract class Home extends BasePage {
        public abstract String getInputValue();
        public abstract void setInputValue(String inputValue);

        public abstract String getPigLatinValue();
        public abstract void setPigLatinValue(String pigLatinValue);

        public void submit(IRequestCycle cycle) {
            String inputValue = getInputValue();
            String pigLatinValue = new PigLatinTranslator().translate(inputValue);
            setPigLatinValue(pigLatinValue);
        }
    }
   

你要提醒的第一件事或许是这个类为什么是抽象类。它还有几个抽象方法访问inputValue,pigLatinValue属性。这里利用了Tapestry会在运行时刻创建子类的功能,这个子类会创建你在页面规范里声明的属性和生成相应的访问方法。

在表单提交时页面类的submit方法会被调用。为什么会这样?因为我们在页面模板里将Form控件的listener属性指定为:ognl:listeners.submit。这就意味着一个名叫submit的listener会通过页面类的listeners被访问。

所有的页面类和控件类都从org.apache.tapestry.AbstractComponent这个类继承来一个叫listeners的属性。当submit方法完成后,页面会显示被翻译好的词。

最后讲讲Web.xml这个Web发布描述文件。Tapestry,像许多其他的流行的Web应用框架一样,由一个Servlet构成,但是还需要一个发布描述文件。那个发布描述文件应该被存放在WEB-INF目录。

web.xml
    <?xml version="1.0"?>
    <!DOCTYPE web-app PUBLIC
        "-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
        "http://java.sun.com/dtd/web-app_2_3.dtd>
    <web-app>
        <display-name>Tapestry Pig Latin Translator</display-name>

        <servlet>
            <servlet-name>tapestry</servlet-name>
            <servlet-class>org.apache.tapestry.ApplicationServlet</servlet-class>
            <load-on-startup>1</load-on-startup>
        </servlet>

        <servlet-mapping>
            <servlet-name>tapestry</servlet-name>
            <url-pattern>/app</url-pattern>
        </servlet-mapping>
    </web-app>
   

虽然Pig Latin翻译应用非常简单,但是它会让你对在Tapestry应用中一个页面的3个组成部分有了基本的了解。它也展示了创建一个Tapestry应用的一个页面只需写多么少的代码。

表单输入验证

Tapestry 提供了一些控件以便校验用户的输入。校验子系统是ValidField控件的核心。在下面的登录应用中我们将使用ValidField控件。ValidField控件位于表单内,对用户在客户端的校验提供了有用的反馈和视觉上的错误提示。

区域化

在Tapestry中,区域化是相当简单的。Tapestry允许文字和图形的区域化。为了区域化页面的内容,你可以为每一个添加一个properties文件,或者提供一个区域化的模板。为每个页面提供一个资源文件的方式远比管理和维护一个巨大的全局的应用范围的资源文件简单。如果页面的区域化并不仅仅只是文字信息的区域化,例如页面的布局不同或者组成的控件不同,这样情况提供区域化的页面模板就能派上用场了。我们会在下面的登录应用的使用Tapestry区域化。

创建控件

Tapestry发布时提供了40多个自带的控件。如果你想知道更多的关于Tapestry自带控件的信息,请参考Tapestry Component Reference.想看看Tapestry的控件的应用范例可访问Tapestry Component Workbench.如果你发现你需要一个Tapestry本身没提供的控件,你可以自己创建一个。创建你自己的Tapestry控件跟创建一个页面是相似的。一个典型的Tapestry控件由一个控件规范文件(XML文档),一个HTML控件模板,一个实现了org.apache.tapestry.Icomponent接口的Java类。这个议题有点超出本文的范围,但是如果你有兴趣学习如何创建你自己的Tapestry控件,你可以参考Tapestry的原创人,Tapestry In Action 一书的作者--Howard Lewis Ship写的 Designing Tapestry Mega-Components 。

Tapestry 登录应用

你在Pig latin翻译器应用中看到了Tapestry的一些基本特性。与其用一个复杂的应用展示Tapestry所有的特性以致于压得你揣不过气来,还不如通过一些简单的应用让你找到一点对Tapestry的感觉。下面这个应用展示Tapestry如何处理页面导航,区域化,验证和其他一些特性。

这里有一个Home页的屏幕抓图,下面跟着它的页面模板。

 

Home.html
    <html>
    <head>
        <title>Welcome to the Tapestry Login Application</title>
    </head>

    <body>
        <h1>Welcome to the Tapestry Login Application</h1>
        <span jwcid="@PageLink"① page="Login">Login</span>
    </body>
    </html>
   
这个Home页的页面模板除了一个jwcid属性定义使用一个Tapestry PageLink①控件以外都是标准的HTML。

PageLink控件生成了一个指向Login页的超链接。既然Home页没有任何动态的行为所以它不需要页面规范和页面对应的Java类。

这里是Login页的屏幕抓图,后面跟着是它的页面模板。

 

Login.html
    <html>
    <head>
        <title>
            <span key="title">①Login</span>
        </title>
    </head>

    <body jwcid="@Body">②
        <span jwcid="@Conditional" condition="ognl:beans.delegate.hasErrors">③
            <div style="color: red">
                <span jwcid="@Delegator" delegate="ognl:beans.delegate.firstError">④
                    Error Message
                </span>
            </div>
        </span>
        <p style="font-weight: bold" >
            <span key="hint">Hint: Your password is your username spelled backwards.</span>
        </p>
       
        <form jwcid="@Form" listener="ognl:listeners.login" delegate="ognl:beans.delegate">

⑤
            <table>
                <tr>
                    <td align="right">
                        <span jwcid="@FieldLabel" field="ognl:components.inputUsername"⑥>
                            Username:
                        </span>
                    </td>
                    <td>
                        <input type="text" jwcid="inputUsername"⑦ value="simpson_h"

size="30"/>
                    </td>
                </tr>

                <tr>
                    <td align="right">
                        <span jwcid="@FieldLabel" field="ognl:components.inputPassword">
                            Password:
                        </span>
                    </td>
                    <td>
                        <input type="text" jwcid="inputPassword" hidden="true" value=""

size="30"/>
                    </td>
                </tr>

                <tr>
                    <td colspan="2" align="center">
                        <input type="submit" jwcid="@Submit" value="message:login"/>
                    </td>
                </tr>
            </table>
        </form>
    </body>
    </html>
   

这个页面模板大多数是通常的HTML。我们从页面模板中可以看到Tapestry的区域化特性:它使用一个span元素,这个span元素带有一个叫key的属性,key的值映射到Login.properties文件里一个属性。一个Body控件被声明使用,因为它对客户端的JavaScript校验是必需的。

为Form component⑤设定delegate属性激活表单输入验证。delegate属性是我们在页面规范里声明的org.apache.tapestry.valid.IvalidationDelegate的实现类。如果验证错误发生了,我们用Conditional component③控件判断delegate是否有任何错误,如果有就把第一个错误④显示给用户。如果ognl 表达式ognl:beans.delegate.hasErrors 为true,Conditional控件将显示它的内容实体。所有的页面类和控件类都从AbstractComponent继承来一个叫beans的属性。这个beans属性是一个org.apache.tapestry.IbeanProvider的实例,利用它可以通过名字取得在页面规范文件里定义的beans.FieldLabel⑥被用于为inputuserName validField控件显示标签,这个FieldLabel控件也被用来与表单的验证代理协作,指出包含错误的输入域。
InputUserName⑦控件是一个显示控件的例子。显式控件是指在页面规范文件声明的控件。InputUsername和inputPassword控件都是显式的,它们与FieldLabel联合显示它们的displayName属性。

下面的是Login页的资源文件。Login.properties跟页面规范一并存放在WEB-INF目录。

Login.properties
    title = Login to the Application
    hint = Hint: Your password is your username spelled backwards.
    login = Login
    username = Username:
    password = Password:
    invalidpassword = Invalid Password
   
Here is the page specification for the Login page.
Login.page
    <?xml version="1.0"?>
    <!DOCTYPE page-specification PUBLIC
        "-//Apache Software Foundation//Tapestry Specification 3.0//EN"
        "http://jakarta.apache.org/tapestry/dtd/Tapestry_3_0.dtd>

    <page-specification class="com.ociweb.tapestry.Login">
        <bean name="delegate" class="org.apache.tapestry.valid.ValidationDelegate"/>①

        <bean name="requiredValidator"②
            class="org.apache.tapestry.valid.StringValidator">
            <set-property name="required" expression="true"/>
            <set-property name="clientScriptingEnabled" expression="true"/>
        </bean>

        <property-specification name="username" type="java.lang.String"/>
        <property-specification name="password" type="java.lang.String"/>

        <component id="inputUsername" type="ValidField"> ③
            <message-binding name="displayName" key="username"/> ④
            <binding name="validator" expression="beans.requiredValidator"/> ⑤
            <binding name="value" expression="username"/> ⑥
        </component>

        <component id="inputPassword" type="ValidField"> ⑦
            <message-binding name="displayName" key="password"/>
            <binding name="validator" expression="beans.requiredValidator"/>
            <binding name="value" expression="password"/>
        </component>

    </page-specification>
   

Page-specification元素的class属性和两个property-specification元素与Pig Latin翻译器应用是相似的。

你会发现第一个新东西-bean元素①,bean元素把一个org.apache.tapestry.valid.ValidationDelegate

的实例指定了名称"delegate"。页面HTML模板里的Form控件把它的参数delegate设定为
ognl:beans.delegate,就是指向了这个org.apache.tapestry.valid.ValidationDelegate实例。
Bean元素②把一个org.apache.tapestry.valid.StringValidator的实例指定了名称"
requiredValidator",以用于验证。这个bean的required属性被设为true表明使用这个bean的域是必须被验证的。这个bean的clientScriptingEnabled属性被设定为ture,表明使用这个bean的域客户端的JavaScript验证功能是激活的。RequiredValidator bean被用于验证inputUsername和inputPassword的内容。

控件inputUsername③被控件规范声明为ValidField,ValidField是一种用于Tapestry验证子系统的特殊版本的TextField控件。Message-binding元素被用于指定inputUsername控件的displayName参数的值,这个值是用"username"为关键字从login.properties④文件里得到。InputUsername控件的validator参数被设定为requiredValidator bean,这是我们在页面规范里声明过的⑤。控件的value参数跟页面Java类的username属性绑定在一起⑥。控件inputPassword的控件规范跟控件inputUsername几乎相似,除了用于取得displayName的关键字和绑定的页面Java类的属性不同。

通过使用ValidField控件和为表单(form)提供一个ValidationDelegate, 我们激活了Login表单的验证功能。除了服务器端的验证,Tapestry也提供了客户端的验证(利用JavaScript)。下面就是当用户提交一个表单而没有为UserName域提供值时,一个JavaScript错误对话框弹出时的屏幕抓图。

 

下面就是当用户提交一个表单而没有为Password域提供值时,一个JavaScript错误对话框弹出时的屏幕抓图。

 

 

下面就是Login页对应的Java 类。

Login.java
    package com.ociweb.tapestry;

    import org.apache.tapestry.html.BasePage;
    import org.apache.tapestry.IRequestCycle;
    import org.apache.tapestry.valid.ValidationConstraint;
    import org.apache.tapestry.valid.IValidationDelegate;

    public abstract class Login extends BasePage {
        public abstract String getUsername();
        public abstract void setUsername(String username);

        public abstract String getPassword();
        public abstract void setPassword(String password);

        public void login(IRequestCycle cycle) {
            String username = getUsername();
            String password = getPassword();
            StringBuffer sb = new StringBuffer(username);
            String validPassword = sb.reverse().toString();
            if (password.equals(validPassword)) {
                cycle.activate("Success");①
            } else {
                String errorMessage = getMessage("invalidpassword");②
                IValidationDelegate validationDelegate =
                        (IValidationDelegate) getBeans().getBean("delegate");③
                validationDelegate.record(errorMessage,
                                          ValidationConstraint.CONSISTENCY);④
            }
        }
    }
   
跟Pig Latin翻译器应用一样,我们的页面类也是抽象的,它有抽象方法访问在页面规范里定义的属性(properties)。Tapestry会在运行时刻创建username和password属性。Login方法只是简单的验证一下用户输入的密码值是否刚好是用户名的反向。如果密码通过验证,用户将被引领导Success page①。

如果密码输入有误,我们用关键字"invalidPassword"通过从org.apache.tapestry.AbstractComponent里继承来的getMessage()方法从Login.properties②里查找对应的资源。我们需要把密码错误信息纪录到我们在页面规范中定义的页面validation delegate中去。我们可以利用我们在页面规范中指定的名称,从页面的beans属性中找回validationDelegate③。最后,我们调用org.apache.tapestry.valid.IvalidationDelegate的record方法把将要显示给用户看的错误信息保存起来。下面就是当用户输入错误密码的提交后的屏幕抓图。

 

下面就是Success页的页面模板。Success页的页面模板仅仅包含HTML标识,所以它不需要页面规范和页面

Java类。

Success.html
    <html>
    <head>
        <title>Successful Login</title>
    </head>
    <body>
        <p>
            Congratulations! You have successfully logged on.
        </p>
    </body>
    </html>
   
总结

我希望这篇文章已经向你展示了Tapestry框架在构建Web应用的是多么简单,然而优雅。Tapestry与大多数主流Web应用框架最大不同在于它让你用基于控件的方式开发,而非以操作为中心的方式开发。如果这篇文章激起了你的兴趣,我建议你把它下载下来利用它你自己的简单的Web应用。通过感受简单的应用,这是你了解这个框架的优点的唯一途径。如果你想在你的下一个项目里使用Tapestry,我强烈建议你购买
Tapestry In Action 这本书。我拥有这本书,对它我感到很满意。

References
1 Zip file with all source code and war files from the article. (12K)

                 http://www.ociweb.com/jnb/jnb2004_05.zip
2 Tapestry Home Page http://jakarta.apache.org/tapestry/
3 Tapestry In Action Page http://www.manning.com/lewisship/
4 Tapestry Wiki http://jakarta.apache.org/tapestry/wiki_frame.html
5 OGNL page http://www.ognl.org/
6 Tapestry Component Reference

                 http://jakarta.apache.org/tapestry/doc/ComponentReference/index.html
7 Tapestry Component Workbench http://www.t-deli.com/app
8 Designing Tapestry Mega-Components

                 http://www.onjava.com/pub/a/onjava/2001/11/21/tapestry.html

Tapestry开源框架的详细讲解doc文档(经典) Tapestry开源框架的doc文档详细讲解了与当前最流行的web开源框架struts进行了全方位的比较,Tapestry是一个基于控件的框架以致于用它开发Web应用类似开发传统的GUI应用。你用Tapestry开发Web应用时你无需关注以操作为中心的(operation-centric) Servlet API.引用Tapestry网站上的一句话:"Tapestry用对象(objects),方法(methods),属性(properties)替代以往的URLs和查询参数, 重新诠释Web应用开发.Tapestry 3.0即将发布,它有大量的改进和新的特性 立即下载

相关推荐

以ATT&CK为例构建网络安全知识图

随着攻击工具、方法的逐渐升级和复杂化,安全数据的大规模融合,攻防对抗愈加激烈。安全团队如何在浩瀚数据中有效发现高级威胁的蛛丝马迹,如何把网络安全专家的经验、知识有效转化为可复制可扩展的数据分析能力,如何将对抗高级威胁的“炼金术”逐步升级为科学淘金指南,如何将安全从业者从繁重的体力劳动中解放出来,愈发成为安全能力亟需突破的难点和重点,也是我们正在探索的方向。正如医疗行业中治疗疑难杂症依赖医疗专家,网络空间高级威胁的防护和处置也依赖安全专家的经验与知识。

2401_88752684的博客 1091

Tapestry入门(译作)

                                Introduction to Jakarta Tapestry                                                          (Tapestry入门)   by Rob Smith , Senior Software Engineer Object Computing

TangAiYun专栏 2458

别再折腾SNAP了!ENVI 5.6.0 直接拖拽打开Sentinel-2 L2A数据的正确姿势

本文详细介绍了ENVI 5.6.0直接处理Sentinel-2 L2A数据的高效方法,无需通过SNAP进行繁琐的重采样预处理。通过直接拖拽XML文件,用户可以快速加载不同分辨率的波段数据,显著提升工作效率。文章还对比了直接打开与SNAP重采样流程的优劣,并提供了常见问题解决方案和高级应用技巧。

weixin_30296405的博客 635

【apache之Tapestry 介绍】

A component-oriented framework for creating highly scalable web applications in Java.   Java Power Tapestry pages and components are simple Java POJOs, with easy access to all Java language featur...

1466

Transformer-Based Attention Networks for Continuous Pixel-Wise Prediction 基于Transformer注意力网络连续像素级与估计

Transformer-Based Attention Networks for Continuous Pixel-Wise Prediction 基于Transformer注意力网络的连续的像素级的

MengYa_Dream的博客 4716

c++篇 cad.arx Win10环境配置vs2019+arx2021多版本配置+vs2022 配置图

msvc v141 v140这个两个好像是编译vs2015 vs2017版本的,必须装,然后v142装最新的,剩下的有些是默认的,还有就是mfc这些恐怕要装,然后是v140v141这两个版本的windows sdk是8.1,需要单独装一下。Windows SDK version 8.1 下载地址。windows sdk是10.0.19041.0。先安装vs2019,如图。

我的博客 782

Tapestry(二):Tapestry基本知识

Tapestry是“基于组件”的表现层框架之一。 Tapestry组件用于表现HTML响应,以及响应HTTP请求。Tapestry组件通过其规范定义。规范是一个XML文档,其中定义了组件类型,参数,组件模板,包含的组件以及被包含组件之间的联系,还原所有的assets。 在运行的时候,规范指定并实例一个类,当页面所包含的组件被表现的时候,组件将访问HTML模板,找到静态的HTML并植入组件。

EGWriket的博客 992

YOLO26训练自己的数据集,从代码下载到实例测试 (含YOLO26网络结构图)

在Windows10上配置CUDA环境教程2026年1月14日,YOLO26是最新发布的计算机视觉模型。支持多种任务,包括目标检测、实例分割、图像分类、姿态估计、有向目标检测以及物体跟踪等。以上就是YOLO26训练自己数据集的全部过程啦,欢迎大家在评论区交流~

Limiiiing的博客 6533

Tapestry经典入门教程

简单介绍   不必关心链接!不必关心请求(http request)到了哪里!不必关心响应(http response)要转向哪里!Tapestry构建于底层的request-resonse模式,基于Servlet技术,抽象出面向组件开发的模型。Tapestry关心的是:页面、组件、事件、对象、方法、属性! 安装jar包 1、 将Tapestry解压目录下的lib目录中的jar包拷贝到WE

棋棋_攻城狮 3554

MATLAB算法实战应用案例精讲-【数模应用】梯度提升决策树(GDBT)(附python代码)

GBDT(Gradient Boosting Decision Tree) 又叫 MART(Multiple Additive Regression Tree),是一种迭代的决策树算法,该算法由多棵决策树组成,它在被提出之初就和SVM一起被认为是泛化能力(generalization)较强的算法。近些年更因为被用于搜索排序的机器学习模型而引起大家关注。.........

qq_36130719的博客 2078

VisionTransformer改进(11):结合CoordAtt注意力机制

​​CoordAtt模块​​:一个轻量级的坐标注意力机制​​ViT模型​​:基于标准Vision Transformer架构,但集成了CoordAtt模块模型最终通过CNNModel函数封装,虽然名称是CNN,但实际上是一个Transformer模型。引入了轻量级的CoordAtt注意力机制,增强了模型对空间位置信息的捕捉能力保持了ViT的主要优势,同时通过注意力机制提升了特征表示能力设计简洁高效,适合作为基础模型进行进一步研究和应用。

2401_82355416的博客 701

Tapestry4入门

 1.       Tapestry4开发环境的安装JDK:5.0开发工具:Eclipse3.2 , WTP 1.5.2服务器:Tomcat 5.5.202.       Tapestry4下载http://tapestry.apache.org版本:tapestry-project-4.1.1-bin.zip3.     安装Tapestry4解压下载下来的t

楓雨人生 2958

33、AI赋能5G/6G通信:LDPC码解码与强化学习技术解析

本文探讨了基于AI和强化学习的LDPC码技术在5G/6G通信中的应用。包括LAMS解码器、神经MS解码器、盲识别方法、统一极性-LDPC解码器、NNMS和SNNMS解码器、N-2D-NMS解码器、神经分层MS解码器、MAB-NS方案以及强化学习与MCTS结合的技术。这些技术在提升解码性能、降低计算复杂度和增强系统适应性方面表现出色,为未来通信系统的发展提供了强有力的支持。

lambda的博客 243

Tapestry入门及进阶一

要Tapestry开发一个Web Application,对一个新手来说有点困难的,Tapestry由于不同于以前的Web Presentation Framework,所以不可讳言,学习曲线比较长这是事实。我先讲讲一个Web Application的大体结构:以JBuider9为开发工具,你要先建立一个工程,例如是名称是TapestryExmaple,它的workspace是F:/myproje

TangAiYun专栏 2256

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

深度学习工具包 DeepLearningToolbox

深度学习工具包Deprecation notice.-----This toolbox is outdated and no longer maintained.There are much better tools available for deep learning than this toolbox, e.g. [Theano](http://deeplearning.net/software/theano/), [torch](http://torch.ch/) or [tensorflow](http://www.tensorflow.org/)I would suggest you use one of the tools mentioned above rather than use this toolbox.Best, Rasmus.DeepLearnToolbox================A Matlab toolbox for Deep Learning.Deep Learning is a new subfield of machine learning that focuses on learning deep hierarchical models of data.It is inspired by the human brain's apparent deep (layered, hierarchical) architecture.A good overview of the theory of Deep Learning theory is[Learning Deep Architectures for AI](http://www.iro.umontreal.ca/~bengioy/papers/ftml_book.pdf)For a more informal introduction, see the following videos by Geoffrey Hinton and Andrew Ng.* [The Next Generation of Neural Networks](http://www.youtube.com/watch?v=AyzOUbkUf3M) (Hinton, 2007)* [Recent Developments in Deep Learning](http://www.youtube.com/watch?v=VdIURAu1-aU) (Hinton, 2010)* [Unsupervised Feature Learning and Deep Learning](http://www.youtube.com/watch?v=ZmNOAtZIgIk) (Ng, 2011)If you use this toolbox in your research please cite [Prediction as a candidate for learning deep hierarchical models of data](http://www2.imm.dtu.dk/pubdb/views/publication_details.php?id=6284)```@MASTERSTHESIS\{IMM2012-06284, author = "R. B. Palm", title = "Prediction as a candidate for learning deep hierarchical models of data", year = "2012",}```Contact: rasmusbergpalm at gmail dot comDirectories included in the toolbox-----------------------------------`NN/` - A library for Feedforward Backpropagation Neural Networks`CNN/` - A library for Convolutional Neural Networks`DBN/` - A library for Deep Belief Networks`SAE/` - A library for Stacked Auto-Encoders`CAE/` - A library for Convolutional Auto-Encoders`util/` - Utility functions used by the libraries`data/` - Data used by the examples`tests/` - unit tests to verify toolbox is workingFor references on each library check REFS.mdSetup-----1. Download.2. addpath(genpath('DeepLearnToolbox'));Example: Deep Belief Network---------------------```matlabfunction test_example_DBNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit RBM and visualize its weightsrand('state',0)dbn.sizes = [100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);figure; visualize(dbn.rbm{1}.W'); % Visualize the RBM weights%% ex2 train a 100-100 hidden unit DBN and use its weights to initialize a NNrand('state',0)%train dbndbn.sizes = [100 100];opts.numepochs = 1;opts.batchsize = 100;opts.momentum = 0;opts.alpha = 1;dbn = dbnsetup(dbn, train_x, opts);dbn = dbntrain(dbn, train_x, opts);%unfold dbn to nnnn = dbnunfoldtonn(dbn, 10);nn.activation_function = 'sigm';%train nnopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.10, 'Too big error');```Example: Stacked Auto-Encoders---------------------```matlabfunction test_example_SAEload mnist_uint8;train_x = double(train_x)/255;test_x = double(test_x)/255;train_y = double(train_y);test_y = double(test_y);%% ex1 train a 100 hidden unit SDAE and use it to initialize a FFNN% Setup and train a stacked denoising autoencoder (SDAE)rand('state',0)sae = saesetup([784 100]);sae.ae{1}.activation_function = 'sigm';sae.ae{1}.learningRate = 1;sae.ae{1}.inputZeroMaskedFraction = 0.5;opts.numepochs = 1;opts.batchsize = 100;sae = saetrain(sae, train_x, opts);visualize(sae.ae{1}.W{1}(:,2:end)')% Use the SDAE to initialize a FFNNnn = nnsetup([784 100 10]);nn.activation_function = 'sigm';nn.learningRate = 1;nn.W{1} = sae.ae{1}.W{1};% Train the FFNNopts.numepochs = 1;opts.batchsize = 100;nn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.16, 'Too big error');```Example: Convolutional Neural Nets---------------------```matlabfunction test_example_CNNload mnist_uint8;train_x = double(reshape(train_x',28,28,60000))/255;test_x = double(reshape(test_x',28,28,10000))/255;train_y = double(train_y');test_y = double(test_y');%% ex1 Train a 6c-2s-12c-2s Convolutional neural network %will run 1 epoch in about 200 second and get around 11% error. %With 100 epochs you'll get around 1.2% errorrand('state',0)cnn.layers = { struct('type', 'i') %input layer struct('type', 'c', 'outputmaps', 6, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %sub sampling layer struct('type', 'c', 'outputmaps', 12, 'kernelsize', 5) %convolution layer struct('type', 's', 'scale', 2) %subsampling layer};cnn = cnnsetup(cnn, train_x, train_y);opts.alpha = 1;opts.batchsize = 50;opts.numepochs = 1;cnn = cnntrain(cnn, train_x, train_y, opts);[er, bad] = cnntest(cnn, test_x, test_y);%plot mean squared errorfigure; plot(cnn.rL);assert(er<0.12, 'Too big error');```Example: Neural Networks---------------------```matlabfunction test_example_NNload mnist_uint8;train_x = double(train_x) / 255;test_x = double(test_x) / 255;train_y = double(train_y);test_y = double(test_y);% normalize[train_x, mu, sigma] = zscore(train_x);test_x = normalize(test_x, mu, sigma);%% ex1 vanilla neural netrand('state',0)nn = nnsetup([784 100 10]);opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samples[nn, L] = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.08, 'Too big error');%% ex2 neural net with L2 weight decayrand('state',0)nn = nnsetup([784 100 10]);nn.weightPenaltyL2 = 1e-4; % L2 weight decayopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex3 neural net with dropoutrand('state',0)nn = nnsetup([784 100 10]);nn.dropoutFraction = 0.5; % Dropout fraction opts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex4 neural net with sigmoid activation functionrand('state',0)nn = nnsetup([784 100 10]);nn.activation_function = 'sigm'; % Sigmoid activation functionnn.learningRate = 1; % Sigm require a lower learning rateopts.numepochs = 1; % Number of full sweeps through dataopts.batchsize = 100; % Take a mean gradient step over this many samplesnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex5 plotting functionalityrand('state',0)nn = nnsetup([784 20 10]);opts.numepochs = 5; % Number of full sweeps through datann.output = 'softmax'; % use softmax outputopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, train_x, train_y, opts);[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');%% ex6 neural net with sigmoid activation and plotting of validation and training error% split training data into training and validation datavx = train_x(1:10000,:);tx = train_x(10001:end,:);vy = train_y(1:10000,:);ty = train_y(10001:end,:);rand('state',0)nn = nnsetup([784 20 10]); nn.output = 'softmax'; % use softmax outputopts.numepochs = 5; % Number of full sweeps through dataopts.batchsize = 1000; % Take a mean gradient step over this many samplesopts.plot = 1; % enable plottingnn = nntrain(nn, tx, ty, opts, vx, vy); % nntrain takes validation set as last two arguments (optionally)[er, bad] = nntest(nn, test_x, test_y);assert(er < 0.1, 'Too big error');```[![Bitdeli Badge](https://d2weczhvl823v0.cloudfront.net/rasmusbergpalm/deeplearntoolbox/trend.png)](https://bitdeli.com/free "Bitdeli Badge")

Tapestry入门及进阶二

下面来谈谈Tapestry的开发流程。Tapestry的开发主要有两种:一种是控件的开发,一种是页面的开发,其实页面也可以被看成控件。以我的工程为例,我的控件全放在com.ht.components下以我的ToolBar为例,我的ToolBar控件放在com.ht.components.toolbar下下面有IToolItemDescirption.javaIToolItemListener.ja

TangAiYun专栏 2002

WINCC7.3破解文件

WINCC7.3硬件够破解文件,有需要的下载!WINCC7.3硬件够破解文件,有需要的下载!

TapeStry入门

Tapestry是一个开源的基于servlet的应用程序框架,它使用组件对象模型来创建动态的,交互的web应用。一个组件就是任意一个带有jwcid属性的html标记。其中jwc的意思是Java Web Component。Tapestry使得java代码与html完全分离,利用这个框架开发大型应用变得轻而易举。并且开发的应用很容易维护和升级。Tapestry支持本地化,其错误报告也很详细。Ta

大T的专栏 4142

OV9734 DATASHEET,完整规格书

OV9734完整规格书,包括电气参数,尺寸规格,寄存器配置表等

Tapestry入门实例

 今天开始接触到Tapestry框架,用的是Tapestry3.03包(MyEclipse 的tapstry插件),开发环境是Eclipse,Web服务器用的是Weblogic。参照的教程是《享受Tapestry给Web开发带来的乐趣》,果然它不辱使命,给我带来了无限的“乐趣”。可能教程上用的是Tapestry4,而我使用的是Tapestry3的缘故吧,好象高版本是有了很多新功能,我完全找

netwares的专栏 1822
上一篇: 游标使用方法
下一篇: 存储过程编写经验和优化措施
gmplayer
博客等级 码龄22年 2粉丝 32原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值