草庐IT

xml - 修改节点和所有子节点中属性的子字符串

coder 2024-06-26 原文

我已经进行了大量搜索,但还没有完全能够使用 XSLT 提出任何建议。我正在尝试采用 XML 模板(对于 McPAT,部分如下所示)指示系统规范并复制 component id="system.core0"name="core0" 节点,这样我就可以拥有 N 核心节点。每个都必须将“system.core#”作为 ID,将“core#”作为名称,# 是核心编号,0-n。

我还必须在任何后代节点中复制它,例如下面的 system.core0.itlb 节点。

更进一步,在任何具有“config.system.cpu.clock”值的后代节点中,我必须将节点号附加到“cpu”。

最后,我要覆盖 param name="number_of_cores"value="1" 在系统下 param name="number_of_cores"value="n" 并改变 param name="homogenous_cores"value="1"param name="homogenous_cores"value="0"

XML 当前看起来像这样:

<?xml version="1.0" ?>
<component id="root" name="root">
    <component id="system" name="system">
         <param name="number_of_cores" value="1"/>
         <param name="homogeneous_cores" value="1"/>
         <param name="number_of_L1Directories" value="0"/>
         <param name="number_of_L2Directories" value="0"/>
         <param name="number_of_L2s" value="1"/> 
         <param name="Private_L2" value="0"/>
         <param name="number_of_L3s" value="0"/> 
         <param name="number_of_NoCs" value="1"/>
         ...
         <component id="system.core0" name="core0">
             <!-- Core property -->
             <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
             <param name="opt_local" value="1"/>      
             <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

             ...
             <component id="system.core0.itlb" name="itlb">
                 <param name="number_entries" value="{config.system.cpu.itb.size}"/>
                 <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
                 ...
             </component>
         </component>
     </component>
 </component>

这里有好几行。感谢 SO,我已经复制了 system.core0 节点 N 次。我会发布链接,但找不到页面。我确实知道 Dimitre Novachev 给出了我遵循的答案,我想感谢他在这方面的帮助。到目前为止,XSLT 样式表如下所示:

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

    <xsl:param name="n" select="5"/>

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

    <xsl:template match="component[@id='system']/component[@name='core0']">
        <xsl:call-template name="copyNtimes">
            <xsl:with-param name="n" select="$n"/>
            <xsl:with-param name="core_num" select="1"/>
        </xsl:call-template>
    </xsl:template>

    <xsl:template name="copyNtimes">
        <xsl:param name="n" select="0"/>
        <xsl:param name="core_num" select="1"/>

        <xsl:if test="$n > 0">
            <xsl:copy>
                <xsl:apply-templates select="@*|node()"/>
            </xsl:copy>
            <xsl:text>
            </xsl:text>
            <xsl:call-template name="copyNtimes">
                <xsl:with-param name="n" select="$n -1"/>
                <xsl:with-param name="core_num" select="$core_num+1"/>
            </xsl:call-template>
        </xsl:if>
    </xsl:template>

</xsl:stylesheet>

所以在通过 xsltproc 运行它的最后,我将带有 system.core0 的原始文件复制了 N 次。剩下的事情让我发疯了好几天。我如何着手更改我创建的每个新节点的核心编号,并将其反射(reflect)在所有子节点中?任何帮助都会有所帮助,即使它不是代码。我玩过制作新模板和使用副本,但似乎没有什么能让我更接近。

我还可以将这一切引入另一种语言,例如 Perl,在那里我可以运行 XSLT 样式表来复制更改并手动修改属性字符串(如果这样会更容易的话)。我知道 Perl 有一些非常好的 XML 和 XSLT 模块。不过,我觉得 XSLT 应该能够做到这一点,而且由于我是新手,所以这种格式让我很反感。

编辑: 我需要的示例输出是这样的:

