2015-01-09 4 views
0

Я пытаюсь автозаполнять названия городов из огромной таблицы sql. Мой код ниже работает, но очень медленный, а иногда и зависает, потому что у меня много повторных предложений. любой способ отфильтровать всю эту повторяющуюся строку, чтобы сделать ее быстрее? благодаряAutocompleteExtender от 65000 записей в sql-таблице

Public Function GetCompletionList(ByVal prefixText As String, ByVal count As Integer) As String() 

    Dim strCn As String = "Data Source=sqlserver\sqlexpress;Initial Catalog=zip;User ID=sa;Password=xxx" 
    cn.ConnectionString = strCn 
    Dim cmd As New SqlClient.SqlCommand 
    cmd.Connection = cn 
    cmd.CommandType = CommandType.Text 
      cmd.CommandText = "select * from zip_code Where City like @myParameter+'%'" 
    cmd.Parameters.AddWithValue("@myParameter", prefixText) 

    Try 
     cn.Open() 
     cmd.ExecuteNonQuery() 
     Dim da As New SqlDataAdapter(cmd) 
     Dim dt As New DataTable() 

     da.Fill(ds) 
    Catch ex As Exception 
    Finally 
     cn.Close() 
    End Try 

    dt = ds.Tables(0) 

      Dim txtItems As New List(Of String)() 
    Dim dbValues As String 

    For Each row As DataRow In dt.Rows 
      dbValues = row("City").ToString() 
     dbValues = dbValues.ToLower() 
     txtItems.Add(dbValues) 
    Next 

    Return txtItems.ToArray 
+0

Попробуйте заменить 'select *' на 'select distinct City' для начала. – J0e3gan

+0

65 000 ничего. Надеюсь, вы выполните это в потоке, отличном от Dispatcher? – Darek

ответ

1
  1. Вы выполняете свой SQL дважды, один раз в течение ExecuteNonQuery, второй раз во время заливки.
  2. Вы не используете объекты IDisposable правильно.
  3. Вы возвращаете все столбцы.
  4. Если у вас есть элемент управления для отображения, проверьте, будет ли он принимать свойство Rows (Dataset?) Напрямую. Не копируйте.

UPDATE

Ваше соединение, команда и другие объекты реализовать IDisposable интерфейс. Таким образом, они должны быть размещены в блоке с помощью:

Using { resourcelist | resourceexpression } 
    [ statements ] 
End Using 

Тогда вам не придется беспокоиться о закрытии и утилизации соединения с базой данных.

UPDATE 2

Ваш код имеет проблемы безопасности потоков, то же соединение не должно быть общим для двух разных потоков. КОГДА-ЛИБО. Два последовательных запроса на заполнение и один закроют соединение с базой данных до того, как другой сможет закончить.

+0

спасибо, это намного быстрее, когда я перестраиваю свой код, чтобы запускать запрос только один раз и использовать select distinct. не могли бы вы рассказать о Idisposable. как я уже сказал, я использую расширитель автозаполнения ajax для получения результатов. –

+0

Использование предпочтительнее, но если вызов Close() находится в блоке finally, все в порядке и, конечно, не поднимается до уровня «неправильный». –

+1

Также: Fill() управляет соединениями. Документы заявляют, что будут открывать и закрывать соединение по мере необходимости. Но да, очень сложно разделить объект подключения в веб-приложении. –

Смежные вопросы