public class parent
{
public string abc { get; set; }
public childclass pos { get; set; }
}
public class childclass
{
public string value { get; set; }
}
I am currently reading the collection of parent class
var obj =
(from dia in parent
select new
{
abc = dia.abc,
pos = new childclass()
{
value = dia.pos.value
},
})
.ToList();
how do I read the nested class childclass using linq to object , this piece is not working
pos = new childclass()
{
Value = dia.pos.Value
},
Please advise
It works perfectly, I think your problem is case sensitive
Classes:
public class Parent
{
public string Abc { get; set; }
public Childclass Pos { get; set; }
}
public class Childclass
{
public string Value { get; set; }
}
Use:
var parent = new List<Parent> {
new Parent { Abc = "abc1", Pos = new Childclass { Value = "Value1" } },
new Parent { Abc = "abc2", Pos = new Childclass { Value = "Value2" } }
};
var obj =(from dia in parent select new {
abc = dia.Abc,
pos = new Childclass()
{
Value = dia.Pos.Value
},
}).ToList();
C# is case-sensitive. The value field in your class childClass has a lower-case 'v'. Your LINQ statement is referencing it using an upper-case 'V'.
Try the following code:
var obj = (from dia in parent
select new
{
abc = dia.abc,
pos = new childclass()
{
value = dia.pos.value // 'Value' has been changed to 'value'
},
}).ToList();
Here is a test I ran to verify that the updated LINQ statement works:
var parents = new List<parent>()
{
new parent{abc = "abc", pos = new childclass{ value = "value" }}
};
var obj =
(from dia in parents // changed to 'parents' to match my variable above
select new
{
abc = dia.abc,
pos = new childclass()
{
value = dia.pos.value
},
}).ToList();
foreach (var par in obj)
{
Console.WriteLine(par);
}
The resulting output was:
"{ abc = abc, pos = ProgrammingTestBed.Program+childclass }"
Related
I have a City_State list:
City_State[0].Range="\"city\":\"REDMOND\",\"state\":\"AK\"";
City_State[1].Range="\"city\":\"Alex City\",\"state\":\"
How to convert it into json like below:
var _pairs = new
{
criteria = new { cities = new[] { new { city = "REDMOND", state = "WA" },
new { city = "Alex City", state = "AL" } }
} ;
I tried the code below, but it does not work:
var _pairs = new { criteria = new { cities = new[] { _paged_City_State.ToArray() } } };
If you had these classes:
public class CityStateRaw
{
public string Range { get; set; }
}
public class CityState
{
public string City { get; set; }
public string State { get; set; }
}
The following code would work:
var ranges = new[]
{
new CityStateRaw { Range = "{\"city\":\"REDMOND\",\"state\":\"AK\"}" },
new CityStateRaw { Range = "{\"city\":\"Alex City\",\"state\":\"foo\"}" },
};
var list = ranges
.Select(raw => JsonConvert.DeserializeObject<CityState>(raw.Range))
.ToList();
But if this doesn't match your expectations you should be more concrete about what your exact input and the expected output should be.
I have the following repro which returns the Name of all MyParent objects with a related MyChild where the specified field (which is only known at runtime) is true.
The sample works, however I am certain there is plenty of room to simplify the query. The test case has much irrelevant data removed such as metadata and navigation properties. The actual data store is an mssql database. Can the group construct be avoided?
using System;
using System.Linq;
using System.Linq.Expressions;
public class MyParent
{
public int Id { get; set; }
public string Name { get; set; }
public bool Enabled { get; set; }
}
public class MyChild
{
public int Id { get; set; }
public bool FieldA { get; set; }
public bool FieldB { get; set; }
public int MyParentId { get; set; }
}
class Program
{
static void Main()
{
var childA = new MyChild { Id = 0, FieldA = false, MyParentId = 0 };
var parentA = new MyParent { Id = 0, Name = "John", Enabled = true };
var childB = new MyChild { Id = 1, FieldA = true, MyParentId = 1 };
var parentB = new MyParent { Id = 1, Name = "Jane", Enabled = true };
var userField = "FieldA";
var parents = new[] { parentA, parentB }.AsQueryable();
var children = new[] { childA, childB }.AsQueryable();
var parameter = Expression.Parameter(typeof(MyChild), "p");
var property = Expression.Property(parameter, userField);
var lambda = Expression.Lambda<Func<MyChild, bool>>(property, parameter);
var query =
from parent in parents
join child in children on parent.Id equals child.MyParentId into grp
from g in grp.AsQueryable().Select(lambda).Where(p => p)
where parent.Enabled
select parent.Name;
}
}
This will do the trick using reflection, no grouping needed.
static void Main()
{
var childA = new MyChild { Id = 0, FieldA = false, MyParentId = 0 };
var parentA = new MyParent { Id = 0, Name = "John", Enabled = true };
var childB = new MyChild { Id = 1, FieldA = true, MyParentId = 1 };
var parentB = new MyParent { Id = 1, Name = "Jane", Enabled = true };
var parents = new[] { parentA, parentB }.AsQueryable();
var children = new[] { childA, childB }.AsQueryable();
var userField = "FieldA";
var childQuery = from child in children.Where(c => c.GetType().GetProperty(userField).GetValue(c).Equals(true)) select child;
var query =
from parent in parents
join child in childQuery on parent.Id equals child.MyParentId
where parent.Enabled
select parent.Name;
}
I have a below class. I will get two objects List<Client> data1 and List<Client> data2. I want to compare data1 and data2 with each of the attribute value.
For example, if data1 object has the LastName=a and ClientId=1,..etc and if data2 list has the same set of data i want to push that into one more list.
Any idea, how can we achieve this using LINQ/Minimal code?
public class Client
{
public int ClientId { get; set; }
public string LastName { get; set; }
public string FirstName { get; set; }
public string Email { get; set; }
}
using Intersect
List<Client> data1 = new List<Client>();
List<Client> data2 = new List<Client>();
List<Client> newlst = new List<Client>();
Client obj = new Client();
obj.ClientId = 1;
obj.LastName = "a";
obj.FirstName = "n";
obj.Email = "e";
data1.Add(obj);
data2.Add(obj);
obj = new Client();
obj.ClientId = 2;
obj.LastName = "a";
obj.FirstName = "f";
obj.Email = "e";
data1.Add(obj);
newlst = data1.Intersect(data2).ToList();
I have used IEqualityComparer which is used to compare both the collection and Intersect will give the common value.I have tested the code for few scenario. You can check for all the scenario.
Hope this code will be helpful.
namespace UnitTestProject
{
[TestClass]
public class CompareTwoGenericList
{
[TestMethod]
public void TestMethod1()
{
var coll = GetCollectionOne();
var col2 = GetCollectionTwo();
//Gives the equal value
var commonValue = coll.Intersect(col2, new DemoComparer()).ToList();
//Difference
var except=coll.Except(col2, new DemoComparer()).ToList();
}
public List<Demo> GetCollectionOne()
{
List<Demo> demoTest = new List<Demo>()
{
new Demo
{
id=1,
color="blue",
},
new Demo
{
id=2,
color="green",
},
new Demo
{
id=3,
color="red",
},
};
return demoTest;
}
public List<Demo> GetCollectionTwo()
{
List<Demo> demoTest = new List<Demo>()
{
new Demo
{
id=1,
color="blue",
},
new Demo
{
id=2,
color="green",
},
new Demo
{
id=4,
color="red",
},
};
return demoTest;
}
}
// Custom comparer for the Demo class
public class DemoComparer : IEqualityComparer<Demo>
{
// Products are equal if their color and id are equal.
public bool Equals(Demo x, Demo y)
{
//Check whether the compared objects reference the same data.
if (Object.ReferenceEquals(x, y)) return true;
//Check whether any of the compared objects is null.
if (Object.ReferenceEquals(x, null) || Object.ReferenceEquals(y, null))
return false;
//Check whether the demo properties are equal.
return x.color == y.color && x.id == y.id;
}
// If Equals() returns true for a pair of objects
// then GetHashCode() must return the same value for these objects.
public int GetHashCode(Demo demo)
{
//Check whether the object is null
if (Object.ReferenceEquals(demo, null)) return 0;
//Get hash code for the color field if it is not null.
int hashColor = demo.color == null ? 0 : demo.color.GetHashCode();
//Get hash code for the id field.
int hashId = demo.id.GetHashCode();
//Calculate the hash code for the product.
return hashColor ^ hashId;
}
}
}
Create Your new class ClientView
public class ClientView{
public int ClientId { get; set; }
public string LastName { get; set; }
public string FirstName { get; set; }
public string Email { get; set; }
}
List lst = new List();
var data = from n in db.client
select new ClientView()
{
ClientId = n.ClientId ,
LastName = n.LastName ,
FirstName = n.FirstName,
};
var data1 = from n in db.client
select new ClientView()
{
ClientId = n.ClientId ,
LastName = n.LastName ,
FirstName = n.FirstName,
};
lst.AddRange(data);
lst.AddRange(data1);
List<ClientView> lst1 = new List<ClientView>();
foreach (var singlelst in lst)
{
ClientView newClient = new ClientView ();
newClient.Id = singlelst.Id;
newClient.આપેલ = singlelst.LastName;
newClient.આપેલતારીખ = singlelst.FirstName;
lst1.Add(newClient);
}
Try this:
public IEnumerable<PropertyInfo> GetVariance(Client user)
{
foreach (PropertyInfo pi in user.GetType().GetProperties()) {
object valueUser = typeof(Client).GetProperty (pi.Name).GetValue (user);
object valueThis = typeof(Client).GetProperty (pi.Name).GetValue (this);
if (valueUser != null && !valueUser.Equals(valueThis))
yield return pi;
}
}
IEnumerable<PropertyInfo> variances = data1.GetVariance (data2);
foreach (PropertyInfo pi in variances)
Console.WriteLine (pi.Name);
I have following objects
class A
{
public List<B> listB { get; set; }
}
class B
{
public int id { get; set; }
}
and in my application I have a scenario like below..
public void main()
{
var lstA = new List<A>();
var lstA = new List<A>();
var a1 = new A();
a1.listB = new List<B>
{
new B() { id = 1 },
new B() { id = 2 }
};
lstA.Add(a1);
a1 = new A();
a1.listB = new List<B>
{
new B() { id = 3 },
new B() { id = 4 }
};
lstA.Add(a1);
}
And I need to select all id's of B objects from lstA
Here is what I've tried so far
var ids = lst.Select(x=>x.listB.Select(y=>y.id)).ToList();
But It gives me a compilation error.
How can I do this?
You have to use SelectMany which flattens the lists:
var ids = lst.SelectMany(x => x.listB.Select(y => y.id)).ToList();
You are almost there, use SelectMany
var ids = lst.SelectMany(x=>x.listB.Select(y=>y.id)).ToList();
Check your Working Code
Here's what i did and it works perfectly
All i did was make the classes public and when you initialise List<B>, you add new List<B> because even though intellisense doesn't show you any error, when you run the application, you get object not referenced error
class Program
{
static void Main(string[] args)
{
var lstA = new List<A>();
var a1 = new A()
{
listB = new List<B>()
{
new B
{
id = 3
},
new B
{
id = 5
}
}
};
var a2 = new A()
{
listB = new List<B>()
{
new B
{
id = 1
},
new B
{
id = 8
}
}
};
lstA.Add(a1);
lstA.Add(a2);
var ids = lstA.SelectMany(r => r.listB.Select(x => x.id));
foreach (var id in ids)
{
Console.WriteLine(id);
}
Console.ReadKey();
}
}
public class A
{
public List<B> listB { get; set; }
}
public class B
{
public int id { get; set; }
}
try this to ignore duplicate id
var ids = lstA.SelectMany(x => x.listB.Select(y => y.id)).Distinct().ToList();
The issue here is that the instance of the class "obj" is re-created every time I run through the loop so at the end of the loop, I only have 1 set of the object. It should have several.
foreach (var project in projectsDictionary)
{
foreach (var season in seasonsDictionary)
{
foreach (var episode in episodesDictionary)
{
obj = new Parent
{
Title = project.Value, Link = "1", Children = new List<Parent>
{
new Parent
{
Title = season.Value, Link = "1", Children = new List<Parent>
{
new Parent
{
Title = episode.Value, Link = "1", Children = null
}
}
}
}
};
}
}
}
var responseBody = JsonConvert.SerializeObject(obj);
return responseBody;
public class Parent
{
public string Title
{
get;
set;
}
public string Link
{
get;
set;
}
public List<Parent> Children
{
get;
set;
}
}
Outside the first loop define obj as a list.
var obj = new List<Parent>();
then
obj.Add(new Parent(...));