问题
I have an xml which I must transform it to another structure of xml. I tried many ways but no success. I need to use xslt 1.0. I asked a question but the format is changed after I asked.
input:
<?xml version="1.0" encoding="ISO-8859-1"?>
<PersonBody>
<Person>
<D>Name</D>
<D>Surname</D>
<D>Id</D>
</Person>
<PersonValues>
<D>Michael</D>
<D>Jackson</D>
<D>01</D>
</PersonValues>
<PersonValues>
<D>James</D>
<D>Bond</D>
<D>007</D>
</PersonValues>
<PersonValues>
<D>Kobe</D>
<D>Bryant</D>
<D>24</D>
</PersonValues>
</PersonBody>
Required output:
<?xml version="1.0" encoding="ISO-8859-1"?>
<PersonBody>
<Persons>
<Person>
<Name>Michael</Name>
<Surname>Jackson</Surname>
<Id>1</Id>
</Person>
<Person>
<Name>James</Name>
<Surname>Bond</Surname>
<Id>007</Id>
</Person>
<Person>
<Name>Kobe</Name>
<Surname>Bryant</Surname>
<Id>24</Id>
</Person>
</Persons>
</PersonBody>
回答1:
This should do it:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes" omit-xml-declaration="yes"/>
<xsl:key name="kColumnName" match="Person/*"
use="count(preceding-sibling::*)" />
<xsl:template match="@* | node()">
<xsl:copy>
<xsl:apply-templates select="@* | node()"/>
</xsl:copy>
</xsl:template>
<xsl:template match="/*">
<xsl:copy>
<Persons>
<xsl:apply-templates select="PersonValues" />
</Persons>
</xsl:copy>
</xsl:template>
<xsl:template match="PersonValues">
<Person>
<xsl:apply-templates select="*" />
</Person>
</xsl:template>
<xsl:template match="PersonValues/*">
<xsl:element name="{key('kColumnName', position() - 1)}">
<xsl:apply-templates />
</xsl:element>
</xsl:template>
</xsl:stylesheet>
When run on your sample input, the result is:
<PersonBody>
<Persons>
<Person>
<Name>Michael</Name>
<Surname>Jackson</Surname>
<Id>01</Id>
</Person>
<Person>
<Name>James</Name>
<Surname>Bond</Surname>
<Id>007</Id>
</Person>
<Person>
<Name>Kobe</Name>
<Surname>Bryant</Surname>
<Id>24</Id>
</Person>
</Persons>
</PersonBody>
来源:https://stackoverflow.com/questions/16192234/how-to-transform-xml-to-requested-one