0

2 つの xml 配列があり、これらの配列を 3 番目の配列にマージしたい...最初の xml 構造は

$current = '<forms id="frm16648">
  <group ref="" id="tarascioheader" mode="block">
    <label>
    <![CDATA[Group (tarascioheader)]]>
    </label> structure u
    <select ref="" id="petorresp">
      <label>
      <![CDATA[Select (petorresp)]]>
      </label>
    </select>

そして2番目の配列は

$old = '<forms id="frm16648">
  <group ref="" id="tarascioheader" mode="block">
    <label>
    <![CDATA[abc]]>
    </label>
 </group>
</forms>':
  </group>
</forms>';

これらのxmlから、一致するすべてのタグを新しい配列にコピーしたい....再帰関数でこれを行おうとしています....

function merge_xmls($current, $old) 
{

    $cxml = str_get_html($current); 
    $oxml = str_get_html($old); 
    do
    {
        $tt = $cxml->first_child();
        if(!empty($tt) && !is_null($cxml->first_child()))
        {

            $x = $cxml->first_child();

            $this->merge_xmls($x, $cxml, $oxml);
        }
        if(empty($tt))
        {
            $cid = $cxml->id;
            $oid = $oxml -> find('#'.$cid);
            if(!is_null($oid))
            {
                $cxml -> innerHTML = $oxml -> innerHTML;
            }
        }
        $cxml = $cxml->next_sibling();
    }
    while(!empty($cxml) && !is_null($cxml));
}
4

1 に答える 1

0

投稿した疑似コードから、ある xml 要素の子を別の要素にコピーしたいようです。別のパーサーを使用しているため、少し異なりますが、同じです。

  1. コピー先のすべての要素を検索します。
    1. コピー先として見つかった要素に基づいて、コピー元の要素を見つけます。
    2. コピー先の要素のすべての子を削除します。
    3. からすべての子をコピーします

次のような専用の操作に適しているため、ここでは DOMDocument を使用して行います。

$doc = new DOMDocument();

$copyTo = $doc->createDocumentFragment();
$copyTo->appendXML($current);

$copyFrom = new DOMDocument();
$copyFrom->loadXML($old);

$xpath = new DOMXPath($copyFrom);

foreach (new DOMElementFilter($copyTo->childNodes, 'forms') as $form) {
    $id         = $form->getAttribute('id');
    $expression = sprintf('(//*[@id=%s])[1]', xpath_string($id));
    $copy       = $xpath->query($expression)->item(0);

    if (!$copy) {
        throw new UnexpectedValueException("No element with ID to copy from \"$id\"");
    }

    dom_replace_children($copy, $form);
}

出力は次のとおりです。

echo $doc->saveXML($doc->importNode($copyTo, TRUE));

そして与えます:

<forms id="frm16648">
  <group ref="" id="tarascioheader" mode="block">
    <label>
    <![CDATA[abc]]>
    </label>
 </group>
</forms>

ここでの支援ルーチンは次のとおりです。

function dom_remove_children(DOMElement $node)
{
    while ($node->firstChild) {
        $node->removeChild($node->firstChild);
    }
}

function dom_replace_children(DOMElement $from, DOMElement $into)
{
    dom_remove_children($into);

    $doc = $into->ownerDocument;

    foreach ($from->childNodes as $child) {
        $into->appendChild($doc->importNode($child, TRUE));
    }
}

また、DOMElementFilterクラス(PHP DOM 経由: エレガントな方法でタグ名で子要素を取得する方法は? ) とxpath_string()関数があります(これもStackoverflow に示されています)。

これが役に立てば幸いです。この例は、あなたのデータを次のように処理します: https://eval.in/59886

于 2013-11-02T19:17:51.463 に答える