Newsgroups: php.internals Path: news.php.net Xref: news.php.net php.internals:80662 Return-Path: Mailing-List: contact internals-help@lists.php.net; run by ezmlm Delivered-To: mailing list internals@lists.php.net Received: (qmail 76140 invoked from network); 16 Jan 2015 21:16:13 -0000 Received: from unknown (HELO lists.php.net) (127.0.0.1) by localhost with SMTP; 16 Jan 2015 21:16:13 -0000 Authentication-Results: pb1.pair.com header.from=yohgaki@gmail.com; sender-id=pass Authentication-Results: pb1.pair.com smtp.mail=yohgaki@gmail.com; spf=pass; sender-id=pass Received-SPF: pass (pb1.pair.com: domain gmail.com designates 209.85.216.172 as permitted sender) X-PHP-List-Original-Sender: yohgaki@gmail.com X-Host-Fingerprint: 209.85.216.172 mail-qc0-f172.google.com Received: from [209.85.216.172] ([209.85.216.172:62663] helo=mail-qc0-f172.google.com) by pb1.pair.com (ecelerity 2.1.1.9-wez r(12769M)) with ESMTP id 2F/76-43627-D9F79B45 for ; Fri, 16 Jan 2015 16:16:13 -0500 Received: by mail-qc0-f172.google.com with SMTP id i8so10306847qcq.3 for ; Fri, 16 Jan 2015 13:16:11 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20120113; h=mime-version:sender:in-reply-to:references:from:date:message-id :subject:to:cc:content-type; bh=tebXmErkJhfZInZFcBFYEZw6WjOtUdWjfRLabyYnOT8=; b=GJJS4A8hOyRjjfNcgGhQBm7j1SermKLw0GTtZyNCF7Z/ihnVb2YSpmM/UIKHI8/51F EvDfhlFGkxLuvn35lAznzZJs/Dnvj+yyTUIjklNFBD+Zc5ai+sJVn3rxOr/TK0cw6OPh WomhJijEUf8vzi37fpj2JrirmIkIM7uhH7JG7dAnzCZV+7XgvR1g+goxky7cmurI0QyZ cZ3w5lhxzmIJs3Bx7oTyTViqv0hh9HHJUd+FHtqcqGtZXwdWs+pEKVqFeKF6E4hCqEGp zMB3hileogyap+N/gW8GewotnGAlektFxR3J1hhb9ytIBLILU+N0XKXzZ2Avign6F4Fh 58Xg== X-Received: by 10.140.90.112 with SMTP id w103mr16017680qgd.65.1421442970883; Fri, 16 Jan 2015 13:16:10 -0800 (PST) MIME-Version: 1.0 Sender: yohgaki@gmail.com Received: by 10.229.93.70 with HTTP; Fri, 16 Jan 2015 13:15:30 -0800 (PST) In-Reply-To: <54B93AAD.6080308@gmail.com> References: <54B93AAD.6080308@gmail.com> Date: Sat, 17 Jan 2015 06:15:30 +0900 X-Google-Sender-Auth: ahowgeQP9ey22W58mDqM-UW61PA Message-ID: To: Rowan Collins Cc: "internals@lists.php.net" Content-Type: multipart/alternative; boundary=001a11c11a98591c9b050ccb7ba4 Subject: Re: [PHP-DEV] Fixing strange foreach behavior. From: yohgaki@ohgaki.net (Yasuo Ohgaki) --001a11c11a98591c9b050ccb7ba4 Content-Type: text/plain; charset=UTF-8 Hi Rowan, On Sat, Jan 17, 2015 at 1:22 AM, Rowan Collins wrote: > Yasuo Ohgaki wrote on 16/01/2015 08:40: > >> Hi all, >> >> Take a look at >> >> http://3v4l.org/HbVnd >> >> foreach should not affect internal(zval) array position, but it does. >> I'm not sure why foreach works this way, but HHVM behavior is >> reasonable. IMHO. >> >> PHP 7 would be perfect opportunity fix this behavior. >> Any comments? >> > > I seem to remember somebody mentioning that the pointer is reused in some > situations and not others. I think the reason is efficiency - we have a > pointer associated with each array, which is rarely used, so why not borrow > it for foreach? (Answer: because it causes the oddity you just spotted. :P) > Right. foreach should not affect internal(zval) position pointer, but it does. > > For instance, if you put a reset() in the middle of the foreach loop, it > doesn't interrupt the progress of the loop, but does cause it to be tracked > separately and output "Apple" after the loop finishes: > http://3v4l.org/KTCrI > > There are other weird cases, like nesting two foreach loops over the same > variable: > - with a true array, the loops are independent (both loops see the full > set of values): http://3v4l.org/lJTQG > - with a rewindable Traversable, such as SimpleXMLElement, they interact > (the inner loop sees all values, but the outer loop doesn't continue after > the inner one completes): http://3v4l.org/fs2Jv > - with a non-rewindable Traversable, such as a Generator, PHP tries to > rewind and gives a fatal error, while HHVM simply uses up the last values > of the generator on the inner loop (possibly a bug?): > http://3v4l.org/BYOmQ > > My conclusion: don't try and nest foreach or any related constructs using > the same variable, because the behaviour is not guaranteed to be in any way > sane. > Nesting foreach is strange, too. There are two issues - array nesting does not work as it seems - generator nesting does not work at all Besides generator, current behavior is strange. It's matter of using external position pointer for arrays, isn't it? How about make foreach behaves sane manner by PHP 7? It's rare that program uses internal position pointer, but it's a basic language construct. Basic language construct should behave intuitive way. IMHO. Regards, -- Yasuo Ohgaki yohgaki@ohgaki.net --001a11c11a98591c9b050ccb7ba4--