admin管理员组

文章数量:1387398

I have a script that is taking too long to run and that is causing me This error on ie : a script on this page is causing internet explorer to run slowly.

I have read other threads concerning this error and have learned that there is a way to by pass it by putting a time out after a certain number of iterations.

Can u help me apply a time out on the following function please ?

Basically each time i find a hidden imput of type submit or radio i want to remove and i have a lot of them . Please do not question why do i have a lots of hidden imputs. I did it bc i needed it just help me put a time out please so i wont have the JS error. Thank you

$('input:hidden').each(function(){
    var name = $(this).attr('name');
    if($("[name='"+name+"']").length >1){
        if($(this).attr('type')!=='radio' && $(this).attr('type')!=='submit'){
            $(this).remove();
        }
    }
  });

One of the exemples i found : Bypassing IE's long-running script warning using setTimeout

I have a script that is taking too long to run and that is causing me This error on ie : a script on this page is causing internet explorer to run slowly.

I have read other threads concerning this error and have learned that there is a way to by pass it by putting a time out after a certain number of iterations.

Can u help me apply a time out on the following function please ?

Basically each time i find a hidden imput of type submit or radio i want to remove and i have a lot of them . Please do not question why do i have a lots of hidden imputs. I did it bc i needed it just help me put a time out please so i wont have the JS error. Thank you

$('input:hidden').each(function(){
    var name = $(this).attr('name');
    if($("[name='"+name+"']").length >1){
        if($(this).attr('type')!=='radio' && $(this).attr('type')!=='submit'){
            $(this).remove();
        }
    }
  });

One of the exemples i found : Bypassing IE's long-running script warning using setTimeout

Share Improve this question edited May 23, 2017 at 12:30 CommunityBot 11 silver badge asked Jul 4, 2013 at 12:34 JosephJoseph 3481 gold badge3 silver badges16 bronze badges 7
  • 2 Stop doing $(this), instead, assign it to a variable – Alvin Wong Commented Jul 4, 2013 at 12:35
  • 1 Dude read the code please before menting, putting $this in a variable or leaving it like that changes nothing. – Joseph Commented Jul 4, 2013 at 12:39
  • How many inputs do you have to make such a small script "long-running"? – Bergi Commented Jul 4, 2013 at 12:42
  • learn pure javascript. the .each() loop can be up 90% slower than pure javascript for loop – Jay Harris Commented Jul 4, 2013 at 12:46
  • Thank you Jay , yes you are 100 % right about that i will swap it with a norma for loop for extra performance. – Joseph Commented Jul 4, 2013 at 12:55
 |  Show 2 more ments

5 Answers 5

Reset to default 2

You may want to add input to your jquery selector to filter out only input tags.

if($("input[name='"+name+"']").length >1){

Here's the same code optimised a bit without (yet) using setTimeout():

var $hidden = $('input:hidden'),
    el;
for (var i = 0; i < $hidden.length; i++) {
  el = $hidden[i];
  if(el.type!=='radio' && el.type!=='submit'
             && $("[name='" + el.name + "']").length >1) {

     $(el).remove();
  }
}

Notice that now there is a maximum of three function calls per iteration, whereas the original code had up to ten function calls per iteration. There's no need for, say, $(this).attr('type') (two function calls) when you can just say this.type (no function calls).

Also, the .remove() only happens if three conditions are true, the two type tests and check for other elements of the same name. Do the type tests first, because they're quick, and only bother doing the slow check for other elements if the type part passes. (JS's && doesn't evaluate the right-hand operand if the left-hand one is falsy.)

Or with setTimeout():

var $hidden = $('input:hidden'),
    i = 0,
    el;
function doNext() {
   if (i < $hidden.length) {
      el = $hidden[i];
      if(el.type!=='radio' && el.type!=='submit'
                && $("[name='" + el.name + "']").length >1) {

         $(el).remove();
      }
      i++;
      setTimeout(doNext, 0);
   }
}
doNext();

You could improve either version by changing $("[name='" + el.name + "']") to specify a specific element type, e.g., if you are only doing inputs use $("input[name='" + el.name + "']"). Also you could limit by some container, e.g., if those inputs are all in a form or something.

It looks like the example you cited is exactly what you need. I think if you take your code and replace the while loop in the example (keep the if statement for checking the batch size), you're basically done. You just need the jQuery version of breaking out of a loop.

To risk stating the obvious; traversing through the DOM looking for matches to these CSS selectors is what's making your code slow. You can cut down the amount of work it's doing with a few simple tricks:

Are these fields inside a specific element? If so you can narrow the search by including that element in the selector.

e.g:

$('#container input:hidden').each(function(){
    ...

You can also narrow the number of fields that are checked for the name attribute

e.g:

if($("#container input[name='"+name+"']").length >1){

I'm also unclear why you're searching again with $("[name='"+name+"']").length >1once you've found the hidden element. You didn't explain that requirement. If you don't need that then you'll speed this up hugely by taking it out.

$('#container input:hidden').each(function(){
    var name = $(this).attr('name');
    if($(this).attr('type')!=='radio' && $(this).attr('type')!=='submit'){
        $(this).remove();
    }
});

If you do need it, and I'd be curious to know why, but the best approach might be to restructure the code so that it only checks the number of inputs for a given name once, and removes them all in one go.

Try this:

$("[type=hidden]").remove(); // at the place of each loop

It will take a short time to delete all hidden fields.

I hope it will help.

JSFiddle example

本文标签: Javascript taking too long to runStack Overflow