0

问题

我正在解决一个问题,我需要获取 JSON 输入文件并转换为 XML 文件。我在下面提供了一个我正在处理的示例。

在 JSON 中:

"playerStats": [
    { "jerseyNumber": "23",  "fgPercentage": 60, "plusMinus": "plus" },
    { "jerseyNumber": "24",  "fgPercentage": 40, "plusMinus": "minus" }
] }

在 XML 中:

<BallerStats>
    <BallerStat>
        <Baller><BallerJersey>23</BallerJersey><Type>Jersey</Type></Baller>
        <fgPercentage><Type>PERCENT</Type><Value>60</Value></fgPercentage>
    </BallerStat>
     <BallerStat>
        <Baller><BallerJersey>23</BallerJersey><Type>Jersey</Type></Baller>
        <fgPercentage><Type>PERCENT</Type><Value>60</Value></fgPercentage>
    </BallerStat>
</BallerStats>

如您所见,这不是 1 比 1 的比率含义,在 JSON 中,我们将 fgPercentage 表示为 60,但在 xml 中,我们用“值”和“类型”分隔它

某些标签名称也不同。在 JSON 中,我们称它们为“playerStats”,在 XML 中,我们称其为等价标签“BallerStats”

解决方案

请记住,除了 playerstats 或 fanstats 等 playerstats 之外,JSON 文件可能还有许多其他字段,但我们只关心 playerstats

以下是我想出的,但我可能又错了。

  1. 扫描 Json 并寻找“playerStats”
  2. 如果没有找到,什么也不做。
  3. 如果找到,则获取有价值的信息,例如 jerseyNumber 、 fgPercentage,忽略 plusMinus 并将它们存储在具有这些值的模板类的对象中。
  4. 然后使用 Object 生成适当的 XML 标记。

我不确定我的方法是否有效。我很想听听建议,我在 Java 中这样做,所以请随意参考任何可靠和流行的库。如果您提供代码片段,我希望看到所有方法,甚至更好。

4

2 回答 2

2

一种选择是json-to-xml()在 XSLT 3.0 中使用。

您需要一个 XSLT 3.0 处理器;我在下面的示例中使用了Saxon-HE 9.8

您可以将 JSON 作为参数传递。

的结果json-to-xml()将如下所示:

<map xmlns="http://www.w3.org/2005/xpath-functions">
   <array key="playerStats">
      <map>
         <string key="jerseyNumber">23</string>
         <number key="fgPercentage">60</number>
         <string key="plusMinus">plus</string>
      </map>
      <map>
         <string key="jerseyNumber">24</string>
         <number key="fgPercentage">40</number>
         <string key="plusMinus">minus</string>
      </map>
   </array>
</map>

您可以处理该 XML 以获得您的目标 XML。

例子...

爪哇

package so.test1;

import java.io.File;
import java.io.OutputStream;
import javax.xml.transform.stream.StreamSource;
import net.sf.saxon.s9api.XsltTransformer;
import net.sf.saxon.s9api.Processor;
import net.sf.saxon.s9api.QName;
import net.sf.saxon.s9api.SaxonApiException;
import net.sf.saxon.s9api.Serializer;
import net.sf.saxon.s9api.XdmAtomicValue;
import net.sf.saxon.s9api.XsltCompiler;
import net.sf.saxon.s9api.XsltExecutable;

/**
 *
 * @author dhaley
 *
 */
public class SOTest1 {

    public static void main(String[] args) throws SaxonApiException {
        final String XSLT_PATH = "src/so/test1/test.xsl";
        final String JSON = "{\"playerStats\": [\n" +
                             "    {\"jerseyNumber\": \"23\", \"fgPercentage\": 60, \"plusMinus\": \"plus\"},\n" +
                             "    {\"jerseyNumber\": \"24\", \"fgPercentage\": 40, \"plusMinus\": \"minus\"}\n" +
                             "]}";

        OutputStream outputStream = System.out;        
        Processor processor = new Processor(false);        
        Serializer serializer = processor.newSerializer();
        serializer.setOutputStream(outputStream);        
        XsltCompiler compiler = processor.newXsltCompiler();
        XsltExecutable executable = compiler.compile(new StreamSource(new File(XSLT_PATH)));        
        XsltTransformer transformer = executable.load();
        transformer.setInitialTemplate(new QName("init")); //<-- SET INITIAL TEMPLATE
        transformer.setParameter(new QName("json"), new XdmAtomicValue(JSON)); //<-- PASS JSON IN AS PARAM
        transformer.setDestination(serializer);
        transformer.transform();
    }

}

