13

Using PHP, is there a function/method/way to check if a variable contains something that would be safe to put into a foreach construct? Something like

//the simple case, would probably never use it this bluntly
function foo($things)
{
    if(isForEachable($things))
    {
        foreach($things as $thing)
        {
            $thing->doSomething();
        }
    }
    else
    {
        throw new Exception("Can't foreach over variable");
    }
}

If your answer is "setup a handler to catch the PHP error", your efforts are appreciated, but I'm looking for something else.

BoltClock
  • 700,868
  • 160
  • 1,392
  • 1,356
Alana Storm
  • 164,128
  • 91
  • 395
  • 599

3 Answers3

17

Well, sort of. You can do:

if (is_array($var) || ($var instanceof Traversable)) {
    //...
}

However, this doesn't guarantee the foreach loop will be successful. It may throw an exception or fail silently. The reason is that some iterable objects, at some point, may not have any information to yield (for instance, they were already iterated and it only makes sense to iterate them once).

See Traversable. Arrays are not objects and hence cannot implement such interface (they predate it), but they can be traversed in a foreach loop.

Artefacto
  • 96,375
  • 17
  • 202
  • 225
  • e.g. DOMNodeList is also a object with its own method but strangely its foreach compatible and its !is_array(...). – thevikas Aug 30 '10 at 05:01
  • 3
    note that objects are foreachable as well, so you may wish to add `|| is_object($var)` to the conditional. – jchook Aug 19 '16 at 02:26
6

PHP 7

Recent versions of PHP have is_iterable() and the iterable pseudo-type.


PHP 5

Since all objects and arrays are "foreachable" in PHP 5+...

function is_foreachable($var) {
  return is_array($var) || is_object($var);
}
jchook
  • 6,690
  • 5
  • 38
  • 40
  • Is_iterable is still not useful tho. It will return false on object that are foreachable. – Brad Feb 14 '23 at 02:49
-2

Check using is_array

if( is_array($things) )
      echo "it is foreachable";
else
      echo "Not it's not foreachable.";
shamittomar
  • 46,210
  • 12
  • 74
  • 78