2 Stimmen

Warum ist jqGrid sehr langsam, wenn die Anzahl der angezeigten Zeilen zunimmt?

Wenn ich nur eine kleine Menge pro Seite anzeige, geht es schnell und sehr gut. Wenn ich es auf 100 oder mehr erhöhe, wird es langsam. Bei 1000 ist es unerträglich! Dies ist der Code, der für das Zeichnen des Rasters verwendet wird:

 $("#stSearchTermsGrid").jqGrid({
        mtype: "POST",
        postData:{},
        datatype: function(postdata) {
            $.ajax({
                url: 'ajax/ajax_termsSearchGridSimple.php',
                data: postdata,
                async: false,
                dataType: "xml",
                error: function(){
                    alert('Fehler beim Laden des XML-Dokuments');
                },
                success: function(data,stat,xmldata){
                    //Fehler überprüfen
                    var $error=$(data).find('error').text();
                    if($error!="0")
                    {
                        messageBox("Fehler",$error);
                        return;
                    }
                    //Inhalt
                    var $content=$(data).find('content').text();
                    if($content!="0")
                    {
                        var thegrid = $("#stSearchTermsGrid")[0];
                        thegrid.addXmlData(xmldata.responseXML);
                    }
                }
            });
        },
        colNames:["tId","term", "revTerm", "uType","freq","description","fId","facet","modifiedTime"],
        colModel:[
            //tId
            {name:'tId',index:'tId',align:"center",searchoptions:{sopt:['eq','ne','lt','le','gt','ge','in','ni']}},
            //Begriff (Änderbar)
            {name:'term',index:'term',searchoptions:{sopt:['eq','ne','in','ni','bw','bn','ew','en','cn','nc']},editable:true,edittype:'text',editoptions:{size:20},editrules:{required:true},formoptions:{elmsuffix:'(*)'}},
            //rückläufiger Begriff (Änderbar)
            {name:'revTerm',index:'revTerm',searchoptions:{sopt:['eq','ne','in','ni','bw','bn','ew','en','cn','nc']},editable:true,edittype:'text',editoptions:{size:20},editrules:{required:true},formoptions:{elmsuffix:'(*)'}},
            //uType (Änderbar)
            {name:'uType',index:'uType',align:"center",searchoptions:{sopt:['eq','ne','in','ni']},editable:true,edittype:'select',editoptions:{value:{'':'beliebig','NPU':'Eigenname','NU':'Substantiv','VU':'Verb'}}},
            //Häufigkeit
            {name:'freq',index:'freq',align:"center",searchoptions:{sopt:['eq','ne','lt','le','gt','ge','in','ni']}},
            //Beschreibung (Änderbar)
            {name:'description',index:'description',searchoptions:{sopt:['bw','bn','ew','en','cn','nc']},editable:true,edittype:'textarea',editoptions:{rows:"3"}},
            //fId
            {name:'fId',index:'fId',align:"center",searchoptions:{sopt:['eq','ne','lt','le','gt','ge','in','ni']}},
            //facet
            {name:'facet',index:'facet',searchoptions:{sopt:['eq','ne','in','ni','bw','bn','ew','en','cn','nc']}},
            //Geänderte Zeit
            {name:'modifiedTime',index:'modifiedTime',align:"center",searchoptions:{sopt:['eq','ne','lt','le','gt','ge','bw','bn','ew','en','cn','nc']}}
        ],
        gridComplete: function(){
            var $ids=$("#stSearchTermsGrid").jqGrid('getDataIDs');
            for($i=0;$i<$ids.length;$i++){
                var $reference="G";
                //Spalten aktualisieren
                $("#stSearchTermsGrid").jqGrid('setRowData',$ids[$i],{"reference":$reference});

                //Färbung der kürzlich klassifizierten Zeile
                var $colorRecentlyModified = '#DFFC91';
                var modifiedTime = $("#stSearchTermsGrid").jqGrid('getCell',$ids[$i],'modifiedTime');
                var timeDiff = Math.abs(new Date() - new Date(modifiedTime.replace(/-/g,'/')));
                // 86400000 ist die Anzahl der Millisekunden in einem Tag. Multiplikation mit Tagen, um diejenigen zu markieren, die vor einigen Tagen geändert wurden
                timeLimit = 86400000 * 1.5;
                if(timeDiff < timeLimit)
                {
                    for(colN=2; colN<9; colN++)
                        $("#stSearchTermsGrid").jqGrid('setCell', $ids[$i], colN, '', {'backgroundColor':$colorRecentlyModified});      
                }

                //Färbung der unklassifizierten Zeile
                var $colorUnclassified = '#FFCECE';
                var $fId = $("#stSearchTermsGrid").jqGrid('getCell',$ids[$i],'fId');
                if($fId == "0")
                {
                    for(colN=2; colN<9; colN++)
                        $("#stSearchTermsGrid").jqGrid('setCell', $ids[$i], colN, '', {'backgroundColor':$colorUnclassified});    

                }

            }
        },
        sortable: true,
        //autowidth:true,
        width: 900, //Breite des Rasters
        height: 250, //Höhe des Rasters
        sortname: 'term',    //Standard-Sortierspalte
        caption: "Begriffe",    //Bezeichnung für das Raster (leer versteckt)
        hidegrid: false,
        gridview: true,        //Gitter schneller laden
        multiselect: true,    //Mehrere Auswahl unterstützen
        //multiboxonly: true,
        pager: '#stSearchTermsGridPager',
        rowNum:10,
        rowList:[10,25,50,100,500,1000],
        viewrecords: true,    //Anzeige von Aufzeichnungsinformationen
        viewsortcols: [true,'vertical',true], //Sortierbare Spalte mit Symbolen anzeigen
        editurl: 'ajax/ajax_termsEdit.php'
    });
    $("#stSearchTermsGrid").jqGrid('navGrid','#stSearchTermsGridPager',
        {edit:true,add:false,del:true,search:true,view:true,refresh:true}, 
        // Bearbeitungsoptionen
        {    
            onclickSubmit : function(params, posdata) {
                var $tId=$("#stSearchTermsGrid").jqGrid('getGridParam','selrow');
                if($tId && $tId.length>0)
                {
                    var $rowAry=$("#stSearchTermsGrid").jqGrid('getRowData',$tId);
                    var $fId=$rowAry["fId"];
                    return {"fId":$fId}
                }
            },
            afterSubmit : gridAfterSubmit,
            reloadAfterSubmit: true,
            closeOnEscape:true,
            bottominfo:"Felder, die mit (*) markiert sind, sind erforderlich."
        },
        // Hinzufügen von Optionen
        {},
        //löschen Optionen
        {
            msg: "Ausgewählte Datensätze werden dauerhaft gelöscht und können nicht wiederhergestellt werden.  Sind Sie sicher?",
            afterSubmit : gridAfterSubmit,
            reloadAfterSubmit: true,
            closeOnEscape:true
        },
        // such Optionen
        {multipleSearch:true,closeOnEscape:true},
        //Ansichtsoptionen
        {
            closeOnEscape:true
        }
    );
    $("#stSearchTermsGrid").jqGrid('gridResize',{minWidth:900,maxWidth:2000,minHeight:250, maxHeight:1000});

