Update(DataRow[])

Метод выполняет необходимые операторы (INSERT, UPDATE или DELETE) для изменения строк в указанном массиве объектов DataRow.

Указанные операторы должны быть либо явно прописаны в соответствующих свойствах объекта DbDataAdapter (InsertCommand, UpdateCommand, DeleteCommand), либо сконструированы с помощью класса DbCommandBuilder.

Когда клиентское приложение вызывает метод Update, объект DbDataAdapter проверяет свойство RowState и выполняет необходимые операторы INSERT, UPDATE или DELETE для каждой строки объекта DataSet на основе заданной очередности выполнения операций. Можно использовать метод Select объекта DataTable для возврата массива DataRow, который ссылается только на строки с конкретным значением RowState. После этого можно передать возвращенный массив DataRow в метод Update объекта DataAdapter для обработки измененных строк. Задавая подмножество строк, подлежащих обновлению, можно управлять тем, в какой последовательности обрабатываются вставки, обновления и удаления. Например, метод Update может сначала выполнить оператор DELETE, затем оператор INSERT, а затем – еще один оператор DELETE, что определяется порядком строк в объекте DataTable.

Операторы манипулирования данными выполняются не как пакетный процесс. Каждая строка обновляется индивидуально. Клиентское приложение может вызвать метод Select в случаях, когда необходимо управлять последовательностью типов операторов (например, когда оператор INSERT выполняется до выполнения оператора UPDATE).

Если операторы INSERT, UPDATE или DELETE не были указаны, метод Update создает исключение. Однако можно создать объект DbCommandBuilder для автоматического создания SQL-операторов для однотабличных обновлений, если задано свойство SelectCommand объекта DbDataAdapter. Затем любые дополнительные SQL-операторы, которые не были ранее заданы, создаются объектом CommandBuilder. Такая логика создания операторов требует, чтобы сведения о столбце с первичным ключом присутствовали в объекте DataSet.

Метод Update получает строки из таблицы, указанной в первом сопоставлении перед выполнением обновления. Затем метод Update обновляет строку, используя значение свойства UpdatedRowSource. Все возвращенные дополнительные строки игнорируются.

После того, как данные загружены снова в объект DataSet, генерируется событие OnRowUpdated, предоставляя пользователю возможность проверить согласованную строку DataSet и любые выходные параметры, возвращенные командой. После успешного обновления строки принимаются изменения этой строки.

При использовании метода Update порядок выполнения является следующим:

  • значения в объекте DataRow переносятся в значения параметров;

  • генерируется событие OnRowUpdating;

  • выполняется команда;

  • если для команды задано значение FirstReturnedRecord, первый возвращенный результат помещается в объект DataRow;

  • при наличии выходных параметров они помещаются в объект DataRow;

  • генерируется событие OnRowUpdated;

  • вызывается метод AcceptChanges.

С каждой командой, связанной с классом DbDataAdapter, обычно связана коллекция параметров. Параметры сопоставляются с текущей строкой с помощью свойств SourceColumn и SourceVersion класса Parameter ADO.NET-провайдера СУБД ЛИНТЕР. Свойство SourceColumn ссылается на столбец объекта DataTable, на который есть ссылка в объекте DbDataAdapter, для получения значений параметров для текущей строки.

Свойство SourceColumn ссылается на несопоставленный столбец перед применением сопоставления таблиц. Если свойство SourceColumn ссылается на несуществующий столбец, выполняемые действия зависят от одного из следующих значений MissingMappingAction:

  1. MissingMappingAction.Passthrough – использовать имена исходных столбцов и таблиц в объекте DataSet, если сопоставление отсутствует;

  2. MissingMappingAction.Ignore – генерируется исключение SystemException. Если сопоставления заданы явным образом, отсутствие сопоставления для входного параметра обычно является следствием ошибки;

  3. MissingMappingAction.Error – генерируется исключение SystemException.

Свойство SourceColumn также используется для сопоставления выходных значений или входных и выходных параметров обратно в объект DataSet. При ссылке на несуществующий столбец генерируется исключение.