<?xml version="1.0" ?>
    <component id="root" name="root">
        <component id="system" name="system">
             <param name="number_of_cores" value="3"/>
             <param name="homogeneous_cores" value="0"/>
             <param name="number_of_L1Directories" value="0"/>
             <param name="number_of_L2Directories" value="0"/>
             <param name="number_of_L2s" value="1"/> 
             <param name="Private_L2" value="0"/>
             <param name="number_of_L3s" value="0"/> 
             <param name="number_of_NoCs" value="1"/>
             <!--...-->
             <component id="system.core0" name="core0">
                 <!-- Core property -->
                 <param name="clock_rate" value="{1e-6/config.system.cpu0.clock*1e12}"/>
                 <param name="opt_local" value="1"/>      
                 <stat name="total_instructions" value="{stats.system.cpu0.iq.iqInstsIssued}"/>
                 <!--...-->
                 <component id="system.core0.itlb" name="itlb">
                     <param name="number_entries" value="{config.system.cpu0.itb.size}"/>
                     <stat name="total_accesses" value="{stats.system.cpu0.itb.fetch_accesses}"/>
                     ...
                 </component>
             </component>
             <component id="system.core1" name="core1">
                 <!-- Core property -->
                 <param name="clock_rate" value="{1e-6/config.system.cpu1.clock*1e12}"/>
                 <param name="opt_local" value="1"/>      
                 <stat name="total_instructions" value="{stats.system.cpu1.iq.iqInstsIssued}"/>
                 <!--...-->
                 <component id="system.core1.itlb" name="itlb">
                     <param name="number_entries" value="{config.system.cpu1.itb.size}"/>
                     <stat name="total_accesses" value="{stats.system.cpu1.itb.fetch_accesses}"/>
                     ...
                 </component>
             </component><component id="system.core2" name="core2">
                 <!-- Core property -->
                 <param name="clock_rate" value="{1e-6/config.system.cpu2.clock*1e12}"/>
                 <param name="opt_local" value="1"/>      
                 <stat name="total_instructions" value="{stats.system.cpu2.iq.iqInstsIssued}"/>
                 <!--...-->
                 <component id="system.core2.itlb" name="itlb">
                     <param name="number_entries" value="{config.system.cpu2.itb.size}"/>
                     <stat name="total_accesses" value="{stats.system.cpu2.itb.fetch_accesses}"/>
                     ...
                 </component>
             </component>
         </component>
     </component>

最佳答案

(1) 如果您将以下两个模板添加到您的 XSLT,

  <xsl:template match="param[@name='number_of_cores' and @value='1']">
    <param name="number_of_cores" value="{$n}"/>
  </xsl:template>

  <xsl:template match="param[@name='homogeneous_cores' and @value='1']">
    <param name="homogenous_cores" value="0"/>
  </xsl:template>

您将覆盖身份转换并能够输出不同的 param 元素,如上所示。

(2) 如果您在 copyNtimes 内调整复制如下,

  <xsl:copy>
    <xsl:attribute name="id" select="concat('system.core', $n)"/>
    <xsl:attribute name="name" select="concat('core', $n)"/>
    <xsl:apply-templates select="node()"/>
  </xsl:copy>

您将生成的不是副本,而是副本,其中 @id@name 反射(reflect)传递给 copyNtimes 的副本数。

(3)如果进一步调整copyNtimes中的xsl:apply-template为隧道n(需要 XSLT 2.0),

  <xsl:apply-templates select="node()">
    <xsl:with-param name="compNum" tunnel="yes" select="$n"/>
  </xsl:apply-templates>

同时添加一个模板来处理隧道另一边的itlb components

  <xsl:template match="component[@name='itlb']">
    <xsl:param name="compNum" tunnel="yes"/>
    <component name="itlb" value="{concat('system.core',$compNum,'.itlb')}">
      <xsl:apply-templates/>
    </component>
  </xsl:template>

您可以将组件编号添加到后代 itlb components 中。

更新(第三次)完整代码和示例输入/输出 XML 文档如下...

此输入 XML 文档:

<?xml version="1.0" ?>
<component id="root" name="root">
  <component id="system" name="system">
    <param name="number_of_cores" value="1"/>
    <param name="homogeneous_cores" value="1"/>
    <param name="number_of_L1Directories" value="0"/>
    <param name="number_of_L2Directories" value="0"/>
    <param name="number_of_L2s" value="1"/> 
    <param name="Private_L2" value="0"/>
    <param name="number_of_L3s" value="0"/> 
    <param name="number_of_NoCs" value="1"/>
    <!-- ... -->
    <component id="system.core0" name="core0">
      <!-- Core property -->
      <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
      <param name="opt_local" value="1"/>      
      <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

      <!-- ... -->
      <component id="system.core0.itlb" name="itlb">
        <param name="number_entries" value="{config.system.cpu.itb.size}"/>
        <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
        <!-- ... -->
      </component>
    </component>
  </component>
</component>

鉴于此 XSLT 转换:

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

  <xsl:param name="n" select="5"/>

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

  <xsl:template match="param[@name='number_of_cores' and @value='1']">
    <param name="number_of_cores" value="{$n}"/>
  </xsl:template>

  <xsl:template match="param[@name='homogeneous_cores' and @value='1']">
    <param name="homogenous_cores" value="0"/>
  </xsl:template>

  <xsl:template match="component[@name='itlb']">
    <xsl:param name="compNum" tunnel="yes"/>
    <component name="itlb" value="{concat('system.core',$compNum,'.itlb')}">
      <xsl:apply-templates/>
    </component>
  </xsl:template>

  <xsl:template match="component[@id='system']/component[@name='core0']">
    <xsl:call-template name="copyNtimes">
      <xsl:with-param name="n" select="$n"/>
      <xsl:with-param name="core_num" select="1"/>
    </xsl:call-template>
  </xsl:template>

  <xsl:template name="copyNtimes">
    <xsl:param name="n" select="0"/>
    <xsl:param name="core_num" select="1"/>

    <xsl:if test="$n > 0">
      <xsl:copy>
        <xsl:attribute name="id" select="concat('system.core', $n)"/>
        <xsl:attribute name="name" select="concat('core', $n)"/>
        <xsl:apply-templates select="node()">
          <xsl:with-param name="compNum" tunnel="yes" select="$n"/>
        </xsl:apply-templates>
      </xsl:copy>
      <xsl:text>
      </xsl:text>
      <xsl:call-template name="copyNtimes">
        <xsl:with-param name="n" select="$n -1"/>
        <xsl:with-param name="core_num" select="$core_num+1"/>
      </xsl:call-template>
    </xsl:if>
  </xsl:template>

</xsl:stylesheet>

将产生此输出 XML 文档:

