首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >如何使用PHP转换XML结构: simpleXMLElement

如何使用PHP转换XML结构: simpleXMLElement
EN

Stack Overflow用户
提问于 2014-02-18 17:47:52
回答 1查看 78关注 0票数 0

我有以下xml:

代码语言:javascript
运行
复制
<?xml version="1.0" encoding="UTF-8"?>

<product version="1.4" productId="{97550402-c98f-4b42-b7e7-521961e2700b}" groupId="ACER" codeId="NX.M81EX.080">
    <name>Notebook Acer Aspire XYZ</name>
    <vendor>Acer</vendor>
    <propertyGroup propertyGroupId="{3f2c48a7-b185-4fad-bd20-7d0c50502645}">
            <propertyGroupName>Product : Common</propertyGroupName>
            <property propertyId="2" type="Text" name="Part No.">
                    <value valueId="0">NX.M81EX.080</value>
            </property>
            <property propertyId="3" type="Text" name="Model No.">
                <value valueId="0">Acer XYZ</value>
            </property>
    </propertyGroup>
    <propertyGroup propertyGroupId="{869eec69-8f70-40ac-a41d-c8958d743ad3}">
            <propertyGroupName>Notebook</propertyGroupName>
            <property propertyId="2" type="Enum" name="CPU">
                    <value valueId="337">CPU XYZ</value>
            </property>
            <property propertyId="10" type="Enum" name="Graphics">
                    <value valueId="242">Graphics XYZ</value>
            </property>
            <property propertyId="5" type="Enum" name="RAM">
                    <value valueId="6">RAM XYZ</value>
            </property>
            <property propertyId="11" type="Enum" name="HDD">
                    <value valueId="34">HDD XYZ</value>
            </property>
    </propertyGroup>
    <file type="Datasheet" description="">http://www.site.com/xyz.pdf</file>
    <image type="other">http://www.site.com/abc.jpg</image>
    <image type="other">http://www.site.com/xyz.jpg</image>
</product>

我正在使用PHP: simpleXMLElement,并且必须将这个XML组织成如下所示:

代码语言:javascript
运行
复制
<?xml version="1.0" encoding="UTF-8"?>
<feed>
    <products>
        <product>
            <codeId>NX.M81EX.080</codeId>
            <name>Notebook Acer Aspire XYZ</name>
            <vendor>Acer</vendor>
            <model>Acer XYZ</model>
            <category>Notebook</category>
            <CPU>CPU XYZ</CPU>
            <graphics>Graphics XYZ</graphics>
            <RAM>RAM XYZ</RAM>
            <HDD>HDD XYZ</HDD>
            <datasheet>http://www.site.com/xyz.pdf</datasheet>
            <image>http://www.site.com/xyz.jpg</image>
        </product>
    </products>
</feed>

我尝试了几个递归函数,但都没有成功。我检索属性的值,但无法检索属性名称。你能帮帮我吗。提前感谢:)

EN

回答 1

Stack Overflow用户

发布于 2014-02-18 19:04:18

您可以使用如下的XSLT样式表:

代码语言:javascript
运行
复制
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    xmlns:xs="http://www.w3.org/2001/XMLSchema"
    exclude-result-prefixes="xs"
    version="1.0">

    <xsl:output indent="yes"/>
    <xsl:strip-space elements="*"/>

    <xsl:template match="product">
        <feed>
            <products>
                <product>
                    <xsl:apply-templates />
                </product>
            </products>
        </feed>
    </xsl:template>

    <xsl:template match="name|vendor">
        <xsl:copy-of select="."/>
    </xsl:template>

    <xsl:template match="propertyGroup">
        <xsl:choose>
            <xsl:when test="propertyGroupName = 'Product : Common'">
                <xsl:apply-templates select="property" mode="common"/>
            </xsl:when>
            <xsl:otherwise>
                <category><xsl:value-of select="propertyGroupName"/></category>
                <xsl:apply-templates select="property"/>
            </xsl:otherwise>
        </xsl:choose>
    </xsl:template>

    <xsl:template match="property" mode="common">
            <xsl:if test="@propertyId=2">
                <codeId><xsl:value-of select="."/></codeId>
            </xsl:if>
            <xsl:if test="@propertyId=1">
                <model><xsl:value-of select="."/></model>
            </xsl:if>
    </xsl:template>

    <xsl:template match="property">
        <xsl:element name="{@name}">
            <xsl:value-of select="value"/>
        </xsl:element>
    </xsl:template>

    <xsl:template match="file[@type='Datasheet']">
        <datasheet><xsl:value-of select="."/></datasheet>
    </xsl:template>

    <xsl:template match="image">
        <xsl:copy>
            <xsl:value-of select="."/>
        </xsl:copy>
    </xsl:template>

    <xsl:template match="*|text()"/>
</xsl:stylesheet>

这将把上面的数据转换成下面的结果:

代码语言:javascript
运行
复制
<?xml version="1.0" encoding="UTF-8"?>
<feed>
   <products>
      <product>
         <name>Notebook Acer Aspire XYZ</name>
         <vendor>Acer</vendor>
         <codeId>NX.M81EX.080</codeId>
         <category>Notebook</category>
         <CPU>CPU XYZ</CPU>
         <Graphics>Graphics XYZ</Graphics>
         <RAM>RAM XYZ</RAM>
         <HDD>HDD XYZ</HDD>
         <datasheet>http://www.site.com/xyz.pdf</datasheet>
         <image>http://www.site.com/abc.jpg</image>
         <image>http://www.site.com/xyz.jpg</image>
      </product>
   </products>
</feed>

您可以加载XSL样式表、源XML并使用以下命令运行XSLT处理程序:

代码语言:javascript
运行
复制
$processor = new XsltProcessor();
$xsl = new DomDocument;
$xsl->load('stylesheet.xsl');
$processor->importStylesheet($xsl);

$source = new DomDocument;
$source->load('your-xml-file.xml');

$result = $processor->transformToXML($source));

如果需要,您可以编辑XSL并使其适应更大范围的源文档。您的源有两个图像,因此结果生成了两个图像标记。如果您只想要最后一个图像,请将模板匹配更改为image[last()]

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/21849808

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档