Свойство SourceVersion класса Parameter ADO.NET-провайдера СУБД ЛИНТЕР определяет, следует ли использовать версию Original, Current или Proposed значения столбца. Эта возможность обычно используется для включения исходных значений в предложении WHERE оператора UPDATE для проверки нарушений параллелизма типа OPTIMISTIC.

Примечание

Если при обновлении строки возникает ошибка, выдается исключение, и обновление прерывается. Чтобы продолжить операцию обновления без создания исключений при обнаружении ошибки, необходимо установить для свойства ContinueUpdateOnError значение true перед вызовом метода Update. Также можно реагировать на ошибки на построчной основе в событии RowUpdated объекта DbDataAdapter. Чтобы продолжить операцию обновления без создания исключения в событии RowUpdated, необходимо установить для свойства Status объекта RowUpdatedEventArgs значение Continue.

Синтаксис
public int Update(DataRow[] dataRows);

dataRows – массив объектов DataRow, используемый для обновления источника данных.

Возвращаемое значение

Количество успешно обновленных строк из объекта DataSet.

Исключения
ArgumentNullException Параметр dataSet содержит null-значение.
InvalidOperationException Исходная таблица является недопустимой.
SystemException

Возможные причины:

  • не существует объект DataRow или DataTable для обновления;

  • не существует объект DataSet для использования в качестве источника.

DBConcurrencyException Попытка выполнить оператор INSERT, UPDATE или DELETE привела к нулевому количеству обработанных записей.
LinterSqlException Код завершения СУБД ЛИНТЕР не равен 0.
Пример

В примере демонстрируется первоочередная обработка удаленных строк таблицы, затем происходит обработка обновленных строк, после чего обрабатываются вставленные строки.

// C#
using System;
using System.Data;
using System.Data.Common;

class UpdateSample
{
  static void Main()
  {
    // Создание фабрики классов провайдера
    DbProviderFactory factory =
      DbProviderFactories.GetFactory("System.Data.LinterClient");
    // Соединение с БД
    DbConnection con = factory.CreateConnection();
    con.ConnectionString =
      "Data Source=LOCAL;User ID=SYSTEM;Password=MANAGER8";
    // Создание таблицы БД
    DbCommand cmd = factory.CreateCommand();
    cmd.Connection = con;
    cmd.CommandText =
      "create or replace table users ( " +
      "id integer primary key, name varchar(70));" +
      "insert into users (id, name) values (0, 'Пользователь A');" +
      "insert into users (id, name) values (1, 'Пользователь B');";
    con.Open();
    cmd.ExecuteNonQuery();
    con.Close();
    // Создание команды для выборки записей
    DbCommand selectCommand = factory.CreateCommand();
    selectCommand.Connection = con;
    selectCommand.CommandText =
      "select id, name from users";
    // Создание объекта DbDataAdapter
    DbDataAdapter adapter = factory.CreateDataAdapter();
    adapter.SelectCommand = selectCommand;
    // Создание объекта DbCommandBuilder
    DbCommandBuilder builder = factory.CreateCommandBuilder();
    builder.DataAdapter = adapter;
    // Заполнение объекта DataTable данными из таблицы БД
    DataTable users = new DataTable();
    adapter.Fill(users);
    // Изменение записей в таблице DataTable
    users.Rows[0]["name"] = "Новый Пользователь A";
    users.Rows[1].Delete();
    users.Rows.Add(2, "Пользователь X");
    // Вначале выполним удаление
    adapter.Update(users.Select(null, null, DataViewRowState.Deleted));
    // Далее выполним обновление
    adapter.Update(users.Select(null, null,
      DataViewRowState.ModifiedCurrent));
    // В конце выполним вставку
    adapter.Update(users.Select(null, null, DataViewRowState.Added));
    // Отображение таблицы после обновления
    Console.WriteLine("Строки таблицы после обновления:");
    foreach (DataRow row in users.Rows)
    {
      Console.WriteLine("{0}: '{1}' ", row[0], row[1]);
    }
  }
}