15voto

Oleg Punkte 219333

Ich sehe viele Stellen, an denen das Raster verbessert werden kann.

1) Sie sollten Paging verwenden. Wenn Sie dem Benutzer 1000 Datensätze anzeigen, werden die Daten nicht auf einmal auf dem Monitor angezeigt. Der Benutzer muss das Fenster des Webbrowsers scrollen, um die meisten Teile der Daten zu sehen. Welchen Sinn hat es, Zeit damit zu verbringen, die Teile des Fensters zu malen, die nicht gesehen werden? Das Scrollen von Daten mit Respekt vor jqGrid ist viel effektiver als das Scrollen des Browserfensters. Außerdem kann keine Person die 1000 Datensätze analysieren. Er muss die Sortierung ändern und verschiedene Filter setzen, um zu verstehen, welche Daten für ihn interessant sind. Es ist ein weiteres Argument für das Datapaging und die Implementierung von Suchfunktionen. Wenn Sie bereits eine erweiterte Suche verwenden, können Sie zusätzlich die Toolbar-Suche mit dem Parameter stringResult:true in Betracht ziehen, der mit der erweiterten Suche kompatibel ist.

2) Sie sollten den Code von gridComplete völlig neu schreiben. Ich nehme an, dass die Funktion bei einer relativ großen Anzahl von Datensätzen das Nadelöhr Ihres Codes ist. Um dies zu überprüfen, kommentieren Sie die Funktion vorübergehend aus und vergleichen Sie die Zeit der Rasterdarstellung. Sie sollten verstehen, dass jedes Mal, wenn Sie Daten nach ID abrufen oder Daten nach ID setzen, jQuery das DOM-Element nach ID suchen muss. Insbesondere die Änderung von Daten auf der Seite kann sehr langsam sein. Übrigens scheint es mir, dass Sie fast alle Zellen der Zeilen mit demselben 'Hintergrundfarbe' (was ist 'Hintergrundfarbe' ???) CSS-Stil setzen. Warum setzen Sie nicht die 'Hintergrundfarbe' für die Zeile ( Element) stattdessen?

3) Ich empfehle Ihnen dringend, datatype nicht als Funktion zu verwenden. Ihr Serverteil sollte einen Fehler-HTTP-Code zurückgeben. In diesem Fall wird das loadError Ereignis funktionieren und Sie können die benutzerdefinierte Fehlermeldung decodieren und anzeigen. Alles andere in Ihren Daten scheint standardmäßig zu sein und Sie müssen datatype nicht als Funktion verwenden. Wenn Sie datatype:"xml" verwenden, können Sie beispielsweise versuchen, loadonce:true zu verwenden und die clientseitige Datenpagenavigation und -sortierung zu implementieren, wenn Sie Probleme mit der Implementierung dieser Funktionen auf dem Server haben.

Ich möchte keinen zu langen Text schreiben, also höre ich bei den 3 wichtigsten Punkten auf. Übrigens, wenn Sie von XML zu JSON als Datentyp für die Kommunikation mit dem Server wechseln, wird sich auch die Leistung etwas verbessern.

AKTUALISIERT: Um die Leistung von jqGrid mit 1000 Datensätzen zu sehen, schauen Sie sich die Links an ohne Paging und mit Datapaging. Ist übrigens die Leistung meines Beispiels mit 1000 Datensätzen ohne Paging genauso langsam wie in Ihrem Fall?

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