1

これに似た XML をアンマーシャリングするために、JAXB アノテーションをクラスに追加しようとしています (Java Bean を XML にマーシャリングする必要はないことに注意してください...):

    <fixture_statistics id="3812596">
      <home_team_stats id="2">
        <id>2</id>
        <tackles>58</tackles>
        <possession>1868</possession>
        <territory>2603</territory>
        <minutes_in_22>1316</minutes_in_22>
        ...
      </home_team_stats>
      <guest_team_stats id="21061">
        <id>21061</id>
        <tackles>20</tackles>
        <possession>3114</possession>
        <territory>2379</territory>
        <minutes_in_22>1171</minutes_in_22>
        ...
      </guest_team_stats>
      <home_player_1 id="2306143" teamid="2">
        <id>2306143</id>
        <tackles>3</tackles>
        <metres_gained>38</metres_gained>
        ...
      </home_player_1>
      <home_player_1 id="2306143" teamid="2">
        <id>2306143</id>
        <tackles>3</tackles>
        <metres_gained>38</metres_gained>
        ...
      </home_player_1>
      <home_player_1 id="2306143" teamid="2">
        <id>2306143</id>
        <tackles>3</tackles>
        <metres_gained>38</metres_gained>
        ...
      </home_player_1>
      ...
      <guest_player_1 id="2306143" teamid="2">
        <id>2306143</id>
        <tackles>3</tackles>
        <metres_gained>38</metres_gained>
        ...
      </guest_player_1>
      <guest_player_2 id="2306143" teamid="2">
        <id>2306143</id>
        <tackles>3</tackles>
        <metres_gained>38</metres_gained>
        ...
      </guest_player_2>
      <guest_player_3 id="2306143" teamid="2">
        <id>2306143</id>
        <tackles>3</tackles>
        <metres_gained>38</metres_gained>
        ...
      </guest_player_3>
      ...
</fixture_statistics>

*この質問のためにコピーして貼り付けたので、要素の値の一部を無視してください...

「fixture_statistics」、「home_team_stats」、および「guest_team_stats」要素をそれぞれのクラスにマッピングし、これらの要素を正しく非整列化できましたが、「home_player_n」要素と「guest_player_n」要素に問題があります. これらの要素内にあるプロパティを含むクラスを作成しましたが、要素の名前が「home_player_1」から「home_player_22」まで、ゲスト プレイヤーでも同じであるという事実を処理する方法がわかりません。

ここに私のフィクスチャ統計クラスと私のフィクスチャ プレーヤー統計クラスのサンプルを示します。

@XmlRootElement(name = "fixture_statistics")
@XmlAccessorType(XmlAccessType.FIELD)
public class FixtureStatistics {

    private Collection<FixturePlayerStatistics> homeTeamPlayerStatistics = new ArrayList<>();

    private Collection<FixturePlayerStatistics> guestTeamPlayerStatistics = new ArrayList<>();
}

@XmlAccessorType(XmlAccessType.FIELD)
public class FixturePlayerStatistics {
    @XmlElement(name="id")
    private Long playerId;
    private Integer tackles;
    @XmlElement(name="metres_gained")
    private Integer metresGained;
}

FixturePlayerStatistics クラスでは、XMlRootElement 注釈を追加できません。要素が 44 個の文字列のうちの 1 つである可能性があるためです。また、FixtureStatistics クラスのコレクションから注釈を一時的に削除しました。@XmlElementRef を使用して、考えられるすべての要素名を指定しようとしましたが、まだうまくいきませんでした。また、XML を変更することもできず、操作するスキーマもありません。API 呼び出しからの結果の XML だけです。

4

1 に答える 1

2

このユースケースをサポートするためのいくつかの異なるオプションがあります。しかし、一般的には、インデックスが要素名に組み込まれる状況を避けることをお勧めします。

オプション #1 - 個別のフィールド/プロパティ

このユース ケースを処理する 1 つの方法は、22 人のゲスト プレーヤーと 22 人のホーム プレーヤーのそれぞれに個別のフィールド/プロパティを用意することです。

package forum13219778;

import javax.xml.bind.annotation.*;

@XmlRootElement(name = "fixture_statistics")
@XmlAccessorType(XmlAccessType.FIELD)
public class FixtureStatistics {

    FixturePlayerStatistics guest_player_1;
    FixturePlayerStatistics guest_player_2;
    FixturePlayerStatistics guest_player_3;
    ...
    FixturePlayerStatistics guest_player_22;

    FixturePlayerStatistics home_player_1;
    FixturePlayerStatistics home_player_2;
    FixturePlayerStatistics home_player_3;
    ...
    FixturePlayerStatistics home_player_22;     
}

