现在的位置: 首页 > 综合 > 正文

MetaData Programme

2013年08月23日 ⁄ 综合 ⁄ 共 4989字 ⁄ 字号 评论关闭

MetaData Programme

作者:Anders小明

1.1.        什么是元数据编程

什么是元数据,元数据就是描述数据的数据(data about data)。最明显的例子是XML Schemaxml schema就是描述xml的数据,所以它是元数据。另一个例子是数据库,比如我们可以查询数据库中有几个表,每个表都有什么字段,这些数据就是元数据。

在开发的世界里,元数据就是能够绑定到一个类的附加信息,在静态或者运行时间。JCR175给我们提供annotation就是一种元数据。

不过在这之前一个我们已经广泛使用的元数据是XML,如就是EJBXML发布描述符中,你需要定义基于每一个方法的事务属性。应用服务器指导什么时候,什么地方开始,挂起或者提交一个事务,因为你在BEANXML的配置文件中的元数据内已经定义如方法:RequiredRequiresNewSupport等等,它们绑定在你的EJB类和事务管理之间。XDoclet是另一个元数据的例子。

1.2.        Annotation的意义和简单例子

       JDK1.5提供的annotation与我们所常见的classesfieldssmethods间是什么关系。如下:如果说类和数据成员是名词,方法是动词,那么annotation就是形容词或者副词,分别描述它们的所具有属性。

好,现在就来实现一个annotation

import java.lang.annotation.Retention;

package sample.annotation

@Retention(java.lang.annotation.RetentionPolicy.RUNTIME)

    public @interface Broker {

    String name();

    String address();

    }

}

使用这个annotation

Import sample.annotation.broker

@Broker(name="anders", address=" xiamen")

public class Agent {

    public String getTelPhone (){

         return  "010-0592-2519280";

    }

}

运行期得到这个annotation

public class Main {

    public static void main(String[] args){

Agent agent = new Agent();

        try{

            Annotation[] a = agent.getClass().getMethod("getBrokerName").getAnnotations();

            for (int i=0; i<a.length ; i++)  {

                 if( a[i] instanceof Broker){

                      Broker broker = (Broker)a[i];

                     System.out.println(broker.name());

                 }

             }

        }

        catch(Exception e){

            e.printStackTrace(System.out);

        }

   }

}

1.3.        Annotationclass文件格式

       利用sun公司的提供的javap,我们可以看到annotation的在class文件中的表示。以下为对比结果:

源码:

@Retention(java.lang.annotation.RetentionPolicy.RUNTIME)

public @interface Broker {

    String name();

    String address();

}

Javap结果:

Compiled from "Broker.java"

interface Broker extends java.lang.annotation.Annotation

  SourceFile: "Broker.java"

  minor version: 0

  major version: 0

  Constant pool:

const #1 = class    #9;  // Broker

const #2 = class    #10; // Object

const #3 = class    #11; //Annotation

const #4 = Asciz    name;

const #5 = Asciz   ()Ljava/lang/String;;

const #6 = Asciz    address;

const #7 = Asciz    SourceFile;

const #8 = Asciz    Broker.java;

const #9 = Asciz    Broker;

const #10 = Asciz   java/lang/Object;

const #11 = Asciz   java/lang/annotation/Annotation;

 

{

public abstract java.lang.String name();

 

public abstract java.lang.String address();

}  

 

源码:

public interface Broker {

    String name();

    String address();

}

Javap结果:

Compiled from "Broker.java"

interface Broker

  SourceFile: "Broker.java"

  minor version: 0

  major version: 0

  Constant pool:

const #1 = class    #8; //  Broker

const #2 = class    #9; //  Object

const #3 = Asciz    name;

const #4 = Asciz    ()Ljava/lang/String;;

const #5 = Asciz    address;

const #6 = Asciz    SourceFile;

const #7 = Asciz    Broker.java;

const #8 = Asciz    Broker;

const #9 = Asciz    java/lang/Object;

 

{

public abstract java.lang.String name();

 

public abstract java.lang.String address();

 

}

 

源码:

@Broker(name="anders", address=" xiamen")

public class Agent {

    public String getTelPhone(){

        return  "0592-2519580";

    }

}

Javap结果:

Compiled from "Agent.java"

public class Agent extends java.lang.Object

  SourceFile: "Agent.java"

  RuntimeVisibleAnnotations: length = 0x10

   00 01 00 11 00 02 00 12 73 00 13 00 14 73 00 15

  

  minor version: 0

  major version: 0

  Constant pool:

const #1 = Method   #4.#22; //  java/lang/Object."<init>":()V

const #2 = String   #23;    //  0592-2519580

const #3 = class    #24;    //  Agent

const #4 = class    #25;    //  Object

const #5 = Asciz    <init>;

const #6 = Asciz    ()V;

const #7 = Asciz    Code;

const #8 = Asciz    LineNumberTable;

const #9 = Asciz    LocalVariableTable;

const #10 = Asciz   this;

const #11 = Asciz   LAgent;;

const #12 = Asciz   getTelPhone;

const #13 = Asciz   ()Ljava/lang/String;;

const #14 = Asciz   SourceFile;

const #15 = Asciz   Agent.java;

const #16 = Asciz   RuntimeVisibleAnnotations;

const #17 = Asciz   LBroker;;

const #18 = Asciz   name;

const #19 = Asciz   anders;

const #20 = Asciz   address;

const #21 = Asciz   xiamen;

const #22 = NameAndType #5:#6;//  "<init>":()V

const #23 = Asciz   0592-2519580;

const #24 = Asciz   Agent;

const #25 = Asciz   java/lang/Object;

// 以下为方法域,略  

 

源码:

public class Agent {

    public String getTelPhone(){

        return  "0592-2519580";

    }

}

Javap结果:

Compiled from "Agent.java"

public class Agent extends java.lang.Object

  SourceFile: "Agent.java"

  minor version: 0

  major version: 0

  Constant pool:

const #1 = Method   #4.#16; //  java/lang/Object."<init>":()V

const #2 = String   #17;    //  0592-2519580

const #3 = class    #18;    //  Agent

const #4 = class    #19;    //  Object

const #5 = Asciz    <init>;

const #6 = Asciz    ()V;

const #7 = Asciz    Code;

const #8 = Asciz    LineNumberTable;

const #9 = Asciz    LocalVariableTable;

const #10 = Asciz   this;

const #11 = Asciz   LAgent;;

const #12 = Asciz   getTelPhone;

const #13 = Asciz   ()Ljava/lang/String;;

const #14 = Asciz   SourceFile;

const #15 = Asciz   Agent.java;

const #16 = NameAndType #5:#6;//  "<init>":()V

const #17 = Asciz   0592-2519580;

const #18 = Asciz   Agent;

const #19 = Asciz   java/lang/Object;

// 以下为方法域,略

 

补充说明:我们都知道在java 1.0发布时,java class file的格式就已经定下来,要说明的是为了应未来的需要java class file设计了属性说的机制。一直到j2se1.4都没有怎么改变。但这次为了更好的支持metadata技术,一共增加了8个属性。分別是:

EnclosingMethodAttribute Anonymous Class Local Inner Class 使用此 Attribute 描述该Class Scope

Signature AttributeGenerics ClassMethod、或 Filed使用此 Attribute 来记录所要的类型,因为java的范型采用了擦拭法。

LocalVariableTypeTable Attribute:主要是給 debugger 使用,目的和「LocalVariableTable

抱歉!评论已关闭.