新书推介:《语义网技术体系》
作者:瞿裕忠,胡伟,程龚
   XML论坛     W3CHINA.ORG讨论区     计算机科学论坛     SOAChina论坛     Blog     开放翻译计划     新浪微博  
 
  • 首页
  • 登录
  • 注册
  • 软件下载
  • 资料下载
  • 核心成员
  • 帮助
  •   Add to Google

    >> 本版讨论XSL,XSLT,XSL-FO,CSS等技术
    [返回] 计算机科学论坛XML.ORG.CN讨论区 - XML技术『 XSL/XSLT/XSL-FO/CSS 』 → 请教一个问题,高手请进 查看新帖用户列表

      发表一个新主题  发表一个新投票  回复主题  (订阅本版) 您是本帖的第 3093 个阅读者浏览上一篇主题  刷新本主题   树形显示贴子 浏览下一篇主题
     * 贴子主题: 请教一个问题,高手请进 举报  打印  推荐  IE收藏夹 
       本主题类别:     
     cgp1996 帅哥哟,离线,有人找我吗?
      
      
      等级:大二(研究C++)
      文章:43
      积分:227
      门派:XML.ORG.CN
      注册:2004/9/13

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给cgp1996发送一个短消息 把cgp1996加入好友 查看cgp1996的个人资料 搜索cgp1996在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看cgp1996的博客楼主
    发贴心情 请教一个问题,高手请进

    <?xml version="1.0"?>
    <character>
    <aa ID="1000" name="one">
      <aa1 ID="0100">
        <aaa1 ID="0100" name="two"/>
        <aaa2 ID="1000"/>
      </aa1>
      <aa2 ID="0010"/>
      <aa3 ID="1000"/>
    </aa>
    <bb ID="0010">
      <bb1 ID="0010" name="three"/>
      <bb2 ID="0001"/>
      <bb3 ID="0000"/>
    </bb>
    </character>
    转换规则为:
    1.根据ID值对元素进行分类:1000-A 0100-B 0010-C 0001-D
    2.不改变直接父子关系,如aa属于A,aa3也属于A,转换后aa3仍为aa的子元素,
    但是aaa2就转换为aa的兄弟元素
    3.若一个元素不属于任一类,则与其父元素同类,若父元素也不属于任一类,则不仅进行处理,即删掉它
    4.其它属性值不变,如name
    转换后的文档为
    <?xml version="1.0"?>
    <CHAR>
    <A>
      <aa ID="1000" name="one">
        <aa3 ID="1000"/>
      </aa>
      <aaa2 ID="1000"/>
    </A>
    <B>
      <aa1 ID="0100">
        <aaa1 ID="0100" name="two"/>
      </aa1>
    </B>
    <C>
      <aa2 ID="0010"/>
      <bb ID="0010">
        <bb1 ID="0010" name="three"/>
        <bb3 ID="0000"/>
      </bb>
    </C>
    <D>
      <bb2 ID="0001"/>
    </D>
    </CHAR>
    谢谢了

       收藏   分享  
    顶(0)
      




    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/15 23:48:00
     
     doubleG 帅哥哟,离线,有人找我吗?
      
      
      威望:7
      等级:大三(面向对象是个好东东!)
      文章:591
      积分:4119
      门派:XML.ORG.CN
      注册:2004/5/27

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给doubleG发送一个短消息 把doubleG加入好友 查看doubleG的个人资料 搜索doubleG在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看doubleG的博客2
    发贴心情 
    思路:如果ID属性满足但父节点的ID属性不为当前的值(1000,0100,0010,0001)中的一个,打出当前节点,并打出满足要求的直接子节点;如果不为当前的值,跳过。xmlspy2004下通过。可能写的稍有麻烦,呵呵。

    <?xml version="1.0" encoding="UTF-8"?>
    <xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:fo="http://www.w3.org/1999/XSL/Format">
     <xsl:output method="xml" indent="yes" encoding="UTF-8"/>
     <xsl:variable name="OrderOne">1000</xsl:variable>
     <xsl:variable name="OrderTwo">0100</xsl:variable>
     <xsl:variable name="OrderThree">0010</xsl:variable>
     <xsl:variable name="OrderFour">0001</xsl:variable>
     <xsl:template match="/">
     <xsl:element name="Char">
      <xsl:call-template name="ReOrder">
       <xsl:with-param name="IDName" select="$OrderOne"/>
       <xsl:with-param name="OrderName">A</xsl:with-param>
      </xsl:call-template>
      <xsl:call-template name="ReOrder">
       <xsl:with-param name="IDName" select="$OrderTwo"/>
       <xsl:with-param name="OrderName">B</xsl:with-param>
      </xsl:call-template>
      <xsl:call-template name="ReOrder">
       <xsl:with-param name="IDName" select="$OrderThree"/>
       <xsl:with-param name="OrderName">C</xsl:with-param>
      </xsl:call-template>
      <xsl:call-template name="ReOrder">
       <xsl:with-param name="IDName" select="$OrderFour"/>
       <xsl:with-param name="OrderName">D</xsl:with-param>
      </xsl:call-template>
     </xsl:element>
     </xsl:template>
     
     <xsl:template name="ReOrder">
      <xsl:param name="IDName"/>
      <xsl:param name="OrderName"/>
      <xsl:element name="{$OrderName}">
       <xsl:for-each select="//node()[@ID=$IDName]">
        <xsl:if test="(../@ID!=$IDName) or (name(..)='character') ">
         <xsl:call-template name="SetCurrentNode">
          <xsl:with-param name="IDName" select="$IDName"/>
          <xsl:with-param name="OrderName" select="$OrderName"/>
          <xsl:with-param name="currentNode" select="."/>
         </xsl:call-template>
         
        </xsl:if>
       </xsl:for-each>
      </xsl:element>
     </xsl:template>
     <xsl:template name="SetCurrentNode">
      <xsl:param name="IDName"/>
      <xsl:param name="OrderName"/>
      <xsl:param name="currentNode"/>
      <xsl:element name="{name($currentNode)}">
       <xsl:for-each select="$currentNode/attribute::*">
        <xsl:attribute name="{name(.)}"><xsl:value-of select="."/></xsl:attribute>
       </xsl:for-each>
       <xsl:if test="@ID=$IDName">
        <xsl:call-template name="SetChildrenNode">
          <xsl:with-param name="IDName" select="$IDName"/>
          <xsl:with-param name="OrderName" select="$OrderName"/>
          <xsl:with-param name="currentNode" select="."/>
         </xsl:call-template>
       </xsl:if>
      </xsl:element>
     </xsl:template>
     <xsl:template name="SetChildrenNode">
      <xsl:param name="IDName"/>
      <xsl:param name="OrderName"/>
      <xsl:param name="currentNode"/>
      <xsl:if test="count($currentNode/child::*)!=0">
       <xsl:for-each select="$currentNode/child::*">
        <xsl:choose>
         <xsl:when test="@ID=$IDName">
          <xsl:call-template name="SetCurrentNode">
           <xsl:with-param name="currentNode" select="."/>
          </xsl:call-template>
          <xsl:call-template name="SetChildrenNode">
           <xsl:with-param name="IDName" select="$IDName"/>
           <xsl:with-param name="OrderName" select="$OrderName"/>
           <xsl:with-param name="currentNode" select="."/>
          </xsl:call-template>
         </xsl:when>
         <xsl:otherwise>
          <xsl:if test="(@ID!=$OrderOne) and (@ID!=$OrderTwo) and (@ID!=$OrderThree) and (@ID!=$OrderFour)">
           <xsl:call-template name="SetCurrentNode">
            <xsl:with-param name="currentNode" select="."/>
           </xsl:call-template>
          </xsl:if>
          </xsl:otherwise>
        </xsl:choose>
       </xsl:for-each>
      </xsl:if>
     </xsl:template>
    </xsl:stylesheet>

    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/16 16:58:00
     
     cgp1996 帅哥哟,离线,有人找我吗?
      
      
      等级:大二(研究C++)
      文章:43
      积分:227
      门派:XML.ORG.CN
      注册:2004/9/13

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给cgp1996发送一个短消息 把cgp1996加入好友 查看cgp1996的个人资料 搜索cgp1996在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看cgp1996的博客3
    发贴心情 
    太感谢了,今天晚上我试一下
    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/16 19:38:00
     
     cgp1996 帅哥哟,离线,有人找我吗?
      
      
      等级:大二(研究C++)
      文章:43
      积分:227
      门派:XML.ORG.CN
      注册:2004/9/13

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给cgp1996发送一个短消息 把cgp1996加入好友 查看cgp1996的个人资料 搜索cgp1996在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看cgp1996的博客4
    发贴心情 
    二楼太厉害了,结果完全一样,谢谢了!不过我现在还有点看不懂你的程序,以后请你多指教。
    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/16 19:48:00
     
     doubleG 帅哥哟,离线,有人找我吗?
      
      
      威望:7
      等级:大三(面向对象是个好东东!)
      文章:591
      积分:4119
      门派:XML.ORG.CN
      注册:2004/5/27

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给doubleG发送一个短消息 把doubleG加入好友 查看doubleG的个人资料 搜索doubleG在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看doubleG的博客5
    发贴心情 
    这个程序思路不复杂,只是涉及到递归调用,所以在模版之间传参数时看起来很乱。思路可能还是没有说清楚。具体是:
    程序由四个模版组成:主模版,ReOrder,SetCurrentNode,SetChildrenNode.
    ReOrder主要是根据四个不同的ID值来整理,所以在主模版里调用了四次ReOrder。在ReOrder中主要是遍历所有拥有当前处理的ID值的节点(<xsl:for-each select="//node()[@ID=$IDName]">),检查改节点的父亲节点是否含有当前处理的ID值或者是否是根节点,如果满足上面的那两个情况就略过该节点不进行处理;否则,调用SetCurrentNode设置该节点,在SetCurrentNode中设置完当前节点后检查这个节点的子节点,如果子节点集为空则略过否则编历子节点集,如果子节点的ID不为当前处理的ID值而是其余的三个则略过,否则就处理,如果继续处理的节点不为四个中的一个则直接设置,如果还是和当前处理ID值相同则设置完节点后调用SetChildrenNode在SetChildrenNode中又调用SetCurrentNode如此递归调用。
    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/17 12:18:00
     
     cgp1996 帅哥哟,离线,有人找我吗?
      
      
      等级:大二(研究C++)
      文章:43
      积分:227
      门派:XML.ORG.CN
      注册:2004/9/13

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给cgp1996发送一个短消息 把cgp1996加入好友 查看cgp1996的个人资料 搜索cgp1996在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看cgp1996的博客6
    发贴心情 
    doubleG你好,我分析一下你的程序,我觉得SetChildrenNode模板中有一段可以去掉:
           <xsl:call-template name="SetChildrenNode">
           <xsl:with-param name="IDName" select="$IDName"/>
           <xsl:with-param name="OrderName" select="$OrderName"/>
           <xsl:with-param name="currentNode" select="."/>
           </xsl:call-template>-->
    我试了一下,结果是一样的,我不知道这一段是多余的还是另有用处,请指教。
    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/17 23:33:00
     
     doubleG 帅哥哟,离线,有人找我吗?
      
      
      威望:7
      等级:大三(面向对象是个好东东!)
      文章:591
      积分:4119
      门派:XML.ORG.CN
      注册:2004/5/27

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给doubleG发送一个短消息 把doubleG加入好友 查看doubleG的个人资料 搜索doubleG在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看doubleG的博客7
    发贴心情 
    哦,这是怕你的xml文件有更深层次啊,这个程序不仅限于你的那个xml文件,更多的层次也是可以的啊。呵呵
    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/18 15:24:00
     
     cgp1996 帅哥哟,离线,有人找我吗?
      
      
      等级:大二(研究C++)
      文章:43
      积分:227
      门派:XML.ORG.CN
      注册:2004/9/13

    姓名:(无权查看)
    城市:(无权查看)
    院校:(无权查看)
    给cgp1996发送一个短消息 把cgp1996加入好友 查看cgp1996的个人资料 搜索cgp1996在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 引用回复这个贴子 回复这个贴子 查看cgp1996的博客8
    发贴心情 
    好的,我再试一下
    点击查看用户来源及管理<br>发贴IP:*.*.*.* 2004/9/19 0:10:00
     
     GoogleAdSense
      
      
      等级:大一新生
      文章:1
      积分:50
      门派:无门无派
      院校:未填写
      注册:2007-01-01
    给Google AdSense发送一个短消息 把Google AdSense加入好友 查看Google AdSense的个人资料 搜索Google AdSense在『 XSL/XSLT/XSL-FO/CSS 』的所有贴子 访问Google AdSense的主页 引用回复这个贴子 回复这个贴子 查看Google AdSense的博客广告
    2025/6/24 0:46:38

    本主题贴数8,分页: [1]

    管理选项修改tag | 锁定 | 解锁 | 提升 | 删除 | 移动 | 固顶 | 总固顶 | 奖励 | 惩罚 | 发布公告
    W3C Contributing Supporter! W 3 C h i n a ( since 2003 ) 旗 下 站 点
    苏ICP备05006046号《全国人大常委会关于维护互联网安全的决定》《计算机信息网络国际联网安全保护管理办法》
    4,469.971ms