<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Knight of the round table

    wansong

    XStream Annotations 入門【翻譯】

    1、簡單的轉換器:

    首先創建示例的環境,
    下面介紹的是最基礎的轉換器,首先創建一個Person類:

    package com.thoughtworks.xstream.examples;
    public class Person {
    private String name;
    public String getName() {
    return name;
    }
    public void setName(String name) {
    this.name = name;
    }
    }

     接著,我們創建一個實例,并轉化他:

    package com.thoughtworks.xstream.examples;
    import com.thoughtworks.xstream.XStream;
    import com.thoughtworks.xstream.io.xml.DomDriver;
    public class PersonTest {
    public static void main(String[] args) {
    Person person = new Person();
    person.setName("Guilherme");
    XStream xStream = new XStream(new DomDriver());
    System.out.println(xStream.toXML(person));
    }
    }

     如你所料,得到下面的結果:

    <com.thoughtworks.xstream.examples.Person>
    <name>Guilherme</name>
    </com.thoughtworks.xstream.examples.Person>

    下面我們為person類創建一個別名:

    XStream xStream = new XStream(new DomDriver());
    xStream.alias("person", Person.class);
    System.out.println(xStream.toXML(person));

    現在的結果就很易讀了:

    <person>
    <name>Guilherme</name>
    </person>

    到此,我們已經建立好一個可以供我們實驗的基礎例子了,下面我們來看看XStream的轉換器能為我們做些什么:
    2,創建一個Person轉換器:
    下面我們來創建一個簡單的轉換器,它能:
    1,用來轉換Person類
    2,將Person實例轉換成XML
    3,將xml轉換為Person實例
    首先創建一個PersonConverter類,并讓這個類實現Converter接口:

    package com.thoughtworks.xstream.examples;
    import com.thoughtworks.xstream.converters.Converter;
    import com.thoughtworks.xstream.converters.MarshallingContext;
    import com.thoughtworks.xstream.converters.UnmarshallingContext;
    import com.thoughtworks.xstream.io.HierarchicalStreamReader;
    import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
    public class PersonConverter implements Converter {
    public boolean canConvert(Class clazz) {
    return false;
    }
    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    }
    public Object unmarshal(HierarchicalStreamReader reader,
    UnmarshallingContext context) {
    return null;
    }
    }

    下面,我們首先告訴轉換器,我們只能轉換Person類,而不是別的類,包括其子類:

    public boolean canConvert(Class clazz) {
    return clazz.equals(Person.class);
    }

    這一步很簡單,除非你是用來處理泛型的轉換器是會困難一點。

    Marshal方法是用來將對象轉換為XML的,他有三個參數:
    1,我們準備轉換的對象
    2,我們準備輸出對象的writer
    3,當前的marshaling context
    首先我們將object轉換成Person

    Person person = (Person) value;
    接著,我們就可以開始輸出數據了,首先我們創建一個叫做fullname的節點,并將person的名字傳給他:

    writer.startNode("fullname");
    writer.setValue(person.getName());
    writer.endNode();

    呵呵~很簡單吧,

    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    Person person = (Person) value;
    writer.startNode("fullname");
    writer.setValue(person.getName());
    writer.endNode();
    }

    我們可以任意次數的調用start/end node方法,但需要記住,你必須在打開一個節點之后記住關閉它。一般來說,執行轉換的操作在setValue方法調用時發生。
    下面,我們進入unmarshal方法,我們使用moveDown和moveUp方法在節點樹層次中移動,所以,這里我們只需要簡單的moveDown,得到值,再moveUp:

    Person person = new Person();
    reader.moveDown();
    person.setName(reader.getValue());
    reader.moveUp();

    最后,我們得到了一個這樣的轉換器:

    package com.thoughtworks.xstream.examples;
    import com.thoughtworks.xstream.converters.Converter;
    import com.thoughtworks.xstream.converters.MarshallingContext;
    import com.thoughtworks.xstream.converters.UnmarshallingContext;
    import com.thoughtworks.xstream.io.HierarchicalStreamReader;
    import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
    public class PersonConverter implements Converter {
    public boolean canConvert(Class clazz) {
    return clazz.equals(Person.class);
    }
    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    Person person = (Person) value;
    writer.startNode("fullname");
    writer.setValue(person.getName());
    writer.endNode();
    }
    public Object unmarshal(HierarchicalStreamReader reader,
    UnmarshallingContext context) {
    Person person = new Person();
    reader.moveDown();
    person.setName(reader.getValue());
    reader.moveUp();
    return person;
    }
    }

    接著,我們在我們的main方法中注冊這個轉化器:

    package com.thoughtworks.xstream.examples;
    import com.thoughtworks.xstream.XStream;
    import com.thoughtworks.xstream.io.xml.DomDriver;
    public class PersonTest {
    public static void main(String[] args) {
    Person person = new Person();
    person.setName("Guilherme");
    XStream xStream = new XStream(new DomDriver());
    xStream.registerConverter(new PersonConverter());
    xStream.alias("person", Person.class);
    System.out.println(xStream.toXML(person));
    }
    }

    注意到我們怎么注冊我們的轉換器了么?只需要下面簡單的一句:

    xStream.registerConverter(new PersonConverter());
    最終得到的結果是:

    <person>
      <fullname>Guilherme</fullname>
    </person>
    也許你會說:這只改變了我輸出的樹,我需要用它來轉換數據。
    下面我們來嘗試在person標簽中創建一個叫做fullname的屬性,而不是新創建一個節點:
    3,一種可選的方式:
    首先,為Person創建一個toString方法,里面包含了所有能用來重新創建一個Person實例的數據:

    package com.thoughtworks.xstream.examples;
    public class Person {
    private String name;
    public String getName() {
    return name;
    }
    public void setName(String name) {
    this.name = name;
    }
    public String toString() {
    return getName();
    }
    }

    現在,我們就能把我們的轉化器簡寫為:

     

    package com.thoughtworks.xstream.examples;
    import com.thoughtworks.xstream.converters.basic.AbstractSingleValueConverter;
    public class PersonConverter extends AbstractSingleValueConverter {
    public boolean canConvert(Class clazz) {
    return clazz.equals(Person.class);
    }
    public Object fromString(String str) {
    Person person = new Person();
    person.setName(string);
    return person;
    }
    }

    現在,輸出的XML也會變得更易讀(為person創建別名person之后):

    <person>Guilherme</person>
    名字變成了一個內置的值,而不是一個單獨的節點。
    4,轉換Date:
    我們已經知道Converter接口是怎樣工作的了,現在我們來創建一個使用Locale對象轉換時間的轉換器:
    在我們的轉換器構造方法中,我們將傳入一個Locale對象,該Locale對象會作為一個成員屬性被轉換器持有:

    package com.thoughtworks.xstream.examples;
    import java.util.Locale;
    import com.thoughtworks.xstream.converters.Converter;
    import com.thoughtworks.xstream.converters.MarshallingContext;
    import com.thoughtworks.xstream.converters.UnmarshallingContext;
    import com.thoughtworks.xstream.io.HierarchicalStreamReader;
    import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
    public class DateConverter implements Converter {
    private Locale locale;
    public DateConverter(Locale locale) {
    super();
    this.locale = locale;
    }
    public boolean canConvert(Class clazz) {
    return false;
    }
    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    }
    public Object unmarshal(HierarchicalStreamReader reader,
    UnmarshallingContext context) {
    return null;
    }
    }

    現在,讓我們能轉換任何繼承了Calendar對象的類:

    public boolean canConvert(Class clazz) {
            return Calendar.class.isAssignableFrom(clazz);
    }
    首先,我們來將Calendar轉換成本地化的字符串:首先我們把object轉化成Calendar,得到Date對象,并使用DataFormatter來得到一個本地化的時間:

    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    Calendar calendar = (Calendar) value;
    // grabs the date
    Date date = calendar.getTime();
    // grabs the formatter
    DateFormat formatter = DateFormat.getDateInstance(DateFormat.FULL,
    this.locale);
    // formats and sets the value
    writer.setValue(formatter.format(date));
    }

    另一方面,在unmarshall方法中,我們創建了一個GregorianCalendar,得到本地化的DataFormat實例,將字符串轉換成Date對象,并賦值給GregorianCalendar。

    public Object unmarshal(HierarchicalStreamReader reader,
                    UnmarshallingContext context) {
            // creates the calendar
            GregorianCalendar calendar = new GregorianCalendar();
            // grabs the converter
            DateFormat formatter = DateFormat.getDateInstance(DateFormat.FULL,
                            this.locale);
            // parses the string and sets the time
            try {
                    calendar.setTime(formatter.parse(reader.getValue()));
            } catch (ParseException e) {
                    throw new ConversionException(e.getMessage(), e);
            }
            // returns the new object
            return calendar;
    }

    注意:
    1,記住一些DataFormat實現不是線程安全的,所以,不要讓你的轉換器持有DataFormat的引用
    2,在經過了保存和加載的過程后,該轉換器可以將其他Calendar實現轉換為GregorianCalendar。如果這不是你希望的,只需要修改canConvert方法,并在類型只有為GregorianCalendar的時候再返回true。
    現在,我們得到了下面這個轉換器:

    package com.thoughtworks.xstream.examples;
    import java.text.DateFormat;
    import java.text.ParseException;
    import java.util.Calendar;
    import java.util.Date;
    import java.util.GregorianCalendar;
    import java.util.Locale;
    import com.thoughtworks.xstream.converters.ConversionException;
    import com.thoughtworks.xstream.converters.Converter;
    import com.thoughtworks.xstream.converters.MarshallingContext;
    import com.thoughtworks.xstream.converters.UnmarshallingContext;
    import com.thoughtworks.xstream.io.HierarchicalStreamReader;
    import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
    public class DateConverter implements Converter {
    private Locale locale;
    public DateConverter(Locale locale) {
    super();
    this.locale = locale;
    }
    public boolean canConvert(Class clazz) {
    return Calendar.class.isAssignableFrom(clazz);
    }
    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    Calendar calendar = (Calendar) value;
    Date date = calendar.getTime();
    DateFormat formatter = DateFormat.getDateInstance(DateFormat.FULL,
    this.locale);
    writer.setValue(formatter.format(date));
    }
    public Object unmarshal(HierarchicalStreamReader reader,
    UnmarshallingContext context) {
    GregorianCalendar calendar = new GregorianCalendar();
    DateFormat formatter = DateFormat.getDateInstance(DateFormat.FULL,
    this.locale);
    try {
    calendar.setTime(formatter.parse(reader.getValue()));
    } catch (ParseException e) {
    throw new ConversionException(e.getMessage(), e);
    }
    return calendar;
    }
    }

    現在,我們來測試一下,創建一個main方法:
    1,創建一個calendar,
    2,創建XStream對象
    3,注冊該轉換器,并使用Brazilian Portuguese本地化對象
    4,將對象轉化成XML
    代碼如下:

    package com.thoughtworks.xstream.examples;
    import java.util.Calendar;
    import java.util.GregorianCalendar;
    import java.util.Locale;
    import com.thoughtworks.xstream.XStream;
    import com.thoughtworks.xstream.io.xml.DomDriver;
    public class DateTest {
    public static void main(String[] args) {
    // grabs the current date from the virtual machine
    Calendar calendar = new GregorianCalendar();
    // creates the xstream
    XStream xStream = new XStream(new DomDriver());
    // brazilian portuguese locale
    xStream.registerConverter(new DateConverter(new Locale("pt", "br")));
    // prints the result
    System.out.println(xStream.toXML(calendar));
    }
    }

     可以得到類似如下的結果:

    <gregorian-calendar>Sexta-feira, 10 de Fevereiro de 2006</gregorian-calendar>
    注意,我們沒有為GregorianCalendar創建任何別名,而gregorian-calendar就是默認的名字。
    下面我們來試試unmarshal 方法:

    // loads the calendar from the string
    Calendar loaded = (Calendar) xStream
                    .fromXML("<gregorian-calendar>Sexta-feira, 10 de Fevereiro de 2006</gregorian-calendar>");
    然后打印出該日期:

    // prints using the system defined locale
    System.out.println(DateFormat.getDateInstance(DateFormat.SHORT).format(
                    loaded.getTime()));
    得到的結果為:

    2/10/06
    5,復雜的轉換器:
    創建另一個例子:
    我們已經創建了兩個對象了,現在把它們組合起來:

    package com.thoughtworks.xstream.examples;
    public class Birthday {
    private Person person;
    private Calendar date;
    public Person getPerson() {
    return person;
    }
    public void setPerson(Person person) {
    this.person = person;
    }
    public Calendar getDate() {
    return date;
    }
    public void setDate(Calendar date) {
    this.date = date;
    }
    }

     要轉換該類,XStream一點問題都沒有。這里,我們實現自己的轉換器主要是為了驗證,在這里,我們想重用我們剛才的PersonConverter和CalendarConverter。canConvert仍然很簡單,不過這里,我們不需要再為每一個屬性重新寫轉換方法了,我們只需要使用已經注冊了的轉換器來完成轉換:

    package com.thoughtworks.xstream.examples;
    import java.util.Calendar;
    import com.thoughtworks.xstream.converters.Converter;
    import com.thoughtworks.xstream.converters.MarshallingContext;
    import com.thoughtworks.xstream.converters.UnmarshallingContext;
    import com.thoughtworks.xstream.io.HierarchicalStreamReader;
    import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
    public class BirthdayConverter implements Converter {
    public boolean canConvert(Class clazz) {
    return Birthday.class == clazz;
    }
    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    Birthday birthday = (Birthday)value;
    if (value.getPerson() != null) {
    writer.startNode("person");
    context.convertAnother(value.getPerson());
    writer.endNode();
    }
    if (value.getDate() != null) {
    writer.startNode("birth");
    context.convertAnother(value.getDate());
    writer.endNode();
    }
    }
    public Object unmarshal(HierarchicalStreamReader reader,
    UnmarshallingContext context) {
    Birthday birthday = new Birthday();
    while (reader.hasMoreChildren()) {
    reader.moveDown();
    if ("person".equals(reader.getNodeName())) {
    Person person = (Person)context.convertAnother(birthday, Person.class);
    birthday.setPerson(person);
    } else if ("birth".equals(reader.getNodeName())) {
    Calendar date = (Calendar)context.convertAnother(birthday, Calendar.class);
    birthday.setDate(date);
    }
    reader.moveUp();
    }
    return birthday;
    }
    }

     如果birthday實例能夠確保不會出現null值,那么我們就可以去掉marshal和unmarshal方法中對null情況的判斷,也不需要循環,而直接根據tag的名字進行解析:

    package com.thoughtworks.xstream.examples;
    import java.util.Calendar;
    import com.thoughtworks.xstream.converters.Converter;
    import com.thoughtworks.xstream.converters.MarshallingContext;
    import com.thoughtworks.xstream.converters.UnmarshallingContext;
    import com.thoughtworks.xstream.io.HierarchicalStreamReader;
    import com.thoughtworks.xstream.io.HierarchicalStreamWriter;
    public class BirthdayConverter implements Converter {
    public boolean canConvert(Class clazz) {
    return Birthday.class == clazz;
    }
    public void marshal(Object value, HierarchicalStreamWriter writer,
    MarshallingContext context) {
    Birthday birthday = (Birthday)value;
    writer.startNode("person");
    context.convertAnother(value.getPerson());
    writer.endNode();
    writer.startNode("birth");
    context.convertAnother(value.getDate());
    writer.endNode();
    }
    public Object unmarshal(HierarchicalStreamReader reader,
    UnmarshallingContext context) {
    Birthday birthday = new Birthday();
    reader.moveDown();
    Person person = (Person)context.convertAnother(birthday, Person.class);
    birthday.setPerson(person);
    reader.moveUp();
    reader.moveDown();
    Calendar date = (Calendar)context.convertAnother(birthday, Calendar.class);
    birthday.setDate(date);
    reader.moveUp();
    return birthday;
    }
    }

    posted on 2010-09-07 21:24 w@ns0ng 閱讀(517) 評論(0)  編輯  收藏 所屬分類: java

    主站蜘蛛池模板: 歪歪漫画在线观看官网免费阅读| 99免费精品视频| 国产一精品一AV一免费孕妇| 久久99国产亚洲精品观看| 国内精品久久久久影院免费| 亚洲精品免费观看| 99精品一区二区免费视频| 亚洲欧洲一区二区| 18禁成人网站免费观看| 亚洲老熟女@TubeumTV| 亚洲成在人线aⅴ免费毛片| 亚洲精品中文字幕无乱码麻豆| 久久不见久久见免费影院| 亚洲AV无码成人网站在线观看| 永久免费bbbbbb视频| 免费人成在线观看播放a| 国产亚洲精品a在线观看 | 青草青草视频2免费观看| 亚洲国产黄在线观看| 中文字幕在线免费观看视频| 亚洲国产第一页www| 韩国免费一级成人毛片| 无码一区二区三区亚洲人妻| 久久亚洲色一区二区三区| 嫩草成人永久免费观看| 激情内射亚洲一区二区三区爱妻| 免费看美女被靠到爽的视频| 未满十八私人高清免费影院| 亚洲av永久无码精品秋霞电影影院| 久草视频免费在线| 国产成人亚洲综合a∨| 久久精品亚洲视频| 最近的免费中文字幕视频| 精品97国产免费人成视频| 亚洲色图.com| 亚洲一级片免费看| 0588影视手机免费看片| 四虎精品成人免费视频| 911精品国产亚洲日本美国韩国| 成人免费在线视频| 日本高清不卡aⅴ免费网站|