How to deny a delegate?

This is my code, greatly shortened for simplicity.

Func<Product, bool> selector; ... selector = p => p.IsNew; ... if(negative) // not selector selector = x => !selector(x); // This is wrong (causes infinite loop) // How do you do negate it? The result should be p => !p.IsNew ... IEnumerable<Product> products = MyContext.Products.Where(selector); 
+4
source share
2 answers

You can do this with a helper method:

 public static Predicate<T> Negate<T>(this Predicate<T> predicate) { return t => !predicate(t); } 

(or replace Predicate with Func<T, bool> ).

Then:

 selector = selector.Negate(); 

The stack overflow problem is pretty obvious; you define selector in terms of yourself 1 . A helper method avoids this problem.

1 : That is, this will explicitly cause a stack overflow:

 public bool M() { return !M(); } 

Believe it or not, you are doing the same.

+7
source

You can also use temporary Func:

 if(negative) { Func<Product, bool> tempSelector = selector; selector = x => !tempSelector(x); } 

This selector method no longer applies to itself.

0
source

Source: https://habr.com/ru/post/1495652/


All Articles