5 Stimmen

Wie kann ich am schnellsten eine große Anzahl von Kontrollkästchen auswählen und deaktivieren?

Da ich jQuery 1.3+ verwende, verwenden alle bis auf einen zeitlich begrenzten Test das. Der andere ist einfaches Javascript, das ich im Jahr 2000 gefunden habe. Ich habe aufgehört, diesen Weg zu gehen, da es rund 150 Sekunden dauerte, um den Test auszuführen. Ich habe einige jQuery-Optimierungs-Webseiten gelesen, die sich auf die Auswahl eines einzelnen Elements beziehen. Eine '#id' ist der beste Fall für die Verwendung, aber jetzt habe ich das Problem der Ankreuzen aller Kästchen in einer Spalte in einer relativ großen Tabelle mit mehreren Kästchenspalten .

Ich habe eine Seite erstellt, die 20.000 Tabellenzeilen mit zwei Kontrollkästchen-Spalten enthält. Ziel ist es, die zweite Spalte zu markieren und zu sehen, wie lange das gedauert hat, und dann die Markierung zu entfernen und zu sehen, wie lange das gedauert hat. Wir wollen natürlich die niedrigste Zeit. Ich verwende nur IE6 und 7, und in meinem Fall werden alle meine Benutzer dasselbe tun.

20.000 Zeilen, sagen Sie? Das habe ich auch gesagt, aber das geht in die Produktion (außerhalb meiner Hände) und es ist zu spät, das jetzt noch zu ändern. Ich versuche gerade, einen Hail Mary zu werfen, wenn noch 1 Sekunde auf der Uhr ist. Außerdem habe ich gelernt, dass input.chkbox nicht der schnellste Selektor (für IE7) ist! :)

Die Frage ist, gibt es einen besseren Weg, dies zu tun jQuery oder anders? Ich möchte, dass es in weniger als einer halben Sekunde auf meiner Maschine ausgeführt werden.

Damit ihr nicht den ganzen Mist, den ich schon gemacht habe, noch einmal abtippen müsst, hier ist das Testmaterial, das ich mir ausgedacht habe:

Aktualisiert am Morgen des 14.4. um weitere Zeitversuche aufzunehmen:

