从树状对象中获取唯一元素的列表

时间:2014-01-24 18:21:09

标签: javascript arrays

在我的小应用程序中,我有一个函数返回树状数据:

function getData() {
return {
    "name": "fish",
        "children": [{
        "name": "mussels & clams",
            "children": [{
            "name": "fennel",
                "size": 1
        }, {
            "name": "garlic",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "onion",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "pasta",
                "size": 1
        }, {
            "name": "rice",
                "size": 1
        }, {
            "name": "soup",
                "size": 1
        }, {
            "name": "tomato",
                "size": 1
        }]
    }, {
        "name": "octopus",
            "children": [{
            "name": "bay",
                "size": 1
        }, {
            "name": "chilli",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "olive oil",
                "size": 1
        }, {
            "name": "paprika",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "pine nuts",
                "size": 1
        }]
    }, {
        "name": "oysters",
            "children": [{
            "name": "asparagus",
                "size": 1
        }, {
            "name": "bacon",
                "size": 1
        }, {
            "name": "butter",
                "size": 1
        }, {
            "name": "cellery",
                "size": 1
        }, {
            "name": "chives",
                "size": 1
        }, {
            "name": "garlic",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "mozzarella",
                "size": 1
        }, {
            "name": "onion",
                "size": 1
        }, {
            "name": "pasta",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "shallot",
                "size": 1
        }]
    }, {
        "name": "pink fish",
            "children": [{
            "name": "balsamic vinegar",
                "size": 1
        }, {
            "name": "chives",
                "size": 1
        }, {
            "name": "cream",
                "size": 1
        }, {
            "name": "dill",
                "size": 1
        }, {
            "name": "garlic",
                "size": 1
        }, {
            "name": "ham",
                "size": 1
        }, {
            "name": "honey",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "lime",
                "size": 1
        }, {
            "name": "mild cheese",
                "size": 1
        }, {
            "name": "miso",
                "size": 1
        }, {
            "name": "potato",
                "size": 1
        }, {
            "name": "sesame",
                "size": 1
        }, {
            "name": "soy souce",
                "size": 1
        }, {
            "name": "spinach",
                "size": 1
        }, {
            "name": "thyme",
                "size": 1
        }]
    }, {
        "name": "shrimp",
            "children": [{
            "name": "coriander",
                "size": 1
        }, {
            "name": "curry",
                "size": 1
        }, {
            "name": "ginger",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "lime",
                "size": 1
        }, {
            "name": "lobster",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "soft cheese",
                "size": 1
        }, {
            "name": "tomato",
                "size": 1
        }]
    }, {
        "name": "smoked fish",
            "children": [{
            "name": "asparagus",
                "size": 1
        }, {
            "name": "butter",
                "size": 1
        }, {
            "name": "eggs",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "mandarin",
                "size": 1
        }, {
            "name": "mild cheese",
                "size": 1
        }, {
            "name": "mushrooms",
                "size": 1
        }, {
            "name": "onion",
                "size": 1
        }, {
            "name": "potato",
                "size": 1
        }, {
            "name": "spring onion",
                "size": 1
        }]
    }, {
        "name": "squid",
            "children": [{
            "name": "bacon",
                "size": 1
        }, {
            "name": "courgette",
                "size": 1
        }, {
            "name": "cumin",
                "size": 1
        }, {
            "name": "garlic",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "lime",
                "size": 1
        }, {
            "name": "onion",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "peper",
                "size": 1
        }, {
            "name": "rocket",
                "size": 1
        }, {
            "name": "thyme",
                "size": 1
        }]
    }, {
        "name": "sushi",
            "children": [{
            "name": "coriander",
                "size": 1
        }, {
            "name": "couscous",
                "size": 1
        }, {
            "name": "cucumber",
                "size": 1
        }, {
            "name": "ginger",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "lime",
                "size": 1
        }, {
            "name": "pepper",
                "size": 1
        }, {
            "name": "rice",
                "size": 1
        }, {
            "name": "sesame",
                "size": 1
        }, {
            "name": "soya souce",
                "size": 1
        }, {
            "name": "spring onion",
                "size": 1
        }, {
            "name": "wasabi",
                "size": 1
        }]
    }, {
        "name": "white fish",
            "children": [{
            "name": "butter",
                "size": 1
        }, {
            "name": "courgette",
                "size": 1
        }, {
            "name": "gream",
                "size": 1
        }, {
            "name": "fennel",
                "size": 1
        }, {
            "name": "french beans",
                "size": 1
        }, {
            "name": "garlic",
                "size": 1
        }, {
            "name": "leak",
                "size": 1
        }, {
            "name": "lemon",
                "size": 1
        }, {
            "name": "lime",
                "size": 1
        }, {
            "name": "mild cheese",
                "size": 1
        }, {
            "name": "onion",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "soup",
                "size": 1
        }, {
            "name": "soya souce",
                "size": 1
        }, {
            "name": "tomato",
                "size": 1
        }]
    }, {
        "name": "caviar",
            "children": [{
            "name": "chives",
                "size": 1
        }, {
            "name": "eggs",
                "size": 1
        }, {
            "name": "sour cream",
                "size": 1
        }, {
            "name": "strong cheese",
                "size": 1
        }]
    }, {
        "name": "lobster & crab",
            "children": [{
            "name": "chili",
                "size": 1
        }, {
            "name": "coriander",
                "size": 1
        }, {
            "name": "fennel",
                "size": 1
        }, {
            "name": "ginger",
                "size": 1
        }, {
            "name": "leek",
                "size": 1
        }, {
            "name": "mayonnaise",
                "size": 1
        }, {
            "name": "parsley",
                "size": 1
        }, {
            "name": "pasta",
                "size": 1
        }, {
            "name": "peas",
                "size": 1
        }, {
            "name": "rice",
                "size": 1
        }, {
            "name": "sesame",
                "size": 1
        }, {
            "name": "soy sauce",
                "size": 1
        }, {
            "name": "wasabi",
                "size": 1
        }]
    }]
};}

