0

Well I have this C# Code:

var searchTerm = search_box.Text;

Predicate<object> firstName = delegate (object pers) 
{
    var person = pers as Person;
    return person.Firstname.StartsWith(searchTerm); 
};

Predicate<object> lastName = delegate (object pers) 
{
    var person = pers as Person;
    return person.Lastname.StartsWith(searchTerm); 
};

So the main problem in this Code is that I do not want to use Predicate. Is there another possible way to get the same result as the code with Predicate

smolchanovsky
  • 1,775
  • 2
  • 15
  • 29
yocak123
  • 33
  • 4
  • Couldn't you replace them with functions? See https://learn.microsoft.com/en-us/dotnet/api/system.predicate-1?view=netcore-3.1 – IndieGameDev Oct 10 '20 at 12:36
  • Is it possible with a for loop? – yocak123 Oct 10 '20 at 12:38
  • The more modern way would be `Func firstName = pers => (pers as Person).FirstName.StartsWith(searchTerm);` – ckuri Oct 10 '20 at 12:39
  • from where do you get the person object anyway – IndieGameDev Oct 10 '20 at 12:39
  • https://stackoverflow.com/questions/1710301/what-is-a-predicate-in-c – Peter Dongan Oct 10 '20 at 13:17
  • 2
    Perhaps you should explain why you don't want to use predicate. What is your purpose and why is predicate unsuitable for that task? Once you do that we don't need to guess what you're doing and a specific solution might be best. Maybe chaining linq queries would be a "better" way to go. – Andy Oct 10 '20 at 13:41

3 Answers3

3

To begin, you can simplify version with Predicate:

Predicate<object> firstName = pers =>
{
    var person = pers as Person;
    return person.Firstname.StartsWith(searchTerm); 
};

Predicate<object> lastName = pers => 
{
    var person = pers as Person;
    return person.Lastname.StartsWith(searchTerm); 
};

then you can replace with Func:

Func<object, bool> firstName = pers =>
{
    var person = pers as Person;
    return person.Firstname.StartsWith(searchTerm); 
};

Func<object, bool> lastName = pers =>
{
    var person = pers as Person;
    return person.Lastname.StartsWith(searchTerm); 
};

or use local functions (C# version >= 7.0):

bool firstName(object pers) 
{
    var person = pers as Person;
    return person.Firstname.StartsWith(searchTerm); 
};

bool lastName(object pers) 
{
    var person = pers as Person;
    return person.Lastname.StartsWith(searchTerm); 
};

or use own delegate:

public delegate bool SetName(object pers);
//...

SetName firstName = pers => 
{
    var person = pers as Person;
    return person.Firstname.StartsWith(searchTerm); 
};

SetName lastName = pers =>  
{
    var person = pers as Person;
    return person.Lastname.StartsWith(searchTerm); 
};
smolchanovsky
  • 1,775
  • 2
  • 15
  • 29
  • `delegate (object pers)` can be simplified to `pers =>` as the compiler already knows that the argument is of type object and a lambda (=> notation) here is functionally equivalent to a delegate. – ckuri Oct 10 '20 at 12:54
  • @ckuri you are absolutely right, I just tried to make minimal changes in this example – smolchanovsky Oct 10 '20 at 12:58
0

You're code seems to be fine, but we can rewrite it like below:

var Customer=(Customer)pers ;

Predicate<Customer> predict=x=>
x.Firstname.StartsWith(searchTerm) && x.Lastname.StartsWith(searchTerm);
osman Rahimi
  • 1,427
  • 1
  • 11
  • 26
0

Assuming, that:

  • your question is about ICollectionView.Filter
  • and you need to search using both first name and last name
  • and Firstname and/or Lastname can be null

your code could be rewritten like this:

var searchTerm = search_box.Text;

yourCollectionView.Filter = obj =>
    obj is Person p &&
    (p.Firstname?.StartsWith(searchTerm) == true || 
     p.Lastname?.StartsWith(searchTerm) == true);

This, of course, uses Predicate<object>, since Filter property declared to be Predicate<object>, but you don't declare it explicitly.

Dennis
  • 37,026
  • 10
  • 82
  • 150