オプション #2 - SAXXMLFilterを使用して _# SUFFIX を削除する

ユースケースがアンマーシャリングのみを扱う場合は、SAX を使用XMLFilterして各要素の一意のサフィックスを取り除き、JAXB アノテーションで および に単純にマップできhome_playerますguest_player。例については、XMLFilter次を参照してください。


オプション #3 - USE@XmlElementRefsObjectFactory

フィクスチャ統計

@XmlElementRefs/注釈を使用するには@XmlElementRef、コレクションを変更して のインスタンスを保持する必要がありますJAXBElement<FixturePlayerStatistics>JAXBElement要素名情報を保持するために使用されます。

package forum13219778;

import java.util.*;

import javax.xml.bind.JAXBElement;
import javax.xml.bind.annotation.*;

@XmlRootElement(name = "fixture_statistics")
@XmlAccessorType(XmlAccessType.FIELD)
public class FixtureStatistics {

    @XmlElementRefs({ 
        @XmlElementRef(name="home_player_1"),
        @XmlElementRef(name="home_player_2"),
        @XmlElementRef(name="home_player_3")
    })
    private Collection<JAXBElement<FixturePlayerStatistics>> homeTeamPlayerStatistics = new ArrayList<>();

    @XmlElementRefs({ 
        @XmlElementRef(name="guest_player_1"),
        @XmlElementRef(name="guest_player_2"),
        @XmlElementRef(name="guest_player_3")
    })
    private Collection<JAXBElement<FixturePlayerStatistics>> guestTeamPlayerStatistics = new ArrayList<>();

}

ObjectFactory

と組み合わせて、注釈@XmlElementRefを使用してルート要素を宣言する必要があります。@XmlElementDeclこれは、 の注釈が付けられたオブジェクト ファクトリ クラスを介して行われます@XmlRegistry

package forum13219778;

import javax.xml.bind.JAXBElement;
import javax.xml.bind.annotation.*;
import javax.xml.namespace.QName;

@XmlRegistry
public class ObjectFactory {

    @XmlElementDecl(name = "home_player_1")
    public JAXBElement<FixturePlayerStatistics> createHomePlayer1(FixturePlayerStatistics player) {
        return new JAXBElement<FixturePlayerStatistics>(new QName("home_player_1"), FixturePlayerStatistics.class, player);
    }

    @XmlElementDecl(name = "home_player_2")
    public JAXBElement<FixturePlayerStatistics> createHomePlayer2(FixturePlayerStatistics player) {
        return new JAXBElement<FixturePlayerStatistics>(new QName("home_player_2"), FixturePlayerStatistics.class, player);
    }

    @XmlElementDecl(name = "home_player_3")
    public JAXBElement<FixturePlayerStatistics> createHomePlayer3(FixturePlayerStatistics player) {
        return new JAXBElement<FixturePlayerStatistics>(new QName("home_player_3"), FixturePlayerStatistics.class, player);
    }

    @XmlElementDecl(name = "guest_player_1")
    public JAXBElement<FixturePlayerStatistics> createGuestPlayer1(FixturePlayerStatistics player) {
        return new JAXBElement<FixturePlayerStatistics>(new QName("guest_player_1"), FixturePlayerStatistics.class, player);
    }


    @XmlElementDecl(name = "guest_player_2")
    public JAXBElement<FixturePlayerStatistics> createGuestPlayer2(FixturePlayerStatistics player) {
        return new JAXBElement<FixturePlayerStatistics>(new QName("guest_player_2"), FixturePlayerStatistics.class, player);
    }

    @XmlElementDecl(name = "guest_player_3")
    public JAXBElement<FixturePlayerStatistics> createGuestPlayer3(FixturePlayerStatistics player) {
        return new JAXBElement<FixturePlayerStatistics>(new QName("guest_player_3"), FixturePlayerStatistics.class, player);
    }

}

デモ

package forum13219778;

import java.io.File;
import javax.xml.bind.*;

public class Demo {

    public static void main(String[] args) throws Exception {
        JAXBContext jc = JAXBContext.newInstance(FixtureStatistics.class, ObjectFactory.class);

        Unmarshaller unmarshaller = jc.createUnmarshaller();
        File xml = new File("src/forum13219778/input.xml");
        FixtureStatistics fs = (FixtureStatistics) unmarshaller.unmarshal(xml);

        Marshaller marshaller = jc.createMarshaller();
        marshaller.setProperty(Marshaller.JAXB_FORMATTED_OUTPUT, true);
        marshaller.marshal(fs,  System.out);
    }

}
于 2012-11-04T19:35:40.237 に答える