XSLT 3.0 (test.xsl)

<xsl:stylesheet version="3.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
  xpath-default-namespace="http://www.w3.org/2005/xpath-functions">
  <xsl:output indent="yes"/>
  <xsl:strip-space elements="*"/>

  <xsl:param name="json"/>

  <xsl:mode on-no-match="shallow-copy"/>

  <xsl:template name="init">
    <!--Only process playerStats-->
    <xsl:apply-templates select="json-to-xml($json)//array[@key='playerStats']"/>
  </xsl:template>

  <xsl:template match="array">
    <BallerStats>
      <xsl:apply-templates/>
    </BallerStats>
  </xsl:template>

  <xsl:template match="map">
    <BallerStat>
      <xsl:apply-templates/>
    </BallerStat>
  </xsl:template>

  <xsl:template match="*[@key='jerseyNumber']">
    <Baller>
      <BallerJersey xsl:expand-text="true">{.}</BallerJersey>
      <Type>Jersey</Type>
    </Baller>
  </xsl:template>

  <xsl:template match="*[@key='fgPercentage']">
    <fgPercentage>
      <Type>PERCENT</Type>
      <Value xsl:expand-text="true">{.}</Value>
    </fgPercentage>
  </xsl:template>

  <xsl:template match="*[@key=('plusMinus')]"/>

</xsl:stylesheet>

输出(标准输出)

<?xml version="1.0" encoding="UTF-8"?>
<BallerStats>
   <BallerStat>
      <Baller>
         <BallerJersey>23</BallerJersey>
         <Type>Jersey</Type>
      </Baller>
      <fgPercentage>
         <Type>PERCENT</Type>
         <Value>60</Value>
      </fgPercentage>
   </BallerStat>
   <BallerStat>
      <Baller>
         <BallerJersey>24</BallerJersey>
         <Type>Jersey</Type>
      </Baller>
      <fgPercentage>
         <Type>PERCENT</Type>
         <Value>40</Value>
      </fgPercentage>
   </BallerStat>
</BallerStats>
于 2018-03-13T19:46:06.917 回答
0

Underscore-java库可以将 json 转换为 xml。我是项目的维护者。活生生的例子

import com.github.underscore.U;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

public class MyClass {
    @SuppressWarnings("unchecked")
    public static void main(String args[]) {
        String json = "{\"playerStats\": [\n"
        + "{ \"jerseyNumber\": \"23\",  \"fgPercentage\": 60, \"plusMinus\": \"plus\" },"
        + "{ \"jerseyNumber\": \"24\",  \"fgPercentage\": 40, \"plusMinus\": \"minus\" }"
        + "] }";
    String xml = "<BallerStats>"
        + "<BallerStat>"
        + "    <Baller><BallerJersey>23</BallerJersey><Type>Jersey</Type></Baller>"
        + "    <fgPercentage><Type>PERCENT</Type><Value>60</Value></fgPercentage>"
        + "</BallerStat>"
        + "</BallerStats>";

    List<Map<String, Object>> jsonArray = U.get((Map<String, Object>) U.fromJson( json ), "playerStats");
    Map<String, Object> map = new LinkedHashMap<>();
    List<Map<String, Object>> ballerStats = new ArrayList<>();
    Map<String, Object> ballerStat = new LinkedHashMap<>();
    map.put("BallerStats", ballerStat);
    ballerStat.put("BallerStat", ballerStats);
    for (Map<String, Object> jsonItem : jsonArray) {
        Map<String, Object> newBallerStat = (Map<String, Object>) ((Map<String, Object>) ((Map<String, Object>) U.fromXml( xml )).get("BallerStats")).get("BallerStat");
        ((Map<String, Object>) newBallerStat.get("Baller")).put("BallerJersey", jsonItem.get("jerseyNumber"));
        ((Map<String, Object>) newBallerStat.get("fgPercentage")).put("Value", jsonItem.get("fgPercentage"));
        ballerStats.add(newBallerStat);
    }
    System.out.println(U.toXml(map)); 
    }
}
于 2018-09-01T03:47:52.200 回答