<form id="form1" runat="server">
    <div>
        <a href="#" id="one">input[id^='chkbox'][type='checkbox']</a><br />
        <a href="#" id="two">#myTable tr[id^='row'] input[id^='chkbox'][type='checkbox']</a><br />
        <a href="#" id="three">#myTable tr.myRow input[id^='chkbox'][type='checkbox']</a><br />
        <a href="#" id="four">tr.myRow input[id^='chkbox'][type='checkbox']</a><br />
        <a href="#" id="five">input[id^='chkbox']</a><br />
        <a href="#" id="six">.chkbox</a><br />
        <a href="#" id="seven">input.chkbox</a><br />
        <a href="#" id="eight">#myTable input.chkbox</a><br />

        <a href="#" id="nine">"input.chkbox", "tr"</a><br />
        <a href="#" id="nine1">"input.chkbox", "tr.myRow"</a><br />
        <a href="#" id="nine2">"input.chkbox", "#form1"</a><br />
        <a href="#" id="nine3">"input.chkbox", "#myTable"</a><br />

        <a href="#" id="ten">input[name=chkbox]</a><br />
        <a href="#" id="ten1">"input[name=chkbox]", "tr.myRow"</a><br />
        <a href="#" id="ten2">"input[name=chkbox]", "#form1"</a><br />
        <a href="#" id="ten3">"input[name=chkbox]", "#myTable"</a><br />

        <a href="#" id="ten4">"input[name=chkbox]", $("#form1")</a><br />
        <a href="#" id="ten5">"input[name=chkbox]", $("#myTable")</a><br />

        <a href="#" id="eleven">input[name='chkbox']:checkbox</a><br />
        <a href="#" id="twelve">:checkbox</a><br />
        <a href="#" id="twelve1">input:checkbox</a><br />
        <a href="#" id="thirteen">input[type=checkbox]</a><br />

        <div>
            <input type="text" id="goBox" /> <button id="go">Go!</button>
            <div id="goBoxTook"></div>
        </div>

        <table id="myTable">
            <tr id="headerRow"><th>Row #</th><th>Checkboxes o' fun!</th><th>Don't check these!</th></tr>
            <% for(int i = 0; i < 20000;i++) { %>
            <tr id="row<%= i %>" class="myRow">
                <td><%= i %> Row</td>
                <td>
                    <input type="checkbox" id="chkbox<%= i %>" name="chkbox" class="chkbox" />
                </td>
                <td>
                    <input type="checkbox" id="otherBox<%= i %>" name="otherBox" class="otherBox" />
                </td>
            </tr>
            <% } %>
        </table>
    </div>

    <script type="text/javascript" src="<%= ResolveUrl(" ~/") %>Javascript/jquery.1.3.1.min.js"></script>
    <script type="text/javascript">

        $(function () {
            function run(selectorText, el) {
                var start = new Date();
                $(selectorText).attr("checked", true);
                var end = new Date();
                var timeElapsed = end - start;
                $(el).after("<br />Checking Took " + timeElapsed + "ms");

                start = new Date();
                $(selectorText).attr("checked", false);
                end = new Date();
                timeElapsed = end - start;
                $(el).after("<br />Unchecking Took " + timeElapsed + "ms");
            }

            function runWithContext(selectorText, context, el) {
                var start = new Date();
                $(selectorText, context).attr("checked", true);
                var end = new Date();
                var timeElapsed = end - start;
                $(el).after("<br />Checking Took " + timeElapsed + "ms");

                start = new Date();
                $(selectorText, context).attr("checked", false);
                end = new Date();
                timeElapsed = end - start;
                $(el).after("<br />Unchecking Took " + timeElapsed + "ms");
            }

            $("#one").click(function () {
                run("input[id^='chkbox'][type='checkbox']", this);
            });

            $("#two").click(function () {
                run("#myTable tr[id^='row'] input[id^='chkbox'][type='checkbox']", this);
            });

            $("#three").click(function () {
                run("#myTable tr.myRow input[id^='chkbox'][type='checkbox']", this);
            });

            $("#four").click(function () {
                run("tr.myRow input[id^='chkbox'][type='checkbox']", this);
            });

            $("#five").click(function () {
                run("input[id^='chkbox']", this);
            });

            $("#six").click(function () {
                run(".chkbox", this);
            });

            $("#seven").click(function () {
                run("input.chkbox", this);
            });

            $("#eight").click(function () {
                run("#myTable input.chkbox", this);
            });

            $("#nine").click(function () {
                runWithContext("input.chkbox", "tr", this);
            });

            $("#nine1").click(function () {
                runWithContext("input.chkbox", "tr.myRow", this);
            });
            $("#nine2").click(function () {
                runWithContext("input.chkbox", "#form1", this);
            });
            $("#nine3").click(function () {
                runWithContext("input.chkbox", "#myTable", this);
            });

            $("#ten").click(function () {
                run("input[name=chkbox]", this);
            });

            $("#ten1").click(function () {
                runWithContext("input[name=chkbox]", "tr.myRow", this);
            });

            $("#ten2").click(function () {
                runWithContext("input[name=chkbox]", "#form1", this);
            });

            $("#ten3").click(function () {
                runWithContext("input[name=chkbox]", "#myTable", this);
            });

            $("#ten4").click(function () {
                runWithContext("input[name=chkbox]", $("#form1"), this);
            });

            $("#ten5").click(function () {
                runWithContext("input[name=chkbox]", $("#myTable"), this);
            });

            $("#eleven").click(function () {
                run("input[name='chkbox']:checkbox", this);
            });

            $("#twelve").click(function () {
                run(":checkbox", this);
            });

            $("#twelve1").click(function () {
                run("input:checkbox", this);
            });

            $("#thirteen").click(function () {
                run("input[type=checkbox]", this);
            });

            $('#go').click(function () {
                run($('#goBox').val(), this);
            });
        });
    </script>
