2010-05-05 19 views
5

मैं एक्सएसएलटी सीखने की कोशिश कर रहा हूं लेकिन उदाहरण के लिए मैं सबसे अच्छा काम करता हूं। मैं स्कीमा परिवर्तन के लिए एक छोटी स्कीमा करना चाहता हूँ। मैं इस परिवर्तन को केवल एक पास में कैसे कर सकता हूं (मेरा वर्तमान समाधान दो पास का उपयोग करता है और ग्राहकों के मूल आदेश को खो देता है)?एकल के लिए एकल नोड्स का चयन कैसे करें XSLT

से:

<?xml version="1.0" encoding="UTF-8"?> 
<sampleroot> 

<badcustomer> 
    <name>Donald</name> 
    <address>Hong Kong</address> 
    <age>72</age> 
</badcustomer> 

<goodcustomer> 
    <name>Jim</name> 
    <address>Wales</address> 
    <age>22</age> 
</goodcustomer> 

<goodcustomer> 
    <name>Albert</name> 
    <address>France</address> 
    <age>51</age> 
</goodcustomer> 

</sampleroot> 

करने के लिए:

<?xml version="1.0" encoding="UTF-8"?> 
<records> 

<record id="customer"> 
    <name>Donald</name> 
    <address>Hong Kong</address> 
    <age>72</age> 
    <customertype>bad</customertype> 
</record> 

<record id="customer"> 
    <name>Jim</name> 
    <address>Wales</address> 
    <age>22</age> 
    <customertype>good</customertype> 
</record> 

<record id="customer"> 
    <name>Albert</name> 
    <address>France</address> 
    <age>51</age> 
    <customertype>good</customertype> 
</record> 

</records> 

मैं पहले से ही यह एक बुरा तरह से हल किया (मैं ग्राहकों के आदेश खो देते हैं और मुझे लगता है कि मैं फ़ाइल को पार्स करने के लिए है कि कई बार:

<?xml version='1.0'?> 
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 

    <xsl:output method="xml" indent="yes"/> 
    <xsl:template match="/sampleroot"> 

    <records> 

     <xsl:for-each select="goodcustomer"> 
      <record id="customer"> 
       <name><xsl:value-of select="name" /></name> 
       <address><xsl:value-of select="address" /></address> 
       <age><xsl:value-of select="age" /></age> 
       <customertype>good</customertype> 
      </record> 
     </xsl:for-each> 

     <xsl:for-each select="badcustomer"> 
      <record id="customer"> 
       <name><xsl:value-of select="name" /></name> 
       <address><xsl:value-of select="address" /></address> 
       <age><xsl:value-of select="age" /></age> 
       <customertype>bad</customertype> 
      </record> 
     </xsl:for-each> 

    </records> 
    </xsl:template> 
</xsl:stylesheet> 

कृपया कोई मुझे सही एक्सएसएलटी निर्माण के साथ मदद कर सकता है जहां मुझे केवल एक ही पार्स (प्रत्येक के लिए केवल एक) का उपयोग करना होगा?

धन्यवाद,

क्रिस

+0

अच्छा प्रश्न क्रिस (+1)। एक अच्छे समाधान के लिए मेरा जवाब देखें। :) –

उत्तर

6

यह एक अच्छा XSLT अभ्यास संभव जितना <xsl:for-each> का उपयोग कर से बचने के लिए है।

यहाँ, एक सरल उपाय है इस सिद्धांत का उपयोग कर:

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"> 
<xsl:output omit-xml-declaration="yes" indent="yes"/> 

<xsl:template match="node()|@*"> 
    <xsl:copy> 
    <xsl:apply-templates select="node()|@*"/> 
    </xsl:copy> 
</xsl:template> 

<xsl:template match="/*"> 
    <records> 
    <xsl:apply-templates/> 
    </records> 
</xsl:template> 

<xsl:template match="badcustomer | goodcustomer"> 
    <record> 
    <xsl:apply-templates/> 
    <customertype> 
    <xsl:value-of select="substring-before(name(), 'customer')"/> 
    </customertype> 
    </record> 
</xsl:template> 
</xsl:stylesheet> 

ध्यान दें करो:

  1. केवल टेम्पलेट्स और <xsl:apply-templates> किया जाता है।

  2. पहचान नियम का उपयोग और जहां भी आवश्यक हो, ओवरराइडिंग। यह सबसे मौलिक एक्सएसएलटी डिजाइन पैटर्न में से एक है।

+0

धन्यवाद, क्या मैं जानकारी के एक अंतिम टुकड़े के लिए पूछ सकता हूं। अगर मैं मूल एक्सएमएल स्कीमा से विशेषताओं से गुजरना चाहता हूं, तो मैं काम करने के लिए xslt को कैसे समायोजित करूं? <नाम myattribute = "attributevalue"> डोनाल्ड <पते myattribute2 = "attributevalue2"> हांगकांग Chris

+0

@Chris: कृपया, एक नया सवाल के रूप में इस पूछते हैं, ठीक से साथ स्वरूपित कोड/एक्सएमएल। इसके अलावा, आप "स्कीमा" शब्द का गलत इस्तेमाल कर रहे हैं। आप वास्तव में "स्रोत XML दस्तावेज़" या उस दस्तावेज़ प्रकार के लिए स्कीमा के उदाहरण के लिए रेफर कर रहे हैं। –

+0

जानकारी के लिए धन्यवाद और "स्कीमा" के गलत उपयोग को सही करने के लिए। मुझे पता चला कि फॉलो-अप प्रश्न कैसे हल करें ताकि मैं अब एक नया प्रश्न नहीं उठाऊंगा। – Chris

संबंधित मुद्दे