如何从平面数据中找到树叶

时间:2013-03-13 18:13:27

标签: c# algorithm tree

我有类似这样的树数据:

[0] => 
      id = 5,
      name = "TV",
      parent_id = 1,
      children => 
                  [0] => 
                        id = 6,
                        name = "PLASMA",
                        parent_id = 5,
                        children = null
                  [1] =>
                        id = 7,
                        name = "LCD",
                        parent_id = 5,
                        children =>
                                    [0] =>
                                          id = 8,
                                          name = "Gloss",
                                          parent_id = 7,
                                          children = null
                                    [1] =>
                                          id = 9,
                                          name = "Matte",
                                          parent_id = 7,
                                          children = null
[1] =>
      id = 4,
      name = "Printers",
      parent_id = 1,
      children =>
                 ....

我有一个扁平的字符串数据,如:

  • TV
  • TV_PLASMA_Gloss
  • TV_LCD

'_'是子类别的分隔符。

查找类别ID数组的最佳算法是什么?

示例输入:

  1. TV
  2. TV_PLASMA_Gloss
  3. TV_LCD
  4. 示例输出:

    1. 数组:5
    2. 阵列:5,6,8
    3. 数组:5,7
    4. 语言并不重要 - 它只是一种算法 - 但在这种情况下我更喜欢C#。

      谢谢。

3 个答案:

答案 0 :(得分:0)

使用HashMap(在这种情况下Dictionary<string, int>会没问题),遍历你的树并将(name,id)对添加到HashMap中。

对于您在输入字符串和散列图中传递的任何输入。

  • 在分隔符上拆分字符串,在本例中为“_”(input.Split(new char[]{'_'})
  • 对于每个字符串部分,在hashmap中查找其id,并将其添加到输出字符串或数组

*

public int[] GetIDsFromString(string input, Dictionary<string, int> lookup)
{
  string stringParts = input.Split(new char[]{'_'});
  int[] retval = new int[stringParts.Length];
  int retIndex = 0;
  foreach(var s in stringParts)
    if (lookup.contains(s))
      retval[retIndex++] = lookup[s];
    else
      throw new Exception(string.format("string contained invalid item {0}", s));
  return retval;
}

答案 1 :(得分:0)

使用字典进行(反向)查找与名称相关的ID

Dictionary<string,int> ids = new Dictionary<string,int>();
ids.Add("TV", 5);
ids.Add("PLASMA", 6);
// And so on

现在,在查找ID之前拆分输入字符串

string input = "TV_PLASMA_Gloss";
string[] categories = input.Split('_');
int[] result = new int[categories.Length];
for (int i = 0; i < categories.Length; i++) {
    int id;
    if (ids.TryGetValue(categories[i], out id)) {
        result[i] = id;
    } else {
        result[i] = -1; // Unknown category
    }
}

答案 2 :(得分:0)

就这样,我会用递归来做:

定义一个函数,它接受一个字符串数组和你的struct / object-array或者其他什么。 在调用函数之前解析字符串数组:

string = "TV_PLASMA_Gloss"
array[0] = "TV"
array[1] = "PLASMA"
array[2] = "Gloss"

将对所有“顶级”条目测试数组中的第一个字符串。如果存在匹配的条目,则将使用剩余的数组和匹配的条目再次调用该函数。

如果数组中只剩下一个字符串,则返回找到的条目的id。这样我们就可以进行递归调用并构建我们想要的integer-id-array。

调用层次结构如下所示:

-> function({"TV","PLASMA","Gloss"}, entry)
   -> function({"PLASMA","Gloss"}, matched_entry)
       -> function({"Gloss"}, matched_entry)
       <- id = 8
   <- id = 6,8
<- id = 5,6,8