如何以递归方式遍历<ul> <li>?

时间:2017-06-21 11:02:21

标签: javascript html dom recursion

我有这个清单:

<ul>
  <li>
    <a href="http://site.ru/cabinet/vidos-1" data-image="assets/images/programs/ai.jpg">Видос 1</a>
    <ul>
      <li><a href="http://site.ru/cabinet/vidos-4" data-image="assets/images/programs/ek.jpg">Видос 4</a></li>
      <li><a href="http://site.ru/cabinet/vidos-5" data-image="assets/images/programs/vs.jpg">Видос 5</a></li>
      <li><a href="http://site.ru/cabinet/vidos-6" data-image="assets/images/programs/lz.jpg">Видос 6</a></li>
    </ul>
  </li>
  <li>
    <a href="http://site.ru/cabinet/vidos-2" data-image="assets/images/test/woodhouse.png">Видос 2</a>
  </li>
  <li>
    <a href="http://site.ru/cabinet/vidos-3" data-image="assets/images/test/sterling.png">Видос 3</a>
    <ul>
      <li>
        <a href="http://site.ru/cabinet/vidos-7" data-image="assets/images/test/pam.png">Видос 7</a>
        <ul>
          <li>
            <a href="http://site.ru/cabinet/vidos-8" data-image="assets/images/test/malory.png">Видос 8</a>
            <ul>
              <li>
                <a href="http://site.ru/cabinet/vidos-9" data-image="">Видос 9</a>
              </li>
              <li>
                <a href="http://site.ru/cabinet/vidos-10" data-image="assets/images/test/figgs.png">Видос 10</a>
                <ul>
                  <li>
                    <a href="http://site.ru/cabinet/vidos-11" data-image="assets/images/test/cheryl.png">Видос 11</a>
                  </li>
                </ul>
              </li>
            </ul>
          </li>
        </ul>
      </li>
    </ul>
  </li>
</ul>

首先想要将其分级打印为

UL
  LI
    A
    UL...
      // And deeper
  LI
    A
  LI
    A
    UL...
      // And deeper

我找到了这个功能:

function getNode($node, $depth = 0) {
    var tab = '';
    for (var $i = 0; $i < $depth; $i++) { tab += '&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;'; }
    var $children = $node.children();
    if ($children.length) {
        $children.each(function() {
            getNode(jQuery(this), $depth+1);
        });
        // Do something with the branch
        document.write(tab+'<b>&lt;'+$node.prop('tagName')+'&gt;</b><br>');
    } else {
        // Do something with the leaf
    }
}

getNode(jQuery('#divtree > ul').first());

但它打印我错了,破坏了ierarchy。我希望以递归方式循环,然后为Treant.js库配置

创建JSON对象

2 个答案:

答案 0 :(得分:0)

忘掉document.write,现在值得使用它会带来太大的伤害。

使用return语句将结果从递归级别传递到上级语句。

var result = getNode(jQuery(this), $depth + 1);
... // do something with result

return tab + '<b>&lt;' + $node.prop('tagName') + '&gt;</b><br>';

这样,由于递归的魔力,调用顺序得到了尊重。

编辑:,为了多元化,这是一个完整的,普通的解决方案。

<!DOCTYPE html>
<html lang="en">
<head>
  <meta charset="utf-8">
  <title>Recursive ul chewing</title>
</head>
<body>

<pre id="output"></pre>
<button>Test</button>

<script> 'use strict';

