8
\$\begingroup\$

Currently I check whether a string contains all words from an array like this:

function contains($string, array $array) {
    $count = 0;
    foreach($array as $value) {
        if (false !== stripos($string,$value)) {
            ++$count;
        };
    }
    return $count == count($array);
}

Example call:

$string = 'Hello, people at Stackoverflow';
$array = array('Hello', 'People');

if (contains($string, $array)) {
    print 'This is true for the given example';
}

I wonder whether a more elegant, faster or even built-in way exists to improve this?

\$\endgroup\$

migrated from stackoverflow.com Sep 22 '14 at 12:29

This question came from our site for professional and enthusiast programmers.

  • 1
    \$\begingroup\$ No need to count. Just reverse condition and return false from loop. Whole iteration pass would mean true. \$\endgroup\$ – shudder Sep 8 '14 at 12:56
3
\$\begingroup\$

You could use something like this:

$string = 'Hello, people at Stackoverflow';
$array = array('Hello', 'People');
$i = count(array_intersect($array, explode(" ", preg_replace("/[^A-Za-z0-9' -]/", "", $string))));
echo ($i) ? "found ($i)" : "not found";

Outputs:

found (1)

(array_intersect is case sensitive)

Or if you'd like to make it a function, then you could do something like this:

function contains($needles, $haystack) {
    return count(array_intersect($needles, explode(" ", preg_replace("/[^A-Za-z0-9' -]/", "", $haystack))));
}

$string = 'Hello, people at Stackoverflow';
$array = array('Hello', 'People');
$i = contains($array, $string);
echo ($i) ? "found ($i)" : "not found";
\$\endgroup\$
2
\$\begingroup\$

I don't think you needed to change much. This version terminates when a word isn't found and ensures that the first parameter and every word in the array are strings.

function contains_all($str,array $words) {
    if(!is_string($str))
        { return false; }

    foreach($words as $word) {
        if(!is_string($word) || stripos($str,$word)===false)
            { return false; }
    }
    return true;
}

Breaking words up as others have done:

function contains_all_s($str,array $words) {
    if(!is_string($str))
        { return false; }
    return count(
        array_intersect(
        #   lowercase all words
            array_map('strtolower',$words),
        #   split by non-alphanumeric chars (hyphens are safe)
            preg_split('/[^a-z0-9\-]/',strtolower($str))
        )
    ) == count($words);
}
\$\endgroup\$
1
\$\begingroup\$

Maybe use explode(' ',$string) and then check if the array is a subset of the string-array using array_diff().

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.