根据数字序列将对象转换为层次结构

时间:2016-06-21 16:46:38

标签: c# linq

我有以下数据结构,我想把它隐藏在一个基于RelationId的层次结构中。这是在RelationId上排序的。

Id = 2具有relationId = 2并且以下两行具有realtionId = 0。代表Id = 3和Id = 4的孩子是Id = 2

的孩子
   Id    Name   RelationId    SortOrder
    1     A       1              1
    2     B       2              2
    3     C       0              3
    4     D       0              4
    5     E       3              5
    6     F       0              6
    7     G       0              7
    8     H       4              8

结果结果如下

 Id = 1
  |
 Id = 2  
  |___  Id = 3 , Id = 4

 Id = 5 
  |___ Id= 6 , Id=7

 Id = 8

所需的结果如下(为简单起见,将其表示为List)。这将是C#中的List<Something>

Result = 
[
   { Id = 1, Name = A, Children = Null },
   { Id = 2, Name = B, Children = [{ Id = 3, Name = C }, {Id = 4, Name = D }] },
   { Id = 5, Name = E, Children = [{ Id = 6, Name = F }, {Id = 7, Name = G }] },
   { Id = 8, Name = H}
]

我的失败尝试如下:

var finalResult = new List<sampleDataClass>();
var sampleData = GetMeSampleData();   
var count = sampleData.Count();

foreach (var item in sampleData)
{
    var alreadyExist = finalResult.Any(x => x.Id == item.Id);
    var newObject = new sampleDataClass();

    if (!alreadyExist && item.RelationId!= 0)
    {
        newObject = item;
    }

    for (int i = item.SortOrder; i < count; i++)
    {
        if (sampleData[i].RelationId== 0)
        {
            newObject.Children.Add(sampleData[i]);
        }
    }

    finalResult.Add(newObject );
}

2 个答案:

答案 0 :(得分:1)

由于您的RelationId决定它是根或嵌套元素,您可以根据这些关系形成一个组并执行此操作。我建议使用 Linq

List<SomeData> somedata = ... // your data.

int index=0;
var results = somedata
    .Select(x=> new {gid = x.RelationId ==0? index: ++index, item=x})
    .GroupBy(x=> x.gid)
    .Select(x=> {
        var first = x.FirstOrDefault();

        return new 
        {
            Id = first.item.Id,
            Name = first.item.Name,
            Children =  x.Skip(1).Select(s=> new {
                Id = s.item.Id,
                Name = s.item.Name,
            })                      
        };
    })
    .ToList();

输出

Id=1, Name=A
Id=2, Name=B
    Id=3, Name=C
    Id=4, Name=D
Id=5, Name=E
    Id=6, Name=F
    Id=7, Name=G
Id=8, Name=H

选中此Working Code

答案 1 :(得分:0)

我这样做了。不知道是否可以有更优雅的解决方案

  var data = new List<MyDataObject>();
            var SampleData = GetMeSampleData;
            var count = SampleData.Count();
            for (int i=0;i<count;i++)
            {
                var rootAdded = false;
                var relationId = SampleData[i].relationId;
                var alreadyExist = data.Any(x => x.Id == SampleData[i].Id);
                var mydataObject = new MyDataObject();
                if (!alreadyExist && SampleData[i].RelationId != 0)
                {
                    mydataObject = SampleData[i];
                    rootAdded = true;
                }


                for(int j=i+1;j<count;j++)
                {
                    if ((SampleData[j].RelationId == 0 && rootAdded))
                    {
                        mydataObject.Children.Add(SampleData[j]);
                    }
                    if (SampleData[j].SubjectId != 0) 
                        break;


                }


                if (rootAdded)
                {
                    data.Add(mydataObject);

                }