Массовая вставка из DataTable в источник данных SQLCE

#c# #wpf #sql-server-ce #bulkinsert

#c# #wpf #sql-server-ce #bulkinsert

Вопрос:

Это приложение C # WPF с SQL CE в качестве источника данных:

У меня есть DataTable (отображается как DataGrid) и источник данных SQL CE. Я заполняю свой DataTable из SQL CE, используя DataAdapter, DataSet и DataTable. Затем привяжите мою сетку данных к DataTable.

Я могу добавлять строки (> 10 000) в свой DataTable и, возможно, редактировать данные, прежде чем распространять все мои изменения вместе в мой источник данных Sql CE.

Мой текущий подход заключается в УДАЛЕНИИ ТАБЛИЦЫ, СОЗДАНИИ ТАБЛИЦЫ и повторной вставке строк методом перебора в SQLCE. В SQL CE нет массовой вставки, и я не хочу использовать третью библиотеку или dll. Производительность низкая…

Я ищу более быстрый способ «массовой вставки» без необходимости удалять, создавать и вставлять строки одну за другой.

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

[ПРАВИТЬ]
Следуя ответу и проверяя это:
http://ruudvanderlinden.com/2010/10/13/bulk-insert-into-sql-ce-in-c/

Я пытался использовать функцию, но, похоже, она не сработала. Ниже приведен мой код. Footable — это таблица моей базы данных, и у меня есть два столбца — «id» и «FooName».

 Hashtable idHash = new Hashtable();
Hashtable fooNameHash = new Hashtable();
foreach(DataRow row in dt.Rows)
{
    idHash.Add("id",row["id"]);
    fooNameHash.Add("FooName",row["FooName"]);
}

List<Hashtable> colHashList = new List<Hashtable>();
colHashList.Add(idHash);
colHashList.Add(fooNameHash);

BulkInsertDatabase(colHashList, "FooTable");
  

Это не сработало, но я не вижу никакой проблемы в моем приведенном выше коде, поэтому надеюсь, что кто-нибудь сможет указать на это..

[ПРАВКА — 2-я][ОТВЕТ]
Наконец-то я заставляю код работать (хотя и сомневаюсь в производительности):

 List<Hashtable> colHashList = new List<Hashtable>();

Hashtable[] idHash = new Hashtable[dt.Rows.Count];
Hashtable[] fooNameHash = new Hashtable[dt.Rows.Count];

int i=0;
foreach(DataRow row in dt.Rows)
{
    idHash[i] = new Hashtable();
    idHash[i].Add("id", row["id"]);
    colHashList.Add(idHash[i]);

    fooNameHash[i] = new Hashtable();
    fooNameHash[i].Add("FooName", row["FooName"]);
    colHashList.Add(fooNameHash[i]);

    i  ;
}

BulkInsertDatabase(colHashList, "FooTable");
  

Комментарии:

1. С вашими записями > 10 Тыс. состоит ли он из обновленных и новых записей? Или просто недавно добавленные записи?

2. @Пейтон Кроу — записи состоят как из обновленных, так и из новых записей. Но я УДАЛЮ, СОЗДАМ и опустошу таблицу в SQL CE перед вставкой. Следовательно, я все равно буду рассматривать все записи DataTable как недавно добавленные.

Ответ №1:

Вы должны использовать класс SqlCeResultSet

это позволяет массовый импорт в базу данных SQL CE, я импортировал 100000 строк за 10 секунд, посмотрите на пример

Комментарии:

1. Я отредактировал свой код. Сработал ли для вас учебник или как вы заставили свой работать?

2. Я нашел статью, из которой я копирую код для своей программы, вы могли бы использовать примеры из этой статьи для реализации массовой вставки msdn.microsoft.com/en-us/library /…

Ответ №2:

Вы можете использовать исходный код C # из моей библиотеки массовой вставки здесь: http://sqlcebulkcopy.codeplex.com

Комментарии:

1. Я не вижу никакого исходного кода. Просто загружаемые библиотеки DLL для всех разных версий.

2. Ах, неловкий момент № 56. Спасибо

Ответ №3:

это работает, попробуйте это.

  public bool CopyDataTableToTable(DataTable dataTable, string tableName, bool deleteTable)
        {
            Boolean returnValue = true;
            if (sqlCeConnection.State == ConnectionState.Closed)
                sqlCeConnection.Open();

            SqlCeTransaction transaction = sqlCeConnection.BeginTransaction();
            SqlCeCommand cmd = sqlCeConnection.CreateCommand();
            SqlCeResultSet rs = null;
            try
            {
                if (deleteTable)
                {
                    cmd.Transaction = transaction;
                    cmd.CommandText = "DELETE "   tableName;
                    cmd.ExecuteNonQuery();
                }

                cmd.CommandType = System.Data.CommandType.TableDirect;
                cmd.CommandText = tableName;
                rs = cmd.ExecuteResultSet(ResultSetOptions.Updatable);

                for (int i = 0; i < dataTable.Rows.Count; i  )
                {
                    SqlCeUpdatableRecord rec = rs.CreateRecord();
                    DataRow row = dataTable.Rows[i];
                    for (int k = 0; k < dataTable.Columns.Count - 1; k  )
                    {
                        rec.SetValue(k   1, row[k]);
                    }
                    rs.Insert(rec);
                }
                transaction.Commit();
            }

            catch (Exception ex)
            {
                returnValue = false;
                transaction.Rollback();
            }
            finally
            {
                rs.Close();
                if (sqlCeConnection.State == ConnectionState.Open)
                    sqlCeConnection.Close();

            }
            return returnValue;
        }