<?xml version="1.0" encoding="UTF-8"?>
<component id="root" name="root">
  <component id="system" name="system">
      <param name="number_of_cores" value="5"/>
      <param name="homogenous_cores" value="0"/>
      <param name="number_of_L1Directories" value="0"/>
      <param name="number_of_L2Directories" value="0"/>
      <param name="number_of_L2s" value="1"/> 
      <param name="Private_L2" value="0"/>
      <param name="number_of_L3s" value="0"/> 
      <param name="number_of_NoCs" value="1"/>
      <!-- ... -->
      <component id="system.core5" name="core5">
      <!-- Core property -->
         <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
         <param name="opt_local" value="1"/>      
         <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

         <!-- ... -->
         <component name="itlb" value="system.core5.itlb">
            <param name="number_entries" value="{config.system.cpu.itb.size}"/>
            <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
            <!-- ... -->
         </component>
      </component>
      <component id="system.core4" name="core4">
      <!-- Core property -->
         <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
         <param name="opt_local" value="1"/>      
         <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

         <!-- ... -->
         <component name="itlb" value="system.core4.itlb">
            <param name="number_entries" value="{config.system.cpu.itb.size}"/>
            <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
            <!-- ... -->
         </component>
      </component>
      <component id="system.core3" name="core3">
      <!-- Core property -->
         <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
         <param name="opt_local" value="1"/>      
         <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

         <!-- ... -->
         <component name="itlb" value="system.core3.itlb">
            <param name="number_entries" value="{config.system.cpu.itb.size}"/>
            <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
            <!-- ... -->
         </component>
      </component>
      <component id="system.core2" name="core2">
      <!-- Core property -->
         <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
         <param name="opt_local" value="1"/>      
         <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

         <!-- ... -->
         <component name="itlb" value="system.core2.itlb">
            <param name="number_entries" value="{config.system.cpu.itb.size}"/>
            <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
            <!-- ... -->
         </component>
      </component>
      <component id="system.core1" name="core1">
      <!-- Core property -->
         <param name="clock_rate" value="{1e-6/config.system.cpu.clock*1e12}"/>
         <param name="opt_local" value="1"/>      
         <stat name="total_instructions" value="{stats.system.cpu.iq.iqInstsIssued}"/>

         <!-- ... -->
         <component name="itlb" value="system.core1.itlb">
            <param name="number_entries" value="{config.system.cpu.itb.size}"/>
            <stat name="total_accesses" value="{stats.system.cpu.itb.fetch_accesses}"/>
            <!-- ... -->
         </component>
      </component>

  </component>
</component>

关于xml - 修改节点和所有子节点中属性的子字符串,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25917507/

