Reputation: 1748
I am trying to bind two list values into a single list based on the values of the column.
below is the list am getting it.
TestCaseName Screen IEStatus IEPath FFStatus FFPath GCStatus GCPath
--------------------------------------------------------------------------------------------
TC001 Yes Pass C:\\a.jpg null null null null
TC002 Yes Pass C:\\b.jpg null null null null
TC001 Yes null null Pass C:\\c.jpg null null
TC002 Yes null null Pass C:\\d.jpg null null
But I want to combine the values and display as below
TestCaseName Screen IEStatus IEPath FFStatus FFPath GCStatus GCPath
--------------------------------------------------------------------------------------------
TC001 Yes Pass C:\\a.jpg Pass C:\\c.jpg null null
TC002 Yes Pass C:\\b.jpg Pass C:\\d.jpg null null
Below is my code
List<ResultProperties> lstCommon = new List<ResultProperties>();
List<ResultProperties> lstNew= new List<ResultProperties>();
var checked_boxes = this.Controls.OfType<CheckBox>().Where(c => c.Checked);
foreach (CheckBox cbx in checked_boxes)
{
Program obj = new Program();
lstNew = obj.PerformTest(cbx.Text, textBox1.Text);
foreach (ResultProperties item in lstNew)
{
lstCommon.Add(item);
}
}
Any suggestions will be greatly helpful..
Upvotes: 1
Views: 87
Reputation: 74317
Rather than doing it in a single Linq expression, I would probably do something list this, so as to avoid multiple iterations over the source data:
List<ResultProperties> a = LoadSourceList() ;
IEnumerable<IGrouping<string,ResultProperties> groups =
a
.GroupBy( x => x.TestCaseName , StringComparer.OrdinalIgnoreCase )
;
List<ResultProperties> coalesced = new List<ResultProperties>() ;
foreach( IGrouping<string,ResultProperties> group in groups )
{
ResultProperties item = null ;
foreach( ResultProperty rp in group )
{
item = item ?? rp ;
item.Screen = item.Screen ?? rp.Screen ;
item.IEStatus = item.IEStatus ?? rp.IEStatus ;
item.IEPath = item.IEPath ?? rp.IEPath ;
item.FFStatus = item.FFStatus ?? rp.FFStatus ;
item.FFPath = item.FFPath ?? rp.FFPath ;
item.GCStatus = item.GCStatus ?? rp.GCStatus ;
item.GCPath = item.GCPath ?? rp.GCPath ;
}
coalesced.Add(item) ;
}
At the end of the day, the source list is unchanged and coalesced
should contain a single ResultProperties
for each distinct test case name, with all the value coalesce on a first-wins strategy (the first non-null value for a property defines the property for the group).
Upvotes: 1
Reputation: 726849
You should be able to do this with GroupBy
, like this:
var res = testData
.GroupBy(test => test.TestCaseName)
.Select(g => new ResultProperties {
TestCaseName = g.Key
, Screen = g.Select(test => test.Screen).FirstOrDefault()
, IEStatus = g.Select(test => test.IEStatus).FirstOrDefault()
, IEPath = g.Select(test => test.IEPath).FirstOrDefault()
, FFStatus = g.Select(test => test.FFStatus).FirstOrDefault()
, FFPath = g.Select(test => test.FFPath).FirstOrDefault()
, GCStatus = g.Select(test => test.GCStatus).FirstOrDefault()
, GCPath = g.Select(test => test.GCPath).FirstOrDefault()
}).ToList();
The idea is to form groups based on the name of the test, and then grab the first non-null entry for each attribute in the group.
Upvotes: 1