代码之家  ›  专栏  ›  技术社区  ›  Rachcha

将节点及其子节点从父节点移动到同级节点

  •  1
  • Rachcha  · 技术社区  · 12 年前

    我有一个XML树,如下所示:

    <root>
        <a>
            <a1>A1</a1>
            <a2>A2</a2>
            ...
            ...
            <an>An</an>
        </a>
        <b>
            <b1>B1</b1>
            <b2>B2</b2>
            ...
            ...
            <bm>Bm</bm>
        </b>
        <x>
            <x1>X1</x1>
            <x2>X2</x2>
            ...
            ...
        </x>
        <y>
            ...
            ...
        </y>
        ...
        ...
    </root>
    

    使用Oracle XMLQuery和XQuery,我希望将此XML更改为:

    <root>
        <a>
            <a1>A1</a1>
            <a2>A2</a2>
            ...
            ...
            <an>An</an>
            <b>
                <b1>B1</b1>
                <b2>B2</b2>
                ...
                ...
                <bm>Bm</bm>
            </b>
        </a>
        <x> <!-- This x node and all its siblings have to stay where they are. -->
            <x1>X1</x1>
            <x2>X2</x2>
            ...
            ...
        </x>
        <y>
            ...
            ...
        </y>
        ...
        ...
    </root>
    

    简而言之,我想把整个 b 下的节点及其后代 a 通过附录。

    到目前为止,我所尝试的是:

    WITH xdata AS (
    SELECT XMLTYPE('<root>
                        <a>
                            <a1>A1</a1>
                            <a2>A2</a2>
                        </a>
                        <b>
                            <b1>B1</b1>
                            <b2>B2</b2>
                        </b>
                        <x>
                            <x1>X1</x1>
                            <x2>X2</x2>
                        </x>
                    </root>') AS xmldata
      FROM dual
    )
    SELECT XMLQuery ('for $a in $x1/root/a, $b in $x1/root/b
                      return <root>{$a}{$b}</root>'
                     PASSING x.xmldata AS "x1" RETURNING CONTENT) AS output
      FROM xdata x;
    

    这显然给了我一个非常错误的结果。也许我正在尝试的是完全错误的。请帮忙。

    1 回复  |  直到 12 年前
        1
  •  1
  •   Dmitry Nikiforov    12 年前
    SQL> WITH xdata AS (
      2  SELECT XMLTYPE('<root>
      3                      <a>
      4                          <a1>A1</a1>
      5                          <a2>A2</a2>
      6                      </a>
      7                      <b>
      8                          <b1>B1</b1>
      9                          <b2>B2</b2>
     10                      </b>
     11                  </root>') AS xmldata
     12    FROM dual
     13  )
     14  SELECT XMLQuery ('for $v in $x1/root return <root><a>{$x1//root/a/*}{$x1//root/b}</a></root>'
     15                   PASSING x.xmldata AS "x1" RETURNING CONTENT) AS output
     16    FROM xdata x;
    
    OUTPUT                                                                          
    --------------------------------------------------------------------------------
    <root><a><a1>A1</a1><a2>A2</a2><b><b1>B1</b1><b2>B2</b2></b></a></root>    
    

    对于更复杂的情况:

    SQL> WITH xdata AS (
      2  SELECT XMLTYPE('<root>
      3                      <a>
      4                          <a1>A1</a1>
      5                          <a2>A2</a2>
      6                      </a>
      7                      <b>
      8                          <b1>B1</b1>
      9                          <b2>B2</b2>
     10                      </b>
     11                      <x>
     12                          <x1>X1</x1>
     13                          <x2>X2</x2>
     14                      </x>
     15                      <y>
     16                          <y1>Y1</y1>
     17                          <y2>Y2</y2>
     18                      </y>
     19                  </root>') AS xmldata
     20    FROM dual
     21  )
     22  SELECT XMLQuery ('for $v in $x1/root
     23  return <root><a>{$x1/root/a/*}{$x1/root/b}</a>
     24  {for $t in $x1/root/* where $t!=$v/a and $t!=$v/b return $t}</root>'
     25  PASSING x.xmldata AS "x1" RETURNING CONTENT) AS output
     26  FROM xdata x
     27  /
    
    OUTPUT                                                                          
    --------------------------------------------------------------------------------
    <root><a><a1>A1</a1><a2>A2</a2><b><b1>B1</b1><b2>B2</b2></b></a><x><x1>X1</x1><x
    2>X2</x2></x><y><y1>Y1</y1><y2>Y2</y2></y></root>