有关xml - 修改节点和所有子节点中属性的子字符串的更多相关文章

  1. ruby - 如何从 ruby​​ 中的字符串运行任意对象方法? - 2

    总的来说,我对ruby​​还比较陌生,我正在为我正在创建的对象编写一些rspec测试用例。许多测试用例都非常基础,我只是想确保正确填充和返回值。我想知道是否有办法使用循环结构来执行此操作。不必为我要测试的每个方法都设置一个assertEquals。例如:describeitem,"TestingtheItem"doit"willhaveanullvaluetostart"doitem=Item.new#HereIcoulddotheitem.name.shouldbe_nil#thenIcoulddoitem.category.shouldbe_nilendend但我想要一些方法来使用

  2. Ruby 解析字符串 - 2

    我有一个字符串input="maybe(thisis|thatwas)some((nice|ugly)(day|night)|(strange(weather|time)))"Ruby中解析该字符串的最佳方法是什么?我的意思是脚本应该能够像这样构建句子:maybethisissomeuglynightmaybethatwassomenicenightmaybethiswassomestrangetime等等,你明白了......我应该一个字符一个字符地读取字符串并构建一个带有堆栈的状态机来存储括号值以供以后计算,还是有更好的方法?也许为此目的准备了一个开箱即用的库?

  3. ruby-on-rails - 在 Rails 中将文件大小字符串转换为等效千字节 - 2

    我的目标是转换表单输入,例如“100兆字节”或“1GB”,并将其转换为我可以存储在数据库中的文件大小(以千字节为单位)。目前,我有这个:defquota_convert@regex=/([0-9]+)(.*)s/@sizes=%w{kilobytemegabytegigabyte}m=self.quota.match(@regex)if@sizes.include?m[2]eval("self.quota=#{m[1]}.#{m[2]}")endend这有效,但前提是输入是倍数(“gigabytes”,而不是“gigabyte”)并且由于使用了eval看起来疯狂不安全。所以,功能正常,

  4. ruby-on-rails - unicode 字符串的长度 - 2

    在我的Rails(2.3,Ruby1.8.7)应用程序中,我需要将字符串截断到一定长度。该字符串是unicode,在控制台中运行测试时,例如'א'.length,我意识到返回了双倍长度。我想要一个与编码无关的长度,以便对unicode字符串或latin1编码字符串进行相同的截断。我已经了解了Ruby的大部分unicode资料,但仍然有些一头雾水。应该如何解决这个问题? 最佳答案 Rails有一个返回多字节字符的mb_chars方法。试试unicode_string.mb_chars.slice(0,50)

  5. ruby - 将差异补丁应用于字符串/文件 - 2

    对于具有离线功能的智能手机应用程序,我正在为Xml文件创建单向文本同步。我希望我的服务器将增量/差异(例如GNU差异补丁)发送到目标设备。这是计划:Time=0Server:hasversion_1ofXmlfile(~800kiB)Client:hasversion_1ofXmlfile(~800kiB)Time=1Server:hasversion_1andversion_2ofXmlfile(each~800kiB)computesdeltaoftheseversions(=patch)(~10kiB)sendspatchtoClient(~10kiBtransferred)Cl

  6. ruby-on-rails - Rails 常用字符串(用于通知和错误信息等) - 2

    大约一年前,我决定确保每个包含非唯一文本的Flash通知都将从模块中的方法中获取文本。我这样做的最初原因是为了避免一遍又一遍地输入相同的字符串。如果我想更改措辞,我可以在一个地方轻松完成,而且一遍又一遍地重复同一件事而出现拼写错误的可能性也会降低。我最终得到的是这样的:moduleMessagesdefformat_error_messages(errors)errors.map{|attribute,message|"Error:#{attribute.to_s.titleize}#{message}."}enddeferror_message_could_not_find(obje

  7. ruby - 如何以所有可能的方式将字符串拆分为长度最多为 3 的连续子字符串? - 2

    我试图获取一个长度在1到10之间的字符串,并输出将字符串分解为大小为1、2或3的连续子字符串的所有可能方式。例如:输入:123456将整数分割成单个字符,然后继续查找组合。该代码将返回以下所有数组。[1,2,3,4,5,6][12,3,4,5,6][1,23,4,5,6][1,2,34,5,6][1,2,3,45,6][1,2,3,4,56][12,34,5,6][12,3,45,6][12,3,4,56][1,23,45,6][1,2,34,56][1,23,4,56][12,34,56][123,4,5,6][1,234,5,6][1,2,345,6][1,2,3,456][123

  8. ruby - 什么是填充的 Base64 编码字符串以及如何在 ruby​​ 中生成它们? - 2

    我正在使用的第三方API的文档状态:"[O]urAPIonlyacceptspaddedBase64encodedstrings."什么是“填充的Base64编码字符串”以及如何在Ruby中生成它们。下面的代码是我第一次尝试创建转换为Base64的JSON格式数据。xa=Base64.encode64(a.to_json) 最佳答案 他们说的padding其实就是Base64本身的一部分。它是末尾的“=”和“==”。Base64将3个字节的数据包编码为4个编码字符。所以如果你的输入数据有长度n和n%3=1=>"=="末尾用于填充n%

  9. ruby-on-rails - 如何从 format.xml 中删除 <hash></hash> - 2

    我有一个对象has_many应呈现为xml的子对象。这不是问题。我的问题是我创建了一个Hash包含此数据,就像解析器需要它一样。但是rails自动将整个文件包含在.........我需要摆脱type="array"和我该如何处理?我没有在文档中找到任何内容。 最佳答案 我遇到了同样的问题;这是我的XML:我在用这个:entries.to_xml将散列数据转换为XML,但这会将条目的数据包装到中所以我修改了:entries.to_xml(root:"Contacts")但这仍然将转换后的XML包装在“联系人”中,将我的XML代码修改为

  10. ruby-on-rails - 如果为空或不验证数值,则使属性默认为 0 - 2

    我希望我的UserPrice模型的属性在它们为空或不验证数值时默认为0。这些属性是tax_rate、shipping_cost和price。classCreateUserPrices8,:scale=>2t.decimal:tax_rate,:precision=>8,:scale=>2t.decimal:shipping_cost,:precision=>8,:scale=>2endendend起初,我将所有3列的:default=>0放在表格中,但我不想要这样,因为它已经填充了字段,我想使用占位符。这是我的UserPrice模型:classUserPrice回答before_val

随机推荐