Reputation:
Assuming the following code
private readonly T entity;
public bool HasUnique<T>(Expression<Func<T, object>> property, IEnumerable<T> entities)
{
}
Where property
is a property expression of T
entity.
How to check if there is any element in entities
with the same property value as entity
has, while property is resolved from given property expression?
By now, I can get property name and its value from entity
The problem seems to be how to set up and execute at runtime a predicate? Something like
Func<T, bool> predicate = // build a predicate
var isUnique = !entities.Any(predicate);
The usage would be like this
var isUnique = HasUnique<Person>(p => p.Name, people);
Upvotes: 2
Views: 176
Reputation: 5103
Do you need an Expression<Func<T,object>>
? Because it can be achieved with just Func<T,object>
.
using System;
using System.Collections.Generic;
using System.Linq;
namespace LinqPlayground
{
class Program
{
public class UniqueChecker<T>
{
public bool HasUnique<T>(Func<T, object> property, IEnumerable<T> entities)
{
var uniqueDict = new Dictionary<object, bool>();
foreach (var entity1 in entities)
{
var key = property(entity1);
if (uniqueDict.ContainsKey(key))
{
uniqueDict[key] = false;
}
else
{
uniqueDict.Add(key, true);
}
}
return uniqueDict.Values.All(b => b);
}
}
public class Person
{
public string Name { get; set; }
}
static void Main(string[] args)
{
var people = new List<Person>
{
new Person {Name = "Chris"},
new Person {Name = "Janet"},
new Person {Name = "John"},
new Person {Name = "Janet"},
};
var checker = new UniqueChecker<Person>();
Console.WriteLine("Are names unique? {0}",checker.HasUnique(person => person.Name, people));
}
}
}
Upvotes: 0
Reputation: 101680
I'm trying to figure out what the word "Unique" has to do with what you described, and your example usage doesn't involve any entity to compare the contents of people
to, but I think you're going for something like this?
public static bool HasUnique<T>(this T referenceItem, Func<T, object> property,
IEnumerable<T> entities)
{
var referenceProperty = property(referenceItem);
return entities.Any(e => property(e) == referenceProperty);
}
or maybe this:
public static bool HasUnique<T>(this T referenceItem, Func<T, object> property,
IEnumerable<T> entities)
{
var referenceProperty = property(referenceItem);
return entities.Any(e => property(e).Equals(referenceProperty));
}
Or even this:
public static bool HasUnique<T, TProp>(this T referenceItem, Func<T, TProp> property,
IEnumerable<T> entities)
{
var referenceProperty = property(referenceItem);
return entities.Any(e => property(e).Equals(referenceProperty));
}
Upvotes: 1