Leistung bezüglich des Rückkehrtyps für LINQ -Abfragen, die mit der automatischen Sortierung kompatibel ist

StackOverflow https://stackoverflow.com/questions/1761597

Frage

Dies ist kein wirkliches Problem, aber eher ein Problem, das ich mir bitte freuen würde.

WinForms C# .NET3.5 [SP1] Visual Studio 2008 mit LINQ2SQL (genauer gesagt Plinqo... was übrigens fantastisch ist!). Ich habe ein Ergebnis, das +/- 19000 Datenzeilen (mit etwa 80 Byten von Daten pro Zeile) zurückgegeben und entschied mich, die Datenabnahmemethode in den Hintergrund zu bringen und die Benutzeroberfläche entsprechend zu aktualisieren. Das funktioniert gut.

Ich habe jedoch einige Leistungsunterschiede festgestellt, wenn ich unterschiedliche Rückkehrtypen für meine Ling-Daten-Abrufmethode verwendet habe. Ich weiß, jeder schlägt vor, a zurückzukehren List<T> oder IEnumarable<T>, und setzen Sie die DataSource des DataGridView darauf, aber leider unterstützt es nicht, dass sie nativ für Objekte sortiert werden. Nachdem ich etwas herumgegraben hatte, fand ich das SortableBindingList<T> an Msdn hier. Ich habe es angewendet, und das Netz nahm unter einer Sekunde, um sich selbst zu bevölkern. Wenn ich jedoch auf eine Spalte klicke, um sie zu sortieren, dauerte es etwas mehr als eine Sekunde, um die Sortierung implementieren zu können.

Ich beschloss dann, die Datentatable -Route zu besuchen, stellte jedoch fest, dass die motagierbare Methode entfernt wurde. MSDN -Artikel. Nachdem ich es angewendet hatte, stellte ich fest, dass das Abruf ungefähr 2 Sekunden dauerte, bis das Netz besiedelt wurde, aber danach war die Sortierung (auf 19000 Reihen!) Sofortig !! Natürlich habe ich mich an diesen Ansatz geblieben.

Denken Sie auch daran, dass ich jegliches In-Gitter-Bewirtschaftung/Hinzufügen/Löschen deaktiviert habe. Das Netz dient nur zum Anzeigen von Daten. Alle anderen CRUD -Operationen werden von Dialogformularen gemäß der aktuellen ausgewählten Zeile (versteckte Primärschlüsselspalte) bereitgestellt.

Hier ist der Code, den ich für beide Methoden verwendet habe:

1) sortierbare Bindungsliste

    //declare private member
    private SortableBindingList<PdtAllocation> listAlloc = null;

    private void RefreshData() {
        bcsDataContext ctx = new bcsDataContext();
        try {
            listAlloc = new SortableBindingList<PdtAllocation>(ctx.PdtAllocation.ToList());
        }
        catch (Exception) {
            throw;
        }
        finally {
            ctx.Dispose();
        }

        dataGridView1.DataSource = listAlloc;
    }

2) CopyTodatatable

    //declare private member
    private DataTable dt = null;

    private void RefreshData() {
        dt = new DataTable();
        bcsDataContext ctx = new bcsDataContext();
        try {
            ctx.PdtAllocation.CopyToDataTable(dt, LoadOption.PreserveChanges);
        }
        catch (Exception) {
            throw;
        }
        finally {
            ctx.Dispose();
        }

        dataGridView1.DataSource = dt;
    }

Jetzt weiß ich, dass dies wahrscheinlich wie ein "scheint"gefragt und beantwortet"Fall, aber ich würde Ihre Beiträge sehr schätzen, sowie alle bekannten Probleme mit dem Gehen CopyToDataTable() Route.

Danke ... und Entschuldigung für die loong -Frage!

War es hilfreich?

Lösung

Hier ist meine Sicht auf Ihre Frage (gehen SortableBindingList Route).

Haben Sie einen generischen, reflektionsbasierten Sortierungsalgorithmus verwendet? Ich habe das zuerst gemacht und die Leistung war wirklich schlecht. Schließlich habe ich die folgende Lösung entwickelt: Standardsortierung in der Standardsuche SortableBindingList<T> Lassen Sie aber auch die Möglichkeit offen, eine spezielle Sortierung in abgeleiteten Klassen zu implementieren.

Hier ist ein Code.

Im SortableBindingList<T>.ApplySortCore():

protected override void ApplySortCore(PropertyDescriptor prop, ListSortDirection direction)
{
    // Check if the sorted property implements IComparable
    ...

    List<T> itemsList = (List<T>)this.Items;

    Comparison<T> comparer = GetComparer(prop);

    itemsList.Sort(comparer);

    if (direction == ListSortDirection.Descending)
    {
        itemsList.Reverse();
    }

    ...
    // Set sort state (is sorted, sort property, sort dir)
}

Das generische SortableBindingList<T> Bietet einen grundlegenden, reflektionsbasierten Sortierer:

protected virtual Comparison<T> GetComparer(PropertyDescriptor prop)
{
    return new Comparison<T>(delegate(T x, T y)
    {
        if (prop.GetValue(x) != null)
            return ((IComparable)prop.GetValue(x)).CompareTo(prop.GetValue(y));
        else if (prop.GetValue(y) != null)
            return -1 * ((IComparable)prop.GetValue(y)).CompareTo(prop.GetValue(x));
        else
            return 0;
    });
}

Wie du sehen kannst, GetComparer() ist virtuell, so dass man es in einer Klasse überschreiben kann SortableBindingList<T> Um a zu liefern viel Schnellerer Vergleich, optimiert an den Typ der Eigenschaft, die tatsächlich sortiert wird. Zum Beispiel, während der generische Vergleich sortiert (nach a String Eigenschaft) 10000 Aufzeichnungen In 4 Sekunden hat der spezialisierte Vergleich in 70 ms den gleichen Job gemacht.

class CustomerList : SortableBindingList<Customer>
{
    protected override Comparison<Customer> GetComparer(PropertyDescriptor prop)
    {
        Comparison<Customer> comparer = null;
        switch (prop.Name)
        {
            case "FirstName":
                comparer = new Comparison<Customer>(delegate(Customer x, Customer y)
                {
                    string xx = (null == x) ? null : x.FirstName;
                    string yy = (null == y) ? null : y.FirstName;
                    return String.Compare(xx, yy);
                });
                break;
            ...
        }
        return comparer;
    }
}

Ein letzter Hinweis: Ein Großteil des veröffentlichten Codes wurde aus anderen Quellen wie SO oder Microsoft kopiert/inspiriert, sodass das Guthaben nicht meine ist. Mein einziger Beitrag war die Virtualisierung des Vergleichs, aber ich bin sicher, dass ein wenig Googeln besser auftreten würde, früher Lösungen, die auf derselben Idee basieren.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top