-2

Just starting to learn and grasp C# and apologies if this has been asked somewhere but I've been looking for a couple hours and can't quite understand why I need to specify the syntax in the latter format. I appreciate all the help!

If you can, please provide a link to documentation, or a good explanation of why I can't just run code A vs code B.

Code A:

if (!Array.Exists(layers, element == collision.gameObject.layer))
{
    doStuff()
}

Code B:

if (!Array.Exists(layers, element => element == collision.gameObject.layer))
{
    doStuff()
}
1
  • 1
    If you think about it from the other direction: what is element supposed to be? Where does it magically come from? Also it would mean you are passing in a simple bool value for the entire method => doesn't make much sense. So of course what you want is rather a function that operates on each individual element of the array and returns an individual bool for each. Using a lambda expression (that's what you are dealing with when you see a => anywhere) is just one of multiple ways of how to write that Commented May 15 at 5:33

3 Answers 3

2

The function Array.Exists takes a Predicate as the second argument.

https://learn.microsoft.com/en-us/dotnet/api/system.array.exists

A Predicate is a function that takes one element as input, should check if this element meets your criteria and returns a boolean.

https://learn.microsoft.com/en-us/dotnet/api/system.predicate-1

In Code A, your second argument is just a comparison that will get evaluated first (before Array.Exists is even called!), and its boolean value will be passed to the Array.Exists function, which is neither what you want nor what the function expects. You want to check each individual element of your array individually.

Furthermore, if you just write: element == collision.gameObject.layer, the word element is not each element of your array, but rather treated as a variable (which likely does not exist in your scope).

Since you want this comparison to be applied to each individual element of your array, you pass a function, which gets called for every item in your array: This is done in Code B using the Lambda expression: element => element == collision.gameObject.layer, where the current item that is passed to this lambda function is given the name element, and is then compared to collision.gameObject.layer.

Sign up to request clarification or add additional context in comments.

2 Comments

Thanks for sharing this and explaining. If I'm understanding correctly now, element => element is just passing the first object/piece of the array to be used in the followup condition, which is why code A doesnt work since it doesnt know what element is as its not defined like another commenter mentioned. I'm not able to up vote yet but thanks again!
Glad i could help :)
1

In the first case you are attempting to evaluate an expression, then pass the result as an argument to the function;

SomeFunction(argument1, someValue == someConstant);

In the second case you are defining a function, then passing the function as an argument. All three of these examples are equivalent;

bool MyFunction(ElementType element) {
   return element == someConstant;
}

SomeFunction(argument1, MyFunction);

or

SomeFunction(argument1, (element) => {
   return element == someConstant;
});

or

SomeFunction(argument1, element => element == someConstant);

Comments

0

You have to supply a function predicate as the second parameter to the Array.Exists function because that is how the function is defined, as noted on the function description it expects the following Parameters:

  1. array T[] The one-dimensional, zero-based Array to search.

  2. match Predicate<T> The Predicate that defines the conditions of the elements to search for.

Returns Boolean true if array contains one or more elements that match the conditions defined by the specified predicate; otherwise, false.


Now if you only want to supply the matching element in the array and check if it is found within the array, you can use the Linq function Contains.

your code would be refactored to:

if (!layers.Contains(collision.gameObject.layer))
{
    doStuff();
}

1 Comment

Thanks for the explanation and sharing another methodology. It appears to be a simpler way of achieving what I'm trying to do.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.