-
Notifications
You must be signed in to change notification settings - Fork 27.5k
forEach should support break #263
Comments
+1 for this feature I used just return true / false (break / continue) in couple of projects, not as verbosing as return forEach.break(), but shorter... (don't forget, outside angular, you have to type angular.forEach.break()) Or returning numbers, that would allow breaking nested loops as well:
Or might be more helpful to return key of the item that caused the break... |
we discussed this with Misko some time ago and realized that the implementation must be compatible with native forEach, which means that we'll have to use an exception (directly or indirectly) to abort the execution. |
Don't know - I don't like exceptions and especially when it comes to using exception for changing control flow... |
It's not that I like it, but rather that it is the only option we have |
+1 Needed this today. I like your proposed solution, @IgorMinar. |
Sorry.. I don't think that this will happen because if we start throwing exceptions to control execution flow we'll make debugging of apps a nightmare (break on exception will see false positives). Maybe one day the native forEach will have an api to break. until then we can't do much about it. I'm going to sadly close this issue since its obsolete. :-/ |
Native each and every are just like forEach, except they can stop... or Herby Igor Minar wrote:
|
Herby Vojčík wrote:
|
Why can't you |
continue and break cause exceptions which /could/ be caught (if you decided this was the road to go down) FF:
Chrome: instead of coding all these strings in, you could catch an illegal break and continue during init, then match that exception string in the forEach code |
These are syntax errors, not runtime errors, and so they are of no help to On Fri, Sep 7, 2012 at 8:48 AM, jamie-pate notifications@github.com wrote:
|
@Herby Array#forEach doesn't have any way of breaking or escaping the loop. |
@IgorMinar I said |
Any possibility of having a new function called |
This is a must have feature, otherwise we end up using for(..). Or as saurabhnanda said, add another function. |
damn, how is this not in, 2 years later? |
Perhaps angular could add an .every() method? |
One thing I don't get from the thread is why delegating to the native forEach is so important. The feature could be implemented with a for loop I guess. What am I missing? |
Efficiency? Are there any benchmarks around how much faster native forEach On Wed, Apr 17, 2013 at 12:01 PM, Christoph Burgdorf <
|
@saurabhnanda definitely not the case - that is the whole purpose behind lodash's loops. http://jsperf.com/angularjs-lodash-underscore-foreach/3 I would venture a guess that it is purely for consistency (jQuery's notwithstanding). |
Wow! This is really interesting. Why is it that a simple for-loop in plain On Wed, Apr 17, 2013 at 12:07 PM, patrick kettner
|
@saurabhnanda mostly because the for loops have been optimized as much as possible, and the native methods are new, so they haven't been as heavily optimized. as to why lodash is slower, i'm not sure, other than they are using a while loop rather than a for loop. |
It would be nice to get an official statement from the core team again on why we would not implement that feature in the fashion lo-dash does. |
@patrickkettner @saurabhnanda because you are calling an anonymous function everytime you iterate. less calls (aka plain loop) is obviously faster than thousands of functions calls in some ms', but of course, in some situations the "slower" is unnoticeable if you are iterating over less than 40 items for example (the jsperf is iterating over 1000 times) |
@pocesar ah-ha, thanks for the explanation. Sleepy minds do not valid test cases make. @saurabhnanda looks like someone updated that test with a anonymous function version of the for loop |
That was me, final (final) test is here: (added every and fixed rawfor so it actually accesses the array) native forEach does a lot more than the for loop, it has to check stuff! |
However, angular.forEach is slower than lodash and lodash does support break.. |
forEach shouldn't support break, every/some does. Christoph Burgdorf wrote:
|
So the only reason that wasn't implemented yet is to keep the same semantics as the native forEach? Fuck yeah, then call it every or some :) |
…Each()`) NOTICE: This is just a POC implementation to see if there is interest for the feature. There are many performance improvements to be made and tests to be written (and run). Sometimes it is useful to be able to iterate over an array/object, but abort the operation as soon as some condition is met. This commit adds two methods that provide this functionality: 1. some: Test whether some element in the array/object passes the test implemented by the provided function. 2. every: Test whether every element in the array/object passes the test implemented by the provided function. Closes angular#263
…Each()`) NOTICE: This is just a POC implementation to see if there is interest for the feature. There are many performance improvements to be made and tests to be written (and run). Sometimes it is useful to be able to iterate over an array/object, but abort the operation as soon as some condition is met. This commit adds two methods that provide this functionality: 1. some: Test whether some element in the array/object passes the test implemented by the provided function. 2. every: Test whether every element in the array/object passes the test implemented by the provided function. Closes angular#263
…Each()`) NOTICE: This is just a POC implementation to see if there is interest for the feature. There are many performance improvements to be made and tests to be written (and run). Sometimes it is useful to be able to iterate over an array/object, but abort the operation as soon as some condition is met. This commit adds two methods that provide this functionality: 1. some: Test whether some element in the array/object passes the test implemented by the provided function. 2. every: Test whether every element in the array/object passes the test implemented by the provided function. Closes angular#263
…Each()`) NOTICE: This is just a POC implementation to see if there is interest for the feature. There are many performance improvements to be made and tests to be written (and run). Sometimes it is useful to be able to iterate over an array/object, but abort the operation as soon as some condition is met. This commit adds two methods that provide this functionality: 1. some: Test whether some element in the array/object passes the test implemented by the provided function. 2. every: Test whether every element in the array/object passes the test implemented by the provided function. Closes angular#263
Shouldn't spec be written based on community needs? Just asking... I confirm I've seen this requirement in multiple projects and redirecting developers to vanilla JS is just not the way to go in a normalized world/framework. |
…Each()`) NOTICE: This is just a POC implementation to see if there is interest for the feature. There are many performance improvements to be made and tests to be written (and run). Sometimes it is useful to be able to iterate over an array/object, but abort the operation as soon as some condition is met. This commit adds two methods that provide this functionality: 1. some: Test whether some element in the array/object passes the test implemented by the provided function. 2. every: Test whether every element in the array/object passes the test implemented by the provided function. Closes angular#263
…Each()`) NOTICE: This is just a POC implementation to see if there is interest for the feature. There are many performance improvements to be made and tests to be written (and run). Sometimes it is useful to be able to iterate over an array/object, but abort the operation as soon as some condition is met. This commit adds two methods that provide this functionality: 1. some: Test whether some element in the array/object passes the test implemented by the provided function. 2. every: Test whether every element in the array/object passes the test implemented by the provided function. Closes angular#263
I don't know what the reasoning TC39 had for not supporting this feature, Maybe you could do the research and see if we could revive the discussion On Mon, Oct 27, 2014, 11:59 AM Dragos Rusu notifications@github.com wrote:
|
??? They have differently named method (.every) just for that. Herby Igor Minar wrote:
|
@IgorMinar : sorry to have lead to confusion - I was referring to what @Herby is saying, that is: implement angular.every and return false there. The reason for adding it in angular would be to iterate on arrays or objects, as @gkalpak was mentioning in #9797 . If you consider this to be useful, lets discuss with @gkalpak (I'm offering to contribute with code as well) and let's make a PR for this. Please confirm here or in #9797. As for changing spec for .forEach - even if I would definitely advocate to that, I consider that guys at Mozilla have better visibility then I do, so if they chose to use .every, they must have had a really good reason (not compat, because people just use "return;" and a strict comparison with FALSE would have done the job). |
My understanding is that we don't want to have any of those utilities in 2.0 so adding more to 1.x doesn't make much sense, IMO. Those little utilities proved to trigger a lot of issues / and endless discussions (this one being good example) so once again - this would be -1 from my side. Let's have AngularJS focus on what it does best instead of turning it into a general purpose utility. This is just my opinion, though. |
@pkozlowski-opensource : you have your point, it is true. If again, forEach is not to be removed in 1.x or 2.0, then why would we use AngularJS forEach when we need to iterate on each item and another utility method (or default vanilla JS) when we want to stop at one point in our iteration. This does not make sense at all. One of the reasons that jquery was made was also to normalize development (not only browser support *). So pushing back to developers to do these stuff in their own way should be either systematically addressed ("do your own utils" or "use our utils" - not BOTH). |
v2 won't provide any of these helper methods. We'll rely on native apis or We won't add any more of these to 1.x for reasons Pawel mentioned. And we won't remove any from 1.x because that would cause too much trouble. I hope this explains our thinking well. On Wed, Oct 29, 2014, 3:38 AM Dragos Rusu notifications@github.com wrote:
|
Sounds reasonable and systematically addressed. |
Thanks! On Wed, Oct 29, 2014, 8:15 AM Dragos Rusu notifications@github.com wrote:
|
For people who don't want to integrate a big library into their app for EACH, check #9797 (comment) . |
I'd recommend checking out https://www.npmjs.org/package/lodash.foreach instead. |
@IgorMinar: "v2 won't provide any of these helper methods" - does this mean that angular.forEach will not be available in v2? If it's in effect deprecated, this could be good to mention in https://docs.angularjs.org/api/ng/function/angular.forEach. Those who read that and switch to a non-deprecated solution any time before the release of v2 will have an easier migration ahead. |
Yeah. Definitely a good advise for people to start using external libraries or vanilla JS for iterations. |
+1 |
@danieljameswilliams: As the issue has had significant discussion and a resolution with a follow-up question, would you like to clarify what do you wish to support with the +1? The original request for forEach to support break, or @IgorMinar's resolution that it won't be implemented, or the request to clarify whether forEach will be deprecated altogether? |
@Daedalon My "+1" was for the implementation for break; and continue; |
+1 |
+1 with function return (no exceptions) |
+1 |
wtf? +1!!! |
+1 |
This is a closed issue and the reasons for not supporting break are outlined in these comments: #263 (comment) and #263 (comment). Why there's no equivalent every() / some() can be read here: #263 (comment) I'm locking this issue as discussion (or +1) in closed threads isn't leading anywhere. |
while
continue
support is already supported by accident, there is no way to do abreak
.continue
can be done by a simple return already://prints all elements but 2
forEach([1,2,3,4], function(i) {
if (i==2) return;
console.log(i);
}
break
on the other hand isn't possible to achieve this way, we need to modify forEach to do that. There are three options;I'm not a big fan of using exceptions to control execution flow in non-exceptional cases, so I'm for the second approach. Here is my proposal:
//prints all elements until 2 is reached == only "1"
forEach([1,2,3,4], function(i) {
//break() is a function that returns an immutable object,
//e.g. an empty string
if (i==2) return forEach.break();
console.log(i);
}
I also considered the third approach, but since you'll have to use return if you want to break from the middle of an iterator anyway, we might prevent issues with accidentally forgetting to return.
This third approach would from the user perspective look exactly the same as the code for the second approach above. From angular implementation point of view, things would be more complicated.
When this feature is implemented, we should look at our existing
forEach
instances and add break where needed.We should also properly document both
continue
andbreak
scenarios.The text was updated successfully, but these errors were encountered: