通过linq选择colections之间的concat



我有两个集合,每个集合都是**模型对象**、**类型对象**、***版本对象**的类型,我需要通过linq获得一个**ConcateName对象**的列表,这个对象有两个类型和模型以及版本的名称,加上每个名称的详细信息列表(详细信息在Classes部分(:类别

class Model
{
public string name { get; set; } // Exemple: "M1"
public string Id { get; set; }  // Exemple:  "codeM1"
}
class Type
{
public string name { get; set; }  // Exemple: "T1"
public string Id { get; set; }  // Exemple: "codeT1"
}
class Version
{
public string name { get; set; } // Exemple: "V1"
public string Id { get; set; }  // Exemple:  "codeV1"
}
class ConcateName
{
public string ConcateName { get; set; } // exemple:  "M1 T1"
public List<ConcateNameInfo> ConcateNameInfos { get; set; }
}
class ConcateNameInfo
{
public Guid TechnicalId { get; set; }
public string Criteria { get; set; }  "M1"
public Guid ValueId { get; set; }  "CodeM1"
}

型号列表

var models = new List<Model>();
var model1 = new Model(){name ="M1", id= "CodeM1"};
var model2 = new Model(){name ="M2", id= "CodeM2"};
models.Add(model1);
models.Add(model2);

类型列表

var types = new List<Type>();
var type1 = new type(){name ="T1", id= "CodeT1"};
var type2 = new type(){name ="M2", id= "CodeT2"};
models.Add(type1);
models.Add(type2);

版本列表

var versions = new List<Version>();
var version1 = new Version(){name ="V1", id= "CodeV1"};
var type2 = new Version(){name ="V2", id= "CodeV2"};
models.Add(type1);
models.Add(type2);

OUTPUT将有12个ConcateName对象

var ConcateName1 = new ConcateName()
{
ConcateName = "M1 P1",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M1",
ValueId = "codeM1"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "T1",
ValueId     = "codeT1"
}
}
}
var ConcateName2 = new ConcateName()
{
ConcateName = "M1 P2",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M1",
ValueId = "codeM1"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "T2",
ValueId     = "codeT2"
}
}
}
var ConcateName3 = new ConcateName()
{
ConcateName = "M2 P1",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M2",
ValueId = "codeM2"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "T1",
ValueId     = "codeT1"
}
}
}

var ConcateName4 = new ConcateName()
{
ConcateName = "M2 P2",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M2",
ValueId = "codeM2"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "T2",
ValueId     = "codeT2"
}
}
}


var ConcateName5 = new ConcateName()
{
ConcateName = "M1 V1",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M1",
ValueId = "codeM1"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "V1",
ValueId     = "codeV1"
}
}
}
var ConcateName6 = new ConcateName()
{
ConcateName = "M1 V2",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M1",
ValueId = "codeM1"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "V2",
ValueId     = "codeV2"
}
}
}
var ConcateName7 = new ConcateName()
{
ConcateName = "M2 V1",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M2",
ValueId = "codeM2"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "V1",
ValueId     = "codeV1"
}
}
}

var ConcateName8 = new ConcateName()
{
ConcateName = "M2 V2",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "M2",
ValueId = "codeM2"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "T2",
ValueId     = "codeV2"
}
}
}

var ConcateName9 = new ConcateName()
{
ConcateName = "T1 V1",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "T1",
ValueId = "codeT1"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "V1",
ValueId     = "codeV1"
}
}
}
var ConcateName10 = new ConcateName()
{
ConcateName = "T1 V2",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "T1",
ValueId = "codeT1"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "V2",
ValueId     = "codeV2"
}
}
}
var ConcateName11 = new ConcateName()
{
ConcateName = "T2 V1",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "T2",
ValueId = "codeT2"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "V1",
ValueId     = "codeV1"
}
}
}

var ConcateName12 = new ConcateName()
{
ConcateName = "T2 V2",
ConcateNameInfos = new List<ConcateNameInfo>() {
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria = "T2",
ValueId = "codeT2"
},
new ConcateNameInfo
{
TechnicalId = Guid.newGuid(),
Criteria    = "T2",
ValueId     = "codeV2"
}
}
}
var output = models.SelectMany(m => types.Select(t => new ConcateName
{
ConcateName = m.Name + " " + t.Name,
ConcateNameInfos = new List<ConcateNameInfo>
{
new ConcateNameInfo
{
TechnicalId = Guid.NewGuid(),
Criteria = m.Name,
ValueId = m.Id
},
new ConcateNameInfo
{
TechnicalId = Guid.NewGuid(),
Criteria = t.Name,
ValueId = t.Id
}
}
});

对于任意数量的类,您需要引入一个接口:

interface IHasNameAndId
{
string Name { get; }
string Id { get; }
}

然后你可以计算笛卡尔乘积:

public static IEnumerable<IEnumerable<T>> CartesianProduct<T>(
this IEnumerable<IEnumerable<T>> enumerables)
{
return enumerables.Aggregate
(
new [] { Enumerable.Empty<T>() }.AsEnumerable(),
(accumulator, enumerable) =>
accumulator.SelectMany(x => enumerable.Select(x.Append))
);
}

可以投影到您所需的结构中:

var lists = new IHasNameAndId[] { models, types, //...
var output = lists
.CartesianProduct()
.Select(x => new ConcateName
{
ConcateName = string.Join(" ", x.Select(y => y.Name)),
ConcateNameInfos = x.Select(y => new ConcateNameInfo
{
TechnicalId = Guid.NewGuid(),
Criteria = y.Name,
ValueId = y.Id
})
.ToList()
});

最新更新