1--TEST-- 2Iterator exceptions in foreach by value 3--FILE-- 4<?php 5class IT implements Iterator { 6 private $n = 0; 7 private $count = 0; 8 private $trap = null; 9 10 function __construct($count, $trap = null) { 11 $this->count = $count; 12 $this->trap = $trap; 13 } 14 15 function trap($trap) { 16 if ($trap === $this->trap) { 17 throw new Exception($trap); 18 } 19 } 20 21 function rewind(): void {$this->trap(__FUNCTION__); $this->n = 0;} 22 function valid(): bool {$this->trap(__FUNCTION__); return $this->n < $this->count;} 23 function key(): mixed {$this->trap(__FUNCTION__); return $this->n;} 24 function current(): mixed {$this->trap(__FUNCTION__); return $this->n;} 25 function next(): void {$this->trap(__FUNCTION__); $this->n++;} 26} 27 28foreach(['rewind', 'valid', 'key', 'current', 'next'] as $trap) { 29 $obj = new IT(3, $trap); 30 try { 31 // IS_CV 32 foreach ($obj as $key => $val) echo "$val\n"; 33 } catch (Exception $e) { 34 echo $e->getMessage() . "\n"; 35 } 36 unset($obj); 37 38 try { 39 // IS_VAR 40 foreach (new IT(3, $trap) as $key => $val) echo "$val\n"; 41 } catch (Exception $e) { 42 echo $e->getMessage() . "\n"; 43 } 44 45 try { 46 // IS_TMP_VAR 47 foreach ((object)new IT(2, $trap) as $key => $val) echo "$val\n"; 48 } catch (Exception $e) { 49 echo $e->getMessage() . "\n"; 50 } 51} 52?> 53--EXPECT-- 54rewind 55rewind 56rewind 57valid 58valid 59valid 60key 61key 62key 63current 64current 65current 660 67next 680 69next 700 71next 72