数据可视化如下:

enter image description here

这是jsfiddle

我想在主图的右侧创建一个标签列表,其中包含在树的叶子中找到的所有值,但每个值只有一次。换句话说,它应该包含:

  • “芦笋”
  • “熏肉”
  • “香醋”

(就像所有叶子的“联合”)

如何使用唯一元素获取该数组?

(一旦我拥有该阵列,显示标签对我来说不是问题)

干杯!

4 个答案:

答案 0 :(得分:2)

检索所有名称属性/属性很容易。

var fishNames = nodes.map(function(x){return x.name});

要在javascript中获取数组的唯一值,请检查here

答案 1 :(得分:1)

var data = getData();
var namesObj = {}; // Put leaves into object first for uniqueness
for( var c0 in data.children )
  for( var c1 in data.children[c0].children )
    namesObj[data.children[c0].children[c1].name] = 1;

var names = []; // Then put unique leaves into an array
for( var name in namesObj ) names.push(name);

names // ["fennel", "garlic", "lemon", "onion", "parsley", "pasta", "rice", "soup", "tomato", "bay", "chilli", "olive oil", "paprika", "pine nuts", "asparagus", "bacon", "butter", "cellery", "chives", "mozzarella", "shallot", "balsamic vinegar", "cream", "dill", "ham", "honey", "lime", "mild cheese", "miso", "potato", "sesame", "soy souce", "spinach", "thyme", "coriander", "curry", "ginger", "lobster", "soft cheese", "eggs", "mandarin", "mushrooms", "spring onion", "courgette", "cumin", "peper", "rocket", "couscous", "cucumber", "pepper", "soya souce", "wasabi", "gream", "french beans", "leak", "sour cream", "strong cheese", "chili", "leek", "mayonnaise", "peas", "soy sauce"]

答案 2 :(得分:1)

您需要对对象执行标准树遍历。例如,假设您有一个在每个节点上执行回调的函数:

walkObject(obj, function(obj, name, parent){
  /* obj === parent[name] */
});

所以我会这样做:

var names = {};
walkObject(nodes, function(obj, name, parent){
  if (name !== 'name') return;
  names[obj] = true;
});
var uniqueList = Object.keys(names);

希望有所帮助。

答案 3 :(得分:1)

因此,您可以使用IxJSlodashunderscore这样的库轻松完成此操作。

但是,这是一种没有外部依赖性的方法。

function flatMap (arr, selector) {
  return Array.prototype.concat.apply([], arr.map(selector));
}

var names =
  flatMap(getData().children, function (x) { return x.children; })
    .map(function (x) { return x.name; });

var length = names.length;
var namesAndCount = {};

for (var i = 0; i < length; i++) {
  var name = names[i];
  namesAndCount[name] = namesAndCount[name] ? namesAndCount[name] + 1 : 1;
}

此时,namesAndCount看起来与此相似:

{
  "fennel":3,
  "garlic":5,
  "lemon":9,
  "onion":5,
  ...
}