</form>

9voto

rball Punkte 6845

input[name=chkbox] ist auf meinem Rechner unter IE7 der schnellste jQuery-Selektor.

Unchecking Took 2453ms
Checking Took 2438ms
Unchecking Took 2438ms
Checking Took 2437ms
Unchecking Took 2453ms
Checking Took 2438ms

Eingabe.chkbox und...

Unchecking Took 2813ms
Checking Took 2797ms
Unchecking Took 2797ms
Checking Took 2797ms
Unchecking Took 2813ms
Checking Took 2797ms

input:checkbox.chkbox gebunden zu sein scheinen

Unchecking Took 2797ms
Checking Took 2797ms
Unchecking Took 2813ms
Checking Took 2781ms

.chkbox dauert fast doppelt so lange wie die input.chkbox

Unchecking Took 4031ms
Checking Took 4062ms
Unchecking Took 4031ms
Checking Took 4062ms

Die javascript for-Schleife ist bei weitem das Schlimmste, die bei:

Checking Took 149797ms

150 Sekunden! Es sperrt auch den Browser. Das macht mich wirklich beeindruckt mit jQuery. Ich habe ehrlich gesagt nicht erwartet, dass es so langsam ist. Wahrscheinlich, weil ich über jedes einzelne Element übergeben, die es dann zu finden ist...

Das war auch für mich sehr interessant:

input[id^='chkbox']

Unchecking Took 3031ms
Checking Took 3016ms

nahm weniger Zeit als:

input[id^='chkbox'][type='checkbox']

Unchecking Took 3375ms
Checking Took 3344ms

Ich dachte, da ich mehr Filter eingestellt habe, würde es schneller gehen. Nix da!

Wenn Sie noch mehr Pfade für das Kontrollkästchen angeben, wird es viel langsamer:

#myTable tr[id^='row'] input[id^='chkbox'][type='checkbox']

Checking Took 10422ms

Es wurde nicht einmal das zweite Häkchen entfernt, da ich gefragt wurde, ob ich weiterhin Skripte auf meinem Computer ausführen möchte. Verrückt! :P

Update Morgen 4/14:

Jemand hat den Kontext angesprochen: Ich habe tatsächlich ein paar davon gemacht, und zu meiner Überraschung und entgegen den Aussagen vieler Leute im Internet im IE7 waren diese langsamer ! Hier sind die Zeiten, die ich mit verschiedenen Kontexten in Verbindung mit den oben genannten schnelleren Selektoren erhalten habe:

"input.chkbox", "tr"

Checking Took 8546ms

"input.chkbox", "tr.myRow"

Checking Took 8875ms

"input.chkbox", "#form1"

Unchecking Took 3032ms
Checking Took 3000ms

"input.chkbox", "#meineTabelle"

Unchecking Took 2906ms
Checking Took 2875ms

Aktueller Gewinner (noch): input[name=chkbox]

Unchecking Took 2469ms
Checking Took 2453ms

"input[name=chkbox]", "tr.myRow"

Checking Took 9547ms

"input[name=chkbox]", "#form1"

Unchecking Took 3140ms
Checking Took 3141ms

"input[name=chkbox]", "#myTable"

Unchecking Took 2985ms
Checking Took 2969ms

Update 2 Morgen 4/14

Ich dachte, ich hätte vielleicht eine bessere, nachdem ich einen Syntaxunterschied zu http://beardscratchers.com/journal/jquery-its-all-about-context . Es scheint, dass diese NICHT dasselbe sind wie sie liefern etwas bessere Zeiten, aber immer noch nicht besser als der nicht kontextgebundene Selektor - verflixt.

"input[name=chkbox]", $("#form1")

