Заполните ревизию файла в виде дерева - PullRequest
1 голос
/ 26 апреля 2020

Я пытаюсь заполнить список версий файлов в виде дерева. У меня есть список файлов ревизий, как показано ниже.

1.17
1.17.1.1
1.17.1.2
1.17.1.2.1.1    
1.17.1.2.1.2
1.17.1.2.1.2.1.1    
1.17.1.2.1.2.1.2
1.17.1.2.1.2.1.3
1.17.1.2.1.2.1.3.1.1
1.17.1.2.1.2.1.3.1.2
1.17.1.2.1.2.1.3.2.1
1.17.1.2.1.2.1.4    
1.17.1.2.1.2.1.5
1.17.1.2.1.2.1.5.1.1
1.17.1.2.1.2.1.5.1.2
1.17.1.2.1.2.1.5.1.2.1.1
1.17.1.2.1.3
1.17.1.2.1.4
1.18
1.19

Теперь я хотел бы заполнить его как

1.17
    1.17.1.1
    1.17.1.2
        1.17.1.2.1.1    
        1.17.1.2.1.2
            1.17.1.2.1.2.1.1    
            1.17.1.2.1.2.1.2
            1.17.1.2.1.2.1.3
                1.17.1.2.1.2.1.3.1.1
                1.17.1.2.1.2.1.3.1.2
                1.17.1.2.1.2.1.3.2.1    
            1.17.1.2.1.2.1.4    
            1.17.1.2.1.2.1.5    
                1.17.1.2.1.2.1.5.1.1
                1.17.1.2.1.2.1.5.1.2    
                    1.17.1.2.1.2.1.5.1.2.1.1        
        1.17.1.2.1.3
        1.17.1.2.1.4                        
1.18
1.19

Моя идея классифицируется по уровню

1.17         -> level 1
1.17.1.1     -> level 2
1.17.1.2     -> level 2
1.17.1.2.1.1 -> level 3
...

Затем я использую регистр переключателя, чтобы заполнить его древовидной структурой

if level = 1 then parent node
else if level = 2 then child node
else if level = 3 then grandchild node
...

Однако я не знаю, является ли это правильным способом достижения моей цели. Есть ли лучший способ сделать это?

Любая помощь, спасибо и большое спасибо

1 Ответ

1 голос
/ 26 апреля 2020

Вы можете воспользоваться повторяющимся шаблоном путей TreeNodes (#. #). Создайте их массив, используя RegEx. Если в массиве есть только один элемент, то путь имеет узел root, в противном случае строка присоединяется к массиву, кроме последнего элемента (для конкатенации имени родителя), и использует функцию TreeView.Nodes.Find(..), чтобы найти родительский узел каждый путь.

C#

private void PopulateTree(IEnumerable<string> paths)
{
    treeView1.SuspendLayout();
    treeView1.Nodes.Clear();

    foreach (var path in paths.OrderBy(x => x))
    {
        var node = new TreeNode { Name = path, Text = path };
        var arr = Regex.Matches(path, @"\d+.\d+")
            .Cast<Match>().Select(x => x.Value).ToArray();

        if (arr.Count() == 1)
            treeView1.Nodes.Add(node);
        else
        {
            var parentPath = string.Join(".", arr, 0, arr.Count() - 1);
            var parentNode = treeView1.Nodes.Find(parentPath, true).FirstOrDefault();

            if (parentNode != null)
                parentNode.Nodes.Add(node);
        }
    }

    treeView1.ResumeLayout();
}

private void TheCaller()
{
    var revisionsList = //Get the list...

    PopulateTree(revisionsList);    
}

VB. NET

Private Sub PopulateTree(paths As IEnumerable(Of String))
    TreeView1.SuspendLayout()
    TreeView1.Nodes.Clear()

    For Each path In paths.OrderBy(Function(x) x)
        Dim node As New TreeNode With {.Name = path, .Text = path}
        Dim arr = Regex.Matches(path, "\d+.\d+").
            Cast(Of Match).Select(Function(x) x.Value).ToArray()

        If arr.Count = 1 Then
            TreeView1.Nodes.Add(node)
        Else
            Dim parentPath = String.Join(".", arr, 0, arr.Count() - 1)
            Dim parentNode = TreeView1.Nodes.Find(parentPath, True).FirstOrDefault

            If parentNode IsNot Nothing Then
                parentNode.Nodes.Add(node)
            End If
        End If
    Next

    TreeView1.EndUpdate()
End Sub

Private Sub TheCaller()
    Dim revisionsList = 'Get the list...

    PopulateTree(revisionsList)
End Sub

результат:

SOQ60904806

...