Home > front end >  Match the condition of the first array to be contains with second array
Match the condition of the first array to be contains with second array

Time:04-05

I would like to check whether first array match with second array items, the second array have texts that I want to match with the first array.

Here is the code that I am using:

public static void Main()
{
    List<string> FirstArrayToLookup = new List<string>();
    List<string> SecondArrayToLookup = new List<string>();
    List<string> ThirdArrayToLookup = new List<string>();
    
    FirstArrayToLookup.Add("FirstArray1");
    FirstArrayToLookup.Add("FirstArray2");
    
    SecondArrayToLookup.Add("SecondArray1");
    
    ThirdArrayToLookup.Add("ThirdArray1");
    ThirdArrayToLookup.Add("ThirdArray2");
    ThirdArrayToLookup.Add("ThirdArray3");
    
    string[] FirstStringContains = { "Array1", "Array2" };
    string[] SecondStringContains = { "Array1" };
    string[] ThirdStringContains = { "Array1", "Array2", "Array3" };
    
    if (FirstArrayToLookup.All(x => FirstStringContains.All(y => x.Contains(y))))
        Console.WriteLine("First Array to Lookup");
    
    if (SecondArrayToLookup.All(x => SecondStringContains.All(y => x.Contains(y))))
        Console.WriteLine("Second Array to Lookup");
    
    if (ThirdArrayToLookup.All(x => ThirdStringContains.All(y => x.Contains(y))))
        Console.WriteLine("Third Array to Lookup");
}

The above code will only return Second Array to Lookup, where what I want to achieve is if the FirstArrayToLookup variable match with the FirstStringContains variable (which it does as because FirstArrayToLookup does have items which has the word of Array1 and Array2, same goes with their check condition FirstStringContains), then it should return First Array to Lookup, same goes with the others. However only the Second Array to Lookup is returned, but not First Array to Lookup and Third Array to Lookup. The FirstArrayToLookup have to be match with FirstStringContains, same goes with others.

Basically, from user point of view, as because the FirstArrayToLookup has Array1 and Array2, and it check against the FirstStringContains that has Array1 and Array2 also which fulfills the condition, it should print First Array to Lookup, same goes with others as it is check against their respective ArrayToLookup with StringContains variable

.Net fiddle: https://dotnetfiddle.net/rhTMuz

Anyone knows on how to solve this?

UPDATE:

I have tried to use as according to the following question: Link , which uses the if else conditions, however it does not fulfills what I want, which is it should print First Array to Lookup, Second Array to Lookup and Third Array to Lookup, as because FirstArrayToLookup does contains Array1 and Array2 items inside them and their check against does contains Array1 and Array2 items as well inside them, same goes with SecondArrayToLookup with their check SecondStringContains, and ThirdArrayToLookup with their check ThirdStringContains. Currently it only returns Second Array to Lookup which only fulfills the condition of SecondArrayToLookup with their check SecondStringContains

.Net Fiddle: https://dotnetfiddle.net/5DZpfL

Thank you

CodePudding user response:

Let's take a look at one of the statements that doesn't evaluate to true:

if (FirstArrayToLookup.All(x => FirstStringContains.All(y => x.Contains(y))))
    Console.WriteLine("First Array to Lookup");

Specifically this secondary .All() query, using the first value contained in FirstArrayToLookup ("FirstArray1"):

FirstStringContains.All(y => x.Contains(y))

This is saying "for the values contained in FirstStringContains ("Array1", "Array2") does "FirstArray1" contain ALL of these values?" So, does the literal value of "FirstArray1" contain both "Array1" AND "Array2"? It only contains "Array1", thus the evaluation of false for that statement.

The second statement is returning true because there is only one value to check against one value.

CodePudding user response:

If you strictly want to match the two sequences element by element (e.g. check whether the first element in FirstArrayToLookup contains the first element in FirstStringContains and the second element in FirstArrayToLookup contains the second element in FirstStringContains; and so on), you can use Enumerable.Zip() to perform element-wise comparison.

For the First*-scenario, you could do:

var allMatch = FirstArrayToLookup
    .Zip(FirstStringContains,
        ( lookupValue, searchValue ) => lookupValue.Contains(searchValue))
    .All(isMatch => isMatch);

The element-wise comparison would then look as follows for the first element:

( "FirstArray1", "Array1" ) => "FirstArray1".Contains("Array1"))

and as follows for the second element:

( "FirstArray2", "Array2" ) => "FirstArray2".Contains("Array2"))

Seeing as both .Contains() will return true, the following .All(isMatch => isMatch) will also return true.

.Zip() will process the two sequences in parallel until the shortest (if any) sequence ends. Therefore, if either sequence is longer than the other (and by that, it is guaranteed that there's not a full element-by-element match), that needs to be addressed before using the .Zip() operation.

I would suggest to create a method, something like the following:

private static bool IsElementWiseMatch(List<string> lookupValues, string[] searchValues)
{
    if (lookupValues.Count != searchValues.Length)
    {
        return false;
    }
    
    return lookupValues
        .Zip(searchValues,
            ( lookupValue, searchValue ) => lookupValue.Contains(searchValue))
        .All(isMatch => isMatch);
}

and call it for each sequence pair:

if (IsElementWiseMatch(FirstArrayToLookup, FirstStringContains))
{
    Console.WriteLine("First Array to Lookup");
}

Example fiddle here.

  • Related