patterncsharpMinor
Using LINQ to group social networking links for each user
Viewed 0 times
sociallinqnetworkingeachgroupuserlinksusingfor
Problem
I have a model named
I want my query to be like this in the result:
I have written following query, It works as I expected but I wonder if there's a better way for doing this:
```
users.Select(p => new UserViewModel {
Name = p.Name,
Facebook = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.FaceBook).Url ?? "#",
Twitter = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Twitter).Url ?? "#",
Youtube = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Youtube).Url ?? "#",
Linkedin = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Linkedin).Url ?? "#",
Telegram = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Tele
User. Each user can have some social links. Now I want to get all users with their social link as a single row in the result. Here are my models:public class User
{
public int Id { get; set; }
public string Name { get; set; }
public ICollection SocialLinks { get; set; }
}
public class SocialLink
{
public string Url { get; set; }
public SocialType Type { get; set; }
public User User { get; set; }
public int UserId { get; set; }
}
public enum SocialType
{
FaceBook = 0,
Twitter = 1,
Youtube = 2,
Linkedin = 3,
GooglePlus = 4,
Telegram = 5,
Instagram = 6
}
public class UserViewModel
{
public string Name { get; set; }
public string Facebook { get; set; }
public string Twitter { get; set; }
public string Youtube { get; set; }
public string Linkedin { get; set; }
public string GooglePlus { get; set; }
public string Telegram { get; set; }
public string Instagram { get; set; }
}I want my query to be like this in the result:
Name | Facebook | Twitter | Youtube | Linkedin | GooglePlus | Telegram | Instagram
======================================================================================
Someone | facebook | @someone | youtube | linkedin | google | @tele | @someinsI have written following query, It works as I expected but I wonder if there's a better way for doing this:
```
users.Select(p => new UserViewModel {
Name = p.Name,
Facebook = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.FaceBook).Url ?? "#",
Twitter = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Twitter).Url ?? "#",
Youtube = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Youtube).Url ?? "#",
Linkedin = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Linkedin).Url ?? "#",
Telegram = p.SocialLinks.FirstOrDefault(x => x.Type == SocialType.Tele
Solution
You could use a
Then your query will looks like:
Dictionary and make properties of UserViewModel to address elements of this dictionary as follows:public class UserViewModel
{
private readonly Dictionary SocialLinks;
public UserViewModel(User user)
{
SocialLinks = (user.SocialLinks ?? new SocialLink[0])
.ToDictionary(x => x.Type, x => x.Url);
Name = user.Name;
}
private string GetUrl(SocialType socialType)
{
string url;
return SocialLinks.TryGetValue(socialType, out url) && url != null ? url : "#";
}
public string Name { get; set; }
public string Facebook
{
get { return GetUrl(SocialType.FaceBook); }
set { SocialLinks[SocialType.FaceBook] = value; }
}
public string Twitter
{
get { return GetUrl(SocialType.Twitter); }
set { SocialLinks[SocialType.Twitter] = value; }
}
public string Youtube
{
get { return GetUrl(SocialType.Youtube); }
set { SocialLinks[SocialType.Youtube] = value; }
}
...
}Then your query will looks like:
users.Select(u => new UserViewModel(u)).ToList();Code Snippets
public class UserViewModel
{
private readonly Dictionary<SocialType, string> SocialLinks;
public UserViewModel(User user)
{
SocialLinks = (user.SocialLinks ?? new SocialLink[0])
.ToDictionary(x => x.Type, x => x.Url);
Name = user.Name;
}
private string GetUrl(SocialType socialType)
{
string url;
return SocialLinks.TryGetValue(socialType, out url) && url != null ? url : "#";
}
public string Name { get; set; }
public string Facebook
{
get { return GetUrl(SocialType.FaceBook); }
set { SocialLinks[SocialType.FaceBook] = value; }
}
public string Twitter
{
get { return GetUrl(SocialType.Twitter); }
set { SocialLinks[SocialType.Twitter] = value; }
}
public string Youtube
{
get { return GetUrl(SocialType.Youtube); }
set { SocialLinks[SocialType.Youtube] = value; }
}
...
}users.Select(u => new UserViewModel(u)).ToList();Context
StackExchange Code Review Q#151150, answer score: 6
Revisions (0)
No revisions yet.