Assuming we have objects that look something like this:
public class Person
{
public int ID { get; set; }
public string Code { get; set; }
}
public class StringProperty
{
public int ID { get; set; }
public int PersonID { get; set; }
public string Name { get; set; }
public string Value { get; set; }
}
public class NumericProperty
{
public int ID { get; set; }
public int PersonID { get; set; }
public string Name { get; set; }
public int Value { get; set; }
}
And data like this:
var persons = new List<Person>
{
new Person { ID = 1, Code = "Person1" },
new Person { ID = 2, Code = "Person2" },
new Person { ID = 3, Code = "Person3" }
};
var stringProperties = new List<StringProperty>
{
new StringProperty { ID = 1, PersonID = 1, Name = "FirstName", Value = "John" },
new StringProperty { ID = 2, PersonID = 1, Name = "LastName", Value = "Smith" },
new StringProperty { ID = 3, PersonID = 2, Name = "FirstName", Value = "William" },
new StringProperty { ID = 4, PersonID = 2, Name = "LastName", Value = "Brown" },
new StringProperty { ID = 5, PersonID = 3, Name = "FirstName", Value = "James" },
new StringProperty { ID = 6, PersonID = 3, Name = "LastName", Value = "Miller" }
};
var numericProperties = new List<NumericProperty>
{
new NumericProperty { ID = 1, PersonID = 1, Name = "Age", Value = 25 },
new NumericProperty { ID = 2, PersonID = 1, Name = "Weight", Value = 50 },
new NumericProperty { ID = 3, PersonID = 2, Name = "Age", Value = 30 },
new NumericProperty { ID = 4, PersonID = 2, Name = "Weight", Value = 80 },
new NumericProperty { ID = 5, PersonID = 3, Name = "Age", Value = 32 },
new NumericProperty { ID = 6, PersonID = 3, Name = "Weight", Value = 73 }
};
We can attach people to a table of row values like this, and at the same time collapse it:
var stringValues = from p in persons
join s in stringProperties on p.ID equals s.PersonID
group s by p.Code into g
select new
{
Code = g.Key,
FirstName = g.Where(s => s.Name == "FirstName").First().Value,
LastName = g.Where(s => s.Name == "LastName").First().Value,
};
Do the same for numerical values:
var numericValues = from p in persons
join n in numericProperties on p.ID equals n.PersonID
group n by p.Code into g
select new
{
Code = g.Key,
Age = g.Where(n => n.Name == "Age").First().Value,
Weight = g.Where(n => n.Name == "Weight").First().Value,
};
Now connect them together:
var q = from s in stringValues
join n in numericValues on s.Code equals n.Code
select new
{
Code = s.Code,
FirstName = s.FirstName,
LastName = s.LastName,
Age = n.Age,
Weight = n.Weight
};
You can do this in one statement, but it is easier if you separate it as follows.
In fact, I would rather do this in a stored procedure, since it is faster there.