const INPUT_STRING =
`<ul>
  <li>
    <a href="http://site.ru/cabinet/vidos-1" data-image="assets/images/programs/ai.jpg">Видос 1</a>
    <ul>
      <li><a href="http://site.ru/cabinet/vidos-4" data-image="assets/images/programs/ek.jpg">Видос 4</a></li>
      <li><a href="http://site.ru/cabinet/vidos-5" data-image="assets/images/programs/vs.jpg">Видос 5</a></li>
      <li><a href="http://site.ru/cabinet/vidos-6" data-image="assets/images/programs/lz.jpg">Видос 6</a></li>
    </ul>
  </li>
  <li>
    <a href="http://site.ru/cabinet/vidos-2" data-image="assets/images/test/woodhouse.png">Видос 2</a>
  </li>
  <li>
    <a href="http://site.ru/cabinet/vidos-3" data-image="assets/images/test/sterling.png">Видос 3</a>
    <ul>
      <li>
        <a href="http://site.ru/cabinet/vidos-7" data-image="assets/images/test/pam.png">Видос 7</a>
        <ul>
          <li>
            <a href="http://site.ru/cabinet/vidos-8" data-image="assets/images/test/malory.png">Видос 8</a>
            <ul>
              <li>
                <a href="http://site.ru/cabinet/vidos-9" data-image="">Видос 9</a>
              </li>
              <li>
                <a href="http://site.ru/cabinet/vidos-10" data-image="assets/images/test/figgs.png">Видос 10</a>
                <ul>
                  <li>
                    <a href="http://site.ru/cabinet/vidos-11" data-image="assets/images/test/cheryl.png">Видос 11</a>
                  </li>
                </ul>
              </li>
            </ul>
          </li>
        </ul>
      </li>
    </ul>
  </li>
</ul>`;

function chew($element, depth = 0) {
  let padding = '  '.repeat(depth);

  let result = `${padding}<${$element.tagName}>\n`;
  for (let $child of $element.children) {
    result += chew($child, depth + 1);
  }
  return result;
}

let $output = document.querySelector('#output');

document.querySelector('button').addEventListener('click',
  function test() {
    let $div = document.createElement('div');
    $div.insertAdjacentHTML('beforeend', INPUT_STRING);
    let $ul = $div.querySelector('ul');
    $output.textContent = chew($ul);
  });


</script>
</body>
</html>

请注意,递归条件包含在for..of循环中。没有孩子,没有迭代,它就像它一样简单。

答案 1 :(得分:0)

此函数将Tree结构中的DOM层次结构打印到控制台中。

function printTree(node, n) {
  console.log(addEmptySpaces(n) + $(node).prop('tagName'));
  $(node).children().each(function(index, el){
    printTree($(el), n + 1);
  });
}

function addEmptySpaces(n){
  var space = '';
  for(var i = 0; i < n; i++){
    space += '  ';
  }
  return space;
}

printTree($("#root"), 1);
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<ul id="root">
  <li>
    <a href="http://site.ru/cabinet/vidos-1" data-image="assets/images/programs/ai.jpg">Видос 1</a>
    <ul>
      <li><a href="http://site.ru/cabinet/vidos-4" data-image="assets/images/programs/ek.jpg">Видос 4</a></li>
      <li><a href="http://site.ru/cabinet/vidos-5" data-image="assets/images/programs/vs.jpg">Видос 5</a></li>
      <li><a href="http://site.ru/cabinet/vidos-6" data-image="assets/images/programs/lz.jpg">Видос 6</a></li>
    </ul>
  </li>
  <li><a href="http://site.ru/cabinet/vidos-2" data-image="assets/images/test/woodhouse.png">Видос 2</a></li>
  <li>
    <a href="http://site.ru/cabinet/vidos-3" data-image="assets/images/test/sterling.png">Видос 3</a>
    <ul>
      <li>
        <a href="http://site.ru/cabinet/vidos-7" data-image="assets/images/test/pam.png">Видос 7</a>
        <ul>
          <li>
            <a href="http://site.ru/cabinet/vidos-8" data-image="assets/images/test/malory.png">Видос 8</a>
            <ul>
              <li><a href="http://site.ru/cabinet/vidos-9" data-image="">Видос 9</a></li>
              <li>
                <a href="http://site.ru/cabinet/vidos-10" data-image="assets/images/test/figgs.png">Видос 10</a>
                <ul>
                  <li><a href="http://site.ru/cabinet/vidos-11" data-image="assets/images/test/cheryl.png">Видос 11</a></li>
                </ul>
              </li>
            </ul>
          </li>
        </ul>
      </li>
    </ul>
  </li>
</ul>