Unchecking Took 3078ms
Checking Took 3000ms
Unchecking Took 3078ms
Checking Took 3016ms

"input[name=chkbox]", $("#myTable")

Unchecking Took 2938ms
Checking Took 2906ms
Unchecking Took 2938ms
Checking Took 2921ms

Update 3 Morgen 4/14

Russ wollte, dass ich diese ausprobiere, sie wählen ALLE Boxen aus, aber es war wieder interessant:

:checkbox

Unchecking Took 8328ms
Checking Took 6250ms

input:checkbox

Unchecking Took 5016ms
Checking Took 5000ms

-> Schnellste?!?! input[type=checkbox]

Unchecking Took 4969ms
Checking Took 4938ms

Die Tatsache, dass der dritte Platz dort oben der schnellste ist, ist recht interessant, denn das widerspricht dem, was ich gedacht hätte. Warum sollte (zumindest im IE7) die :checkbox nicht einfach die type=checkbox verwenden, um eine schnellere Zeit zu erreichen? Die Ergebnisse liegen sehr dicht beieinander, aber die Überprüfung hat 62ms weniger Zeit in Anspruch genommen. Und warum unterscheiden sich die ersten beiden überhaupt? Gibt es außer einem Eingabefeld noch ein anderes Element, das ein Kontrollkästchen enthalten kann?

5voto

Codebrain Punkte 5365

Ich habe nicht getestet, aber Sie könnten versuchen, ein Array[] der Checkbox Verweise auf Seite laden dann einfach iterieren über das jedes Mal, wenn Sie eine Änderung vornehmen möchten?

Sie würden die Kosten für die Leistung beim Laden der Seite zahlen, aber es könnte schneller sein, als jedes Mal den DOM abzulaufen. Hey, zumindest würden Sie das schwere Heben in Benutzer "down time" (wie lange dauert es für die Menschen zu lokalisieren und klicken Sie auf die Abwahl / Auswahl-Optionen) durchführen.

2voto

Chris Brandsma Punkte 11525

Mein einziger Vorschlag wird wahrscheinlich auch nicht funktionieren. Wechseln Sie den Browser. Aber ich hatte nur ein Unternehmen, das dem tatsächlich zugestimmt hat. Wir haben das Unternehmen auf FireFox umgestellt, und bestimmte Benutzer sind zu Google Chrome gewechselt. Der IE ist bei JavaScript einfach zu langsam.

Sie können auch versuchen, die Jquery-Abfrageliste im Voraus zu speichern.

Wenn alles andere versagt, lösen Sie das Problem mit Psychologie. Das bedeutet, dass Sie den Benutzer wissen lassen müssen, dass etwas lange dauern wird. Zeigen Sie ein "Bitte warten"-Div an, während die Funktion ausgeführt wird. Auf diese Weise weiß der Benutzer, dass der Browser nicht einfach blockiert ist, und er weiß, wann er sich wieder an die Arbeit machen kann. Ich habe schon so manche langsame Seite dadurch "gelöst", dass ich genau das getan habe.

1voto

Russ Cam Punkte 120837

Haben Sie versucht, die jQuery-Selektoren mit einer context um zu sehen, ob dies die Leistung verbessert? Vermutlich werden die Steuerelemente innerhalb eines ASP.NET-Formulars sein, und vielleicht ein anderes eindeutig identifizierbares Element?

Zum Beispiel, wenn Sie Folgendes haben

$("input[id^='chkbox']")

Versuchen Sie es mit

$("input[id^='chkbox']", "#myFormID")

Hier ist ein Artikel von BeardScratchers zum Kontext

EDIT:

Nach Ihren Aktualisierungen scheinen 2,45 bis 6 Sekunden die schnellste Zeit zu sein, die Sie unter den gegebenen Umständen erreichen können.

Nur der Vollständigkeit halber: Haben Sie die folgenden Selektoren ausprobiert?

$(':checkbox')
$('input[type=checkbox]')

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X