Как загрузить общий класс без цикла - PullRequest
0 голосов
/ 20 июля 2010

хорошо, это то, что у меня есть сейчас, и оно работает довольно хорошо, за исключением того, что оно немного медленное:

Public Function GetList() As List(Of SalesOrder)
Try
    Dim list As New List(Of SalesOrder)

    Dim ds As DataSet

    ds = cls.GetSalesOrderList 'CLS is the data access class


    For i = 0 To ds.Tables(0).Rows.Count - 1

        Dim row As DataRow = ds.Tables(0).Rows(i)
        Dim kk As SalesOrder = New SalesOrder()


        kk.ID = Val(row.Item("id") & "")
        kk.SalesOrderNo = row.Item("salesorderid") & ""
        kk.SalesOrderDate = row.Item("OrderDate") & ""
        kk.CustomerId = Val(row.Item("customerid") & "")

        list.Add(kk)

    Next
    Return list

    Catch ex As Exception
        Throw ex
    End Try

End Function

Теперь, когда я начинаю извлекать более 10000 записей из таблицы, циклу требуется много времени для загрузки значений в общий класс. Есть ли способ, которым я могу избавиться от петли? Могу ли я сделать что-то вроде следующего с универсальным классом?

txtSearch.AutoCompleteCustomSource.AddRange(Array. ConvertAll(Of DataRow, String)(BusinessLogic.ToDataTable.ConvertTo(WorkOr derList).Select(), Function(row As DataRow) row("TradeContactName"))) 

Ответы [ 3 ]

0 голосов
/ 20 июля 2010

Преобразование цикла в некую конструкцию LINQ не обязательно повысит производительность, если вы все еще будете перечислять все строки сразу. Вы можете вернуть IEnumerable (Of SalesOrder), если вам не нужно предоставлять потребителю возможность добавлять / удалять из списка (как это может выглядеть), и тогда в этом случае вы можете создать перечислитель для обработки этот. Таким образом, набор данных загружается все сразу, но элементы преобразуются в объекты только при перечислении, что может быть частью вашего удара по производительности.

Примерно так:

Return ds.Tables(0).Rows.Select(Function(dr As DataRow) Return New SalesOrder ... );

Мой VB с LINQ немного ржавый, но что-то в этом роде, где ... - это код для создания нового SalesOrder. Это создаст только новый объект SalesOrder, так как IEnumerable (Of SalesOrder) перечисляется (ленивый, если хотите).

0 голосов
/ 20 июля 2010

Эй, Пол, Вы имеете в виду что-то вроде кода ниже

Dim list As New List(Of SalesOrder) 

Dim kk As SalesOrder = New SalesOrder() 

Function DrToOrder(dr as datareader)     
        kk.ID = Val(dr.Item("id") & "") 
        kk.SalesOrderNo = dr.Item("salesorderid") & "" 
        list.Add(kk)     
End function 

Function LoadData()     
         datareader.Rows.Select(DrToOrder)     
End function 

Вы говорите о чем-то вроде кода выше?

0 голосов
/ 20 июля 2010

Я бы подумал, что проблема не в цикле, а в объемах данных.Кажется, что ваш метод цикла обрабатывает каждый бит данных только один раз, поэтому не происходит значительного сбоя в эффективности (например, циклическое повторение набора данных один раз, а затем снова для каждой строки или тому подобное).Любой метод, который вы выберете, в конце концов будет нуждаться в циклическом просмотре всех ваших данных.

Их методы могут быть немного более эффективными, чем ваши, но они не будут намного более важными, поэтому я 'я думаюЯ хотел бы посмотреть, можете ли вы выполнить какой-либо рефакторинг, чтобы уменьшить ваш набор данных (например, ограничить его определенным периодом или аналогичным), или можете ли вы выполнять поиск или агрегирование этого списка, который вы намереваетесь в базе данных, а не в коде.например, если вы просто собираетесь суммировать значения этого списка, то вы почти наверняка можете сделать это лучше, имея хранимую процедуру, которая будет выполнять суммирование в базе данных, а не в коде.

Я знаю этоЯ не ответил прямо на ваш вопрос, но это в основном потому, что я не знаю более эффективного метода.Я воспринял вопрос как просьбу об оптимизации в целом, а не о том, как это сделать.:)

...