DataTable.Load 方法

定义

通过所提供的 IDataReader,用某个数据源的值填充 DataTable。 如果 DataTable 已经包含行,则从数据源传入的数据与现有行合并。

重载

Load(IDataReader)

通过所提供的 IDataReader,用某个数据源的值填充 DataTable。 如果 DataTable 已经包含行,则从数据源传入的数据与现有行合并。

Load(IDataReader, LoadOption)

通过所提供的 IDataReader,用某个数据源的值填充 DataTable。 如果 DataTable 已包含行,则从数据源传入的数据根据 loadOption 参数的值与现有行合并。

Load(IDataReader, LoadOption, FillErrorEventHandler)

通过所提供的使用错误处理委托的 IDataReader,用某个数据源中的值填充 DataTable

示例

以下示例演示了调用 Load 方法所涉及的几个问题。 首先,该示例侧重于架构问题,包括从加载 IDataReader的 推断架构,然后处理不兼容的架构,以及包含缺失列或其他列的架构。 然后,该示例侧重于数据问题,包括处理各种加载选项。

备注

此示例演示如何使用 的某个重载版本 Load。 有关可能提供的其他示例,请参阅各个重载主题。

static void Main()
{
    // This example examines a number of scenarios involving the
    // DataTable.Load method.
    Console.WriteLine("Load a DataTable and infer its schema:");

    // The table has no schema. The Load method will infer the
    // schema from the IDataReader:
    DataTable table = new DataTable();

    // Retrieve a data reader, based on the Customers data. In
    // an application, this data might be coming from a middle-tier
    // business object:
    DataTableReader reader = new DataTableReader(GetCustomers());

    table.Load(reader);
    PrintColumns(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine("Load a DataTable from an incompatible IDataReader:");

    // Create a table with a single integer column. Attempt
    // to load data from a reader with a schema that is
    // incompatible. Note the exception, determined
    // by the particular incompatibility:
    table = GetIntegerTable();
    reader = new DataTableReader(GetStringTable());
    try
    {
        table.Load(reader);
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex.GetType().Name + ":" + ex.Message);
    }

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable with an IDataReader that has extra columns:");

    // Note that loading a reader with extra columns adds
    // the columns to the existing table, if possible:
    table = GetIntegerTable();
    reader = new DataTableReader(GetCustomers());
    table.Load(reader);
    PrintColumns(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable with an IDataReader that has missing columns:");

    // Note that loading a reader with missing columns causes
    // the columns to be filled with null data, if possible:
    table = GetCustomers();
    reader = new DataTableReader(GetIntegerTable());
    table.Load(reader);
    PrintColumns(table);

    // Demonstrate the various possibilites when loading data into
    // a DataTable that already contains data.
    Console.WriteLine(" ============================= ");
    Console.WriteLine("Demonstrate data considerations:");
    Console.WriteLine("Current value, Original value, (RowState)");
    Console.WriteLine(" ============================= ");
    Console.WriteLine("Original table:");

    table = SetupModifiedRows();
    DisplayRowState(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine("Data in IDataReader to be loaded:");
    DisplayRowState(GetChangedCustomers());

    PerformDemo(LoadOption.OverwriteChanges);
    PerformDemo(LoadOption.PreserveChanges);
    PerformDemo(LoadOption.Upsert);

    Console.WriteLine("Press any key to continue.");
    Console.ReadKey();
}

private static void DisplayRowState(DataTable table)
{
    for (int i = 0; i <= table.Rows.Count - 1; i++)
    {
        object current = "--";
        object original = "--";
        DataRowState rowState = table.Rows[i].RowState;

        // Attempt to retrieve the current value, which doesn't exist
        // for deleted rows:
        if (rowState != DataRowState.Deleted)
        {
            current = table.Rows[i]["Name", DataRowVersion.Current];
        }

        // Attempt to retrieve the original value, which doesn't exist
        // for added rows:
        if (rowState != DataRowState.Added)
        {
            original = table.Rows[i]["Name", DataRowVersion.Original];
        }
        Console.WriteLine("{0}: {1}, {2} ({3})", i, current,
            original, rowState);
    }
}

private static DataTable GetChangedCustomers()
{
    // Create sample Customers table.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));
    table.Columns.Add("Name", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 0, "XXX" });
    table.Rows.Add(new object[] { 1, "XXX" });
    table.Rows.Add(new object[] { 2, "XXX" });
    table.Rows.Add(new object[] { 3, "XXX" });
    table.Rows.Add(new object[] { 4, "XXX" });
    table.AcceptChanges();
    return table;
}

private static DataTable GetCustomers()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));
    table.Columns.Add("Name", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 0, "Mary" });
    table.Rows.Add(new object[] { 1, "Andy" });
    table.Rows.Add(new object[] { 2, "Peter" });
    table.AcceptChanges();
    return table;
}

private static DataTable GetIntegerTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 4 });
    table.Rows.Add(new object[] { 5 });
    table.AcceptChanges();
    return table;
}

private static DataTable GetStringTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { "Mary" });
    table.Rows.Add(new object[] { "Andy" });
    table.Rows.Add(new object[] { "Peter" });
    table.AcceptChanges();
    return table;
}

private static void PerformDemo(LoadOption optionForLoad)
{

    // Load data into a DataTable, retrieve a DataTableReader containing
    // different data, and call the Load method. Depending on the
    // LoadOption value passed as a parameter, this procedure displays
    // different results in the DataTable.
    Console.WriteLine(" ============================= ");
    Console.WriteLine("table.Load(reader, {0})", optionForLoad);
    Console.WriteLine(" ============================= ");

    DataTable table = SetupModifiedRows();
    DataTableReader reader = new DataTableReader(GetChangedCustomers());
    table.RowChanging +=new DataRowChangeEventHandler(HandleRowChanging);

    table.Load(reader, optionForLoad);
    Console.WriteLine();
    DisplayRowState(table);
}

private static void PrintColumns(DataTable table)
{
    // Loop through all the rows in the DataTableReader
    foreach (DataRow row in table.Rows)
    {
        for (int i = 0; i < table.Columns.Count; i++)
        {
            Console.Write(row[i] + " ");
        }
        Console.WriteLine();
    }
}

private static DataTable SetupModifiedRows()
{
    // Fill a DataTable with customer info, and
    // then modify, delete, and add rows.

    DataTable table = GetCustomers();
    // Row 0 is unmodified.
    // Row 1 is modified.
    // Row 2 is deleted.
    // Row 3 is added.
    table.Rows[1]["Name"] = "Sydney";
    table.Rows[2].Delete();
    DataRow row = table.NewRow();
    row["ID"] = 3;
    row["Name"] = "Melony";
    table.Rows.Add(row);

    // Note that the code doesn't call
    // table.AcceptChanges()
    return table;
}

static void HandleRowChanging(object sender, DataRowChangeEventArgs e)
{
    Console.WriteLine(
        "RowChanging event: ID = {0}, action = {1}", e.Row["ID"],
        e.Action);
}
Sub Main()
  Dim table As New DataTable()

  ' This example examines a number of scenarios involving the 
  ' DataTable.Load method.
  Console.WriteLine("Load a DataTable and infer its schema:")

  ' Retrieve a data reader, based on the Customers data. In
  ' an application, this data might be coming from a middle-tier
  ' business object:
  Dim reader As New DataTableReader(GetCustomers())

  ' The table has no schema. The Load method will infer the 
  ' schema from the IDataReader:
  table.Load(reader)
  PrintColumns(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine("Load a DataTable from an incompatible IDataReader:")

  ' Create a table with a single integer column. Attempt
  ' to load data from a reader with a schema that is 
  ' incompatible. Note the exception, determined
  ' by the particular incompatibility:
  table = GetIntegerTable()
  reader = New DataTableReader(GetStringTable())
  Try
    table.Load(reader)
  Catch ex As Exception
    Console.WriteLine(ex.GetType.Name & ":" & ex.Message())
  End Try

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable with an IDataReader that has extra columns:")

  ' Note that loading a reader with extra columns adds
  ' the columns to the existing table, if possible:
  table = GetIntegerTable()
  reader = New DataTableReader(GetCustomers())
  table.Load(reader)
  PrintColumns(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable with an IDataReader that has missing columns:")

  ' Note that loading a reader with missing columns causes 
  ' the columns to be filled with null data, if possible:
  table = GetCustomers()
  reader = New DataTableReader(GetIntegerTable())
  table.Load(reader)
  PrintColumns(table)

  ' Demonstrate the various possibilites when loading data into
  ' a DataTable that already contains data.
  Console.WriteLine(" ============================= ")
  Console.WriteLine("Demonstrate data considerations:")
  Console.WriteLine("Current value, Original value, (RowState)")
  Console.WriteLine(" ============================= ")
  Console.WriteLine("Original table:")

  table = SetupModifiedRows()
  DisplayRowState(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine("Data in IDataReader to be loaded:")
  DisplayRowState(GetChangedCustomers())

  PerformDemo(LoadOption.OverwriteChanges)
  PerformDemo(LoadOption.PreserveChanges)
  PerformDemo(LoadOption.Upsert)

  Console.WriteLine("Press any key to continue.")
  Console.ReadKey()
End Sub

Private Sub DisplayRowState(ByVal table As DataTable)
  For i As Integer = 0 To table.Rows.Count - 1
    Dim current As Object = "--"
    Dim original As Object = "--"
    Dim rowState As DataRowState = table.Rows(i).RowState

    ' Attempt to retrieve the current value, which doesn't exist
    ' for deleted rows:
    If rowState <> DataRowState.Deleted Then
      current = table.Rows(i)("Name", DataRowVersion.Current)
    End If

    ' Attempt to retrieve the original value, which doesn't exist
    ' for added rows:
    If rowState <> DataRowState.Added Then
      original = table.Rows(i)("Name", DataRowVersion.Original)
    End If
    Console.WriteLine("{0}: {1}, {2} ({3})", i, current, original, rowState)
  Next
End Sub

Private Function GetChangedCustomers() As DataTable
  ' Create sample Customers table.
  Dim table As New DataTable

  ' Create two columns, ID and Name.
  Dim idColumn As DataColumn = table.Columns.Add("ID", GetType(Integer))
  table.Columns.Add("Name", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {0, "XXX"})
  table.Rows.Add(New Object() {1, "XXX"})
  table.Rows.Add(New Object() {2, "XXX"})
  table.Rows.Add(New Object() {3, "XXX"})
  table.Rows.Add(New Object() {4, "XXX"})
  table.AcceptChanges()
  Return table
End Function

Private Function GetCustomers() As DataTable
  ' Create sample Customers table.
  Dim table As New DataTable

  ' Create two columns, ID and Name.
  Dim idColumn As DataColumn = table.Columns.Add("ID", GetType(Integer))
  table.Columns.Add("Name", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {0, "Mary"})
  table.Rows.Add(New Object() {1, "Andy"})
  table.Rows.Add(New Object() {2, "Peter"})
  table.AcceptChanges()
  Return table
End Function

Private Function GetIntegerTable() As DataTable
  ' Create sample table with a single Int32 column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", GetType(Integer))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {4})
  table.Rows.Add(New Object() {5})
  table.AcceptChanges()
  Return table
End Function

Private Function GetStringTable() As DataTable
  ' Create sample table with a single String column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {"Mary"})
  table.Rows.Add(New Object() {"Andy"})
  table.Rows.Add(New Object() {"Peter"})
  table.AcceptChanges()
  Return table
End Function

Private Sub PerformDemo(ByVal optionForLoad As LoadOption)

  ' Load data into a DataTable, retrieve a DataTableReader containing
  ' different data, and call the Load method. Depending on the
  ' LoadOption value passed as a parameter, this procedure displays
  ' different results in the DataTable.
  Console.WriteLine(" ============================= ")
  Console.WriteLine("table.Load(reader, {0})", optionForLoad)
  Console.WriteLine(" ============================= ")

  Dim table As DataTable = SetupModifiedRows()
  Dim reader As New DataTableReader(GetChangedCustomers())
  AddHandler table.RowChanging, New _
      DataRowChangeEventHandler(AddressOf HandleRowChanging)

  table.Load(reader, optionForLoad)
  Console.WriteLine()
  DisplayRowState(table)
End Sub

Private Sub PrintColumns( _
   ByVal table As DataTable)

  ' Loop through all the rows in the DataTableReader.
  For Each row As DataRow In table.Rows
    For Each col As DataColumn In table.Columns
      Console.Write(row(col).ToString() & " ")
    Next
    Console.WriteLine()
  Next
End Sub

Private Function SetupModifiedRows() As DataTable
  ' Fill a DataTable with customer info, and 
  ' then modify, delete, and add rows.

  Dim table As DataTable = GetCustomers()
  ' Row 0 is unmodified.
  ' Row 1 is modified.
  ' Row 2 is deleted.
  ' Row 3 is added.
  table.Rows(1)("Name") = "Sydney"
  table.Rows(2).Delete()
  Dim row As DataRow = table.NewRow
  row("ID") = 3
  row("Name") = "Melony"
  table.Rows.Add(row)

  ' Note that the code doesn't call
  ' table.AcceptChanges()
  Return table
End Function

Private Sub HandleRowChanging(ByVal sender As Object, _
  ByVal e As System.Data.DataRowChangeEventArgs)
  Console.WriteLine( _
      "RowChanging event: ID = {0}, action = {1}", e.Row("ID"), _
      e.Action)
End Sub

注解

方法 Load 可用于多种常见方案,其中心都是从指定数据源获取数据并将其添加到当前数据容器 (在本例 DataTable 中为) 。 这些方案描述 的标准用法 DataTable,描述其更新和合并行为。

DataTable 单个主数据源同步或更新。 跟踪 DataTable 更改,从而允许与主数据源同步。 此外, DataTable 可以接受来自一个或多个辅助数据源的增量数据。 DataTable不负责跟踪更改以允许与辅助数据源同步。

给定这两个假设数据源,用户可能需要以下行为之一:

  • 从主数据源初始化 DataTable 。 在此方案中,用户希望使用主数据源中的值初始化空 DataTable 。 稍后,用户打算将更改传播回主数据源。

  • 保留更改并从主数据源重新同步。 在此方案中,用户希望获取 DataTable 上一方案中填充的 ,并执行与主数据源的增量同步,从而保留 中 DataTable所做的修改。

  • 来自辅助数据源的增量数据馈送。 在此方案中,用户希望合并来自一个或多个辅助数据源的更改,并将这些更改传播回主数据源。

方法 Load 使所有这些方案成为可能。 此方法的所有重载(其中一个重载)都允许指定 load 选项参数,指示 中 DataTable 已有的行如何与正在加载的行合并。 (不允许指定行为的重载使用默认加载选项。) 下表描述了 枚举提供的 LoadOption 三个加载选项。 在每种情况下,说明都指示传入数据中行的主键与现有行的主键匹配时的行为。

加载选项 描述
PreserveChanges(默认值) 使用传入行的值汇报行的原始版本。
OverwriteChanges 使用传入行的值汇报行的当前和原始版本。
Upsert 使用传入行的值汇报行的当前版本。

通常, PreserveChangesOverwriteChanges 选项适用于用户需要将 及其更改与主数据源同步 DataSet 的方案。 选项 Upsert 有助于聚合来自一个或多个辅助数据源的更改。

Load(IDataReader)

Source:
DataTable.cs
Source:
DataTable.cs
Source:
DataTable.cs

通过所提供的 IDataReader,用某个数据源的值填充 DataTable。 如果 DataTable 已经包含行,则从数据源传入的数据与现有行合并。

public:
 void Load(System::Data::IDataReader ^ reader);
public void Load (System.Data.IDataReader reader);
member this.Load : System.Data.IDataReader -> unit
Public Sub Load (reader As IDataReader)

参数

reader
IDataReader

提供结果集的 IDataReader

示例

以下示例演示了调用 Load 方法所涉及的几个问题。 首先,该示例侧重于架构问题,包括从加载 IDataReader的 推断架构,然后处理不兼容的架构,以及包含缺失列或其他列的架构。 然后,该示例调用 Load 方法,在加载操作之前和之后都显示数据。

static void Main()
{
    // This example examines a number of scenarios involving the
    // DataTable.Load method.
    Console.WriteLine("Load a DataTable and infer its schema:");

    // The table has no schema. The Load method will infer the
    // schema from the IDataReader:
    DataTable table = new DataTable();

    // Retrieve a data reader, based on the Customers data. In
    // an application, this data might be coming from a middle-tier
    // business object:
    DataTableReader reader = new DataTableReader(GetCustomers());

    table.Load(reader);
    PrintColumns(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable from an incompatible IDataReader:");

    // Create a table with a single integer column. Attempt
    // to load data from a reader with a schema that is
    // incompatible. Note the exception, determined
    // by the particular incompatibility:
    table = GetIntegerTable();
    reader = new DataTableReader(GetStringTable());
    try
    {
        table.Load(reader);
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex.GetType().Name + ":" + ex.Message);
    }

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable with an IDataReader that has extra columns:");

    // Note that loading a reader with extra columns adds
    // the columns to the existing table, if possible:
    table = GetIntegerTable();
    reader = new DataTableReader(GetCustomers());
    table.Load(reader);
    PrintColumns(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable with an IDataReader that has missing columns:");

    // Note that loading a reader with missing columns causes
    // the columns to be filled with null data, if possible:
    table = GetCustomers();
    reader = new DataTableReader(GetIntegerTable());
    table.Load(reader);
    PrintColumns(table);

    // Demonstrate the various possibilites when loading data
    // into a DataTable that already contains data.
    Console.WriteLine(" ============================= ");
    Console.WriteLine("Demonstrate data considerations:");
    Console.WriteLine("Current value, Original value, (RowState)");
    Console.WriteLine(" ============================= ");
    Console.WriteLine("Original table:");

    table = SetupModifiedRows();
    DisplayRowState(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine("Data in IDataReader to be loaded:");
    DisplayRowState(GetChangedCustomers());

    // Load data into a DataTable, retrieve a DataTableReader
    // containing different data, and call the Load method.
    Console.WriteLine(" ============================= ");
    Console.WriteLine("table.Load(reader)");
    Console.WriteLine(" ============================= ");

    table = SetupModifiedRows();
    reader = new DataTableReader(GetChangedCustomers());
    table.Load(reader);
    DisplayRowState(table);

    Console.WriteLine("Press any key to continue.");
    Console.ReadKey();
}

private static void DisplayRowState(DataTable table)
{
    for (int i = 0; i <= table.Rows.Count - 1; i++)
    {
        object current = "--";
        object original = "--";
        DataRowState rowState = table.Rows[i].RowState;

        // Attempt to retrieve the current value, which doesn't exist
        // for deleted rows:
        if (rowState != DataRowState.Deleted)
        {
            current = table.Rows[i]["Name", DataRowVersion.Current];
        }

        // Attempt to retrieve the original value, which doesn't exist
        // for added rows:
        if (rowState != DataRowState.Added)
        {
            original = table.Rows[i]["Name", DataRowVersion.Original];
        }
        Console.WriteLine("{0}: {1}, {2} ({3})", i,
            current, original, rowState);
    }
}

private static DataTable GetChangedCustomers()
{
    // Create sample Customers table.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID",
        typeof(int));
    table.Columns.Add("Name", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 1, "XXX" });
    table.Rows.Add(new object[] { 2, "XXX" });
    table.Rows.Add(new object[] { 3, "XXX" });
    table.Rows.Add(new object[] { 4, "XXX" });
    table.Rows.Add(new object[] { 5, "XXX" });
    table.Rows.Add(new object[] { 6, "XXX" });
    table.AcceptChanges();
    return table;
}

private static DataTable GetCustomers()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID",
        typeof(int));
    table.Columns.Add("Name", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 1, "Mary" });
    table.Rows.Add(new object[] { 2, "Andy" });
    table.Rows.Add(new object[] { 3, "Peter" });
    table.Rows.Add(new object[] { 4, "Russ" });
    table.AcceptChanges();
    return table;
}

private static DataTable GetIntegerTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID",
        typeof(int));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 5 });
    table.Rows.Add(new object[] { 6 });
    table.Rows.Add(new object[] { 7 });
    table.Rows.Add(new object[] { 8 });
    table.AcceptChanges();
    return table;
}

private static DataTable GetStringTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID",
        typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { "Mary" });
    table.Rows.Add(new object[] { "Andy" });
    table.Rows.Add(new object[] { "Peter" });
    table.Rows.Add(new object[] { "Russ" });
    table.AcceptChanges();
    return table;
}

private static void PrintColumns(DataTable table)
{
    // Loop through all the rows in the DataTableReader
    foreach (DataRow row in table.Rows)
    {
        for (int i = 0; i < table.Columns.Count; i++)
        {
            Console.Write(row[i] + " ");
        }
        Console.WriteLine();
    }
}

private static DataTable SetupModifiedRows()
{
    // Fill a DataTable with customer info, and
    // then modify, delete, and add rows.

    DataTable table = GetCustomers();
    // Row 0 is unmodified.
    // Row 1 is modified.
    // Row 2 is deleted.
    // Row 5 is added.
    table.Rows[1]["Name"] = "Sydney";
    table.Rows[2].Delete();
    DataRow row = table.NewRow();
    row["ID"] = 5;
    row["Name"] = "Melony";
    table.Rows.Add(row);

    // Note that the code doesn't call
    // table.AcceptChanges()
    return table;
}
Sub Main()
  ' This example examines a number of scenarios involving the 
  ' DataTable.Load method.
  Console.WriteLine("Load a DataTable and infer its schema:")

  ' The table has no schema. The Load method will infer the 
  ' schema from the IDataReader:
  Dim table As New DataTable()

  ' Retrieve a data reader, based on the Customers data. In
  ' an application, this data might be coming from a middle-tier
  ' business object:
  Dim reader As New DataTableReader(GetCustomers())

  table.Load(reader)
  PrintColumns(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable from an incompatible IDataReader:")

  ' Create a table with a single integer column. Attempt
  ' to load data from a reader with a schema that is 
  ' incompatible. Note the exception, determined
  ' by the particular incompatibility:
  table = GetIntegerTable()
  reader = New DataTableReader(GetStringTable())
  Try
    table.Load(reader)
  Catch ex As Exception
    Console.WriteLine(ex.GetType.Name & ":" & ex.Message())
  End Try

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable with an IDataReader that has extra columns:")

  ' Note that loading a reader with extra columns adds
  ' the columns to the existing table, if possible:
  table = GetIntegerTable()
  reader = New DataTableReader(GetCustomers())
  table.Load(reader)
  PrintColumns(table)

  Console.WriteLine(" ============================= ")
      Console.WriteLine( _
          "Load a DataTable with an IDataReader that has missing columns:")

  ' Note that loading a reader with missing columns causes 
  ' the columns to be filled with null data, if possible:
  table = GetCustomers()
  reader = New DataTableReader(GetIntegerTable())
  table.Load(reader)
  PrintColumns(table)

  ' Demonstrate the various possibilites when loading data into
  ' a DataTable that already contains data.
  Console.WriteLine(" ============================= ")
  Console.WriteLine("Demonstrate data considerations:")
  Console.WriteLine("Current value, Original value, (RowState)")
  Console.WriteLine(" ============================= ")
  Console.WriteLine("Original table:")

  table = SetupModifiedRows()
  DisplayRowState(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine("Data in IDataReader to be loaded:")
  DisplayRowState(GetChangedCustomers())

  ' Load data into a DataTable, retrieve a DataTableReader 
  ' containing different data, and call the Load method. 
  Console.WriteLine(" ============================= ")
  Console.WriteLine("table.Load(reader)")
  Console.WriteLine(" ============================= ")

  table = SetupModifiedRows()
  reader = New DataTableReader(GetChangedCustomers())
  table.Load(reader)
  DisplayRowState(table)

  Console.WriteLine("Press any key to continue.")
  Console.ReadKey()
End Sub

Private Sub DisplayRowState(ByVal table As DataTable)
  For i As Integer = 0 To table.Rows.Count - 1
    Dim current As Object = "--"
    Dim original As Object = "--"
    Dim rowState As DataRowState = table.Rows(i).RowState

    ' Attempt to retrieve the current value, which doesn't exist
    ' for deleted rows:
    If rowState <> DataRowState.Deleted Then
      current = table.Rows(i)("Name", DataRowVersion.Current)
    End If

    ' Attempt to retrieve the original value, which doesn't exist
    ' for added rows:
    If rowState <> DataRowState.Added Then
      original = table.Rows(i)("Name", DataRowVersion.Original)
    End If
    Console.WriteLine("{0}: {1}, {2} ({3})", i, _
      current, original, rowState)
  Next
End Sub

Private Function GetChangedCustomers() As DataTable
  ' Create sample Customers table.
  Dim table As New DataTable

  ' Create two columns, ID and Name.
  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(Integer))
  table.Columns.Add("Name", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {1, "XXX"})
  table.Rows.Add(New Object() {2, "XXX"})
  table.Rows.Add(New Object() {3, "XXX"})
  table.Rows.Add(New Object() {4, "XXX"})
  table.Rows.Add(New Object() {5, "XXX"})
  table.Rows.Add(New Object() {6, "XXX"})
  table.AcceptChanges()
  Return table
End Function

Private Function GetCustomers() As DataTable
  ' Create sample Customers table.
  Dim table As New DataTable

  ' Create two columns, ID and Name.
  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(Integer))
  table.Columns.Add("Name", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {1, "Mary"})
  table.Rows.Add(New Object() {2, "Andy"})
  table.Rows.Add(New Object() {3, "Peter"})
  table.Rows.Add(New Object() {4, "Russ"})
  table.AcceptChanges()
  Return table
End Function

Private Function GetIntegerTable() As DataTable
  ' Create sample table with a single Int32 column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(Integer))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {5})
  table.Rows.Add(New Object() {6})
  table.Rows.Add(New Object() {7})
  table.Rows.Add(New Object() {8})
  table.AcceptChanges()
  Return table
End Function

Private Function GetStringTable() As DataTable
  ' Create sample table with a single String column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {"Mary"})
  table.Rows.Add(New Object() {"Andy"})
  table.Rows.Add(New Object() {"Peter"})
  table.Rows.Add(New Object() {"Russ"})
  table.AcceptChanges()
  Return table
End Function

Private Sub PrintColumns( _
   ByVal table As DataTable)

  ' Loop through all the rows in the DataTableReader.
  For Each row As DataRow In table.Rows
    For Each col As DataColumn In table.Columns
      Console.Write(row(col).ToString() & " ")
    Next
    Console.WriteLine()
  Next
End Sub

Private Function SetupModifiedRows() As DataTable
  ' Fill a DataTable with customer info, and 
  ' then modify, delete, and add rows.

  Dim table As DataTable = GetCustomers()
  ' Row 0 is unmodified.
  ' Row 1 is modified.
  ' Row 2 is deleted.
  ' Row 5 is added.
  table.Rows(1)("Name") = "Sydney"
  table.Rows(2).Delete()
  Dim row As DataRow = table.NewRow
  row("ID") = 5
  row("Name") = "Melony"
  table.Rows.Add(row)

  ' Note that the code doesn't call
  ' table.AcceptChanges()
  Return table
End Function

注解

方法 Load 使用加载 IDataReader的第一个结果集,成功完成后,将读取器的位置设置为下一个结果集(如果有)。 转换数据时, Load 方法使用与 方法相同的转换规则 DbDataAdapter.Fill

从实例加载数据时, Load 方法必须考虑三个 IDataReader 特定问题:架构、数据和事件操作。 使用架构时, Load 方法可能会遇到下表中所述的条件。 架构操作针对所有导入的结果集进行,即使是那些没有数据的结果集。

条件 行为
没有 DataTable 架构。 方法 Load 根据导入 IDataReader的结果集推断架构。
具有 DataTable 架构,但它与加载的架构不兼容。 方法 Load 引发与尝试将数据加载到不兼容架构时发生的特定错误对应的异常。
架构兼容,但加载的结果集架构包含 中不存在的 DataTable列。 方法 Load 将额外的列添加到 DataTable的 架构。 如果 和加载的结果集中的对应列 DataTable 不兼容值,则 方法将引发异常。 方法还从结果集中检索所有添加列的约束信息。 除主键约束的情况外,仅当当前 DataTable 在加载操作开始时不包含任何列时,才会使用此约束信息。
架构是兼容的,但加载的结果集架构包含的列比 包含的 DataTable列少。 如果缺少的列定义了默认值,或者该列的数据类型可为 null,则 Load 方法允许添加行,用默认值或 null 值替换缺失列。 如果没有默认值 或 null 可以使用,则 Load 方法将引发异常。 如果未提供任何特定的默认值,则 Load 方法使用 null 值作为隐含默认值。

在考虑方法在数据操作方面的行为 Load 之前,请考虑 内的每一 DataTable 行都维护每列的当前值和原始值。 这些值可能是等效的,或者如果行中的数据在填充 后已更改, DataTable则这些值可能不同。 有关详细信息,请参阅 行状态和行版本

此方法的 Load 此版本尝试保留每一行中的当前值,使原始值保持不变。 (如果要更好地控制传入数据的行为,请参阅 DataTable.Load.) 如果现有行和传入行包含相应的主键值,则使用其当前行状态值处理该行,否则将它视为新行。

就事件操作而言, RowChanging 事件发生在每一行更改之前,事件 RowChanged 在更改每行之后发生。 在每种情况下, Action 传递给事件处理程序的 DataRowChangeEventArgs 实例的 属性都包含有关与事件关联的特定操作的信息。 此操作值取决于加载操作前行的状态。 在每种情况下,这两个事件都会发生,并且每个事件的操作都是相同的。 操作可以应用于每一行的当前版本或原始版本,也可以应用于两者,具体取决于当前行状态。

下表显示了 方法的行为 Load 。 标记为“ (不存在) ”的最后一行 () 描述了与任何现有行不匹配的传入行的行为。 此表中的每个单元格都描述行内字段的当前值和原始值,以及 DataRowState 方法完成后的值的 Load 。 在这种情况下, 方法不允许指示加载选项,并使用默认值 PreserveChanges

现有 DataRowState 方法和事件操作后 Load 的值
已添加 当前 = <现有>

原始 = <传入>

状态 = <已修改>

RowAction = ChangeOriginal
修改时间 当前 = <现有>

原始 = <传入>

状态 = <已修改>

RowAction = ChangeOriginal
Deleted 当前 = <不可用>

原始 = <传入>

状态 = <已删除>

RowAction = ChangeOriginal
不变 当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
(不存在) 当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal

可以通过使用 和 AutoIncrementReadOnly属性来约束 中的DataColumn值。 方法 Load 以与列的属性定义的行为一致的方式处理此类列。 上的 DataColumn 只读约束仅适用于内存中发生的更改。 方法 Load 的 将覆盖只读列值(如果需要)。

为了确定用于比较当前行和传入行的主键字段的版本, Load 该方法使用行内主键值的原始版本(如果存在)。 否则, Load 方法使用当前版本的主键字段。

另请参阅

适用于

Load(IDataReader, LoadOption)

Source:
DataTable.cs
Source:
DataTable.cs
Source:
DataTable.cs

通过所提供的 IDataReader,用某个数据源的值填充 DataTable。 如果 DataTable 已包含行,则从数据源传入的数据根据 loadOption 参数的值与现有行合并。

public:
 void Load(System::Data::IDataReader ^ reader, System::Data::LoadOption loadOption);
public void Load (System.Data.IDataReader reader, System.Data.LoadOption loadOption);
member this.Load : System.Data.IDataReader * System.Data.LoadOption -> unit
Public Sub Load (reader As IDataReader, loadOption As LoadOption)

参数

reader
IDataReader

提供一个或多个结果集的 IDataReader

loadOption
LoadOption

LoadOption 枚举的值,指示 DataTable 中已有的行如何与共享相同主键的传入行合并。

示例

以下示例演示了调用 Load 方法所涉及的几个问题。 首先,该示例侧重于架构问题,包括从加载 IDataReader的 推断架构,然后处理不兼容的架构,以及包含缺失列或其他列的架构。 然后,该示例侧重于数据问题,包括处理各种加载选项。

static void Main()
{
    // This example examines a number of scenarios involving the
    // DataTable.Load method.
    Console.WriteLine("Load a DataTable and infer its schema:");

    // The table has no schema. The Load method will infer the
    // schema from the IDataReader:
    DataTable table = new DataTable();

    // Retrieve a data reader, based on the Customers data. In
    // an application, this data might be coming from a middle-tier
    // business object:
    DataTableReader reader = new DataTableReader(GetCustomers());

    table.Load(reader);
    PrintColumns(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable from an incompatible IDataReader:");

    // Create a table with a single integer column. Attempt
    // to load data from a reader with a schema that is
    // incompatible. Note the exception, determined
    // by the particular incompatibility:
    table = GetIntegerTable();
    reader = new DataTableReader(GetStringTable());
    try
    {
        table.Load(reader);
    }
    catch (Exception ex)
    {
        Console.WriteLine(ex.GetType().Name + ":" + ex.Message);
    }

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable with an IDataReader that has extra columns:");

    // Note that loading a reader with extra columns adds
    // the columns to the existing table, if possible:
    table = GetIntegerTable();
    reader = new DataTableReader(GetCustomers());
    table.Load(reader);
    PrintColumns(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine(
        "Load a DataTable with an IDataReader that has missing columns:");

    // Note that loading a reader with missing columns causes
    // the columns to be filled with null data, if possible:
    table = GetCustomers();
    reader = new DataTableReader(GetIntegerTable());
    table.Load(reader);
    PrintColumns(table);

    // Demonstrate the various possibilites when loading data into
    // a DataTable that already contains data.
    Console.WriteLine(" ============================= ");
    Console.WriteLine("Demonstrate data considerations:");
    Console.WriteLine("Current value, Original value, (RowState)");
    Console.WriteLine(" ============================= ");
    Console.WriteLine("Original table:");

    table = SetupModifiedRows();
    DisplayRowState(table);

    Console.WriteLine(" ============================= ");
    Console.WriteLine("Data in IDataReader to be loaded:");
    DisplayRowState(GetChangedCustomers());

    PerformDemo(LoadOption.OverwriteChanges);
    PerformDemo(LoadOption.PreserveChanges);
    PerformDemo(LoadOption.Upsert);

    Console.WriteLine("Press any key to continue.");
    Console.ReadKey();
}

private static void DisplayRowState(DataTable table)
{
    for (int i = 0; i <= table.Rows.Count - 1; i++)
    {
        object current = "--";
        object original = "--";
        DataRowState rowState = table.Rows[i].RowState;

        // Attempt to retrieve the current value, which doesn't exist
        // for deleted rows:
        if (rowState != DataRowState.Deleted)
        {
            current = table.Rows[i]["Name", DataRowVersion.Current];
        }

        // Attempt to retrieve the original value, which doesn't exist
        // for added rows:
        if (rowState != DataRowState.Added)
        {
            original = table.Rows[i]["Name", DataRowVersion.Original];
        }
        Console.WriteLine("{0}: {1}, {2} ({3})", i,
            current, original, rowState);
    }
}

private static DataTable GetChangedCustomers()
{
    // Create sample Customers table.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));
    table.Columns.Add("Name", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 0, "XXX" });
    table.Rows.Add(new object[] { 1, "XXX" });
    table.Rows.Add(new object[] { 2, "XXX" });
    table.Rows.Add(new object[] { 3, "XXX" });
    table.Rows.Add(new object[] { 4, "XXX" });
    table.AcceptChanges();
    return table;
}

private static DataTable GetCustomers()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));
    table.Columns.Add("Name", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 0, "Mary" });
    table.Rows.Add(new object[] { 1, "Andy" });
    table.Rows.Add(new object[] { 2, "Peter" });
    table.AcceptChanges();
    return table;
}

private static DataTable GetIntegerTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 4 });
    table.Rows.Add(new object[] { 5 });
    table.AcceptChanges();
    return table;
}

private static DataTable GetStringTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { "Mary" });
    table.Rows.Add(new object[] { "Andy" });
    table.Rows.Add(new object[] { "Peter" });
    table.AcceptChanges();
    return table;
}

private static void PerformDemo(LoadOption optionForLoad)
{

    // Load data into a DataTable, retrieve a DataTableReader containing
    // different data, and call the Load method. Depending on the
    // LoadOption value passed as a parameter, this procedure displays
    // different results in the DataTable.
    Console.WriteLine(" ============================= ");
    Console.WriteLine("table.Load(reader, {0})", optionForLoad);
    Console.WriteLine(" ============================= ");

    DataTable table = SetupModifiedRows();
    DataTableReader reader = new DataTableReader(GetChangedCustomers());
    table.RowChanging +=new DataRowChangeEventHandler(HandleRowChanging);

    table.Load(reader, optionForLoad);
    Console.WriteLine();
    DisplayRowState(table);
}

private static void PrintColumns(DataTable table)
{
    // Loop through all the rows in the DataTableReader
    foreach (DataRow row in table.Rows)
    {
        for (int i = 0; i < table.Columns.Count; i++)
        {
            Console.Write(row[i] + " ");
        }
        Console.WriteLine();
    }
}

private static DataTable SetupModifiedRows()
{
    // Fill a DataTable with customer info, and
    // then modify, delete, and add rows.

    DataTable table = GetCustomers();
    // Row 0 is unmodified.
    // Row 1 is modified.
    // Row 2 is deleted.
    // Row 3 is added.
    table.Rows[1]["Name"] = "Sydney";
    table.Rows[2].Delete();
    DataRow row = table.NewRow();
    row["ID"] = 3;
    row["Name"] = "Melony";
    table.Rows.Add(row);

    // Note that the code doesn't call
    // table.AcceptChanges()
    return table;
}

static void HandleRowChanging(object sender, DataRowChangeEventArgs e)
{
    Console.WriteLine(
        "RowChanging event: ID = {0}, action = {1}", e.Row["ID"], e.Action);
}
Sub Main()
  Dim table As New DataTable()

  ' This example examines a number of scenarios involving the
  '  DataTable.Load method.
  Console.WriteLine("Load a DataTable and infer its schema:")

  ' Retrieve a data reader, based on the Customers data. In
  ' an application, this data might be coming from a middle-tier
  ' business object:
  Dim reader As New DataTableReader(GetCustomers())

  ' The table has no schema. The Load method will infer the 
  ' schema from the IDataReader:
  table.Load(reader)
  PrintColumns(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable from an incompatible IDataReader:")

  ' Create a table with a single integer column. Attempt
  ' to load data from a reader with a schema that is 
  ' incompatible. Note the exception, determined
  ' by the particular incompatibility:
  table = GetIntegerTable()
  reader = New DataTableReader(GetStringTable())
  Try
    table.Load(reader)
  Catch ex As Exception
    Console.WriteLine(ex.GetType.Name & ":" & ex.Message())
  End Try

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable with an IDataReader that has extra columns:")

  ' Note that loading a reader with extra columns adds
  ' the columns to the existing table, if possible:
  table = GetIntegerTable()
  reader = New DataTableReader(GetCustomers())
  table.Load(reader)
  PrintColumns(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine( _
      "Load a DataTable with an IDataReader that has missing columns:")

  ' Note that loading a reader with missing columns causes 
  ' the columns to be filled with null data, if possible:
  table = GetCustomers()
  reader = New DataTableReader(GetIntegerTable())
  table.Load(reader)
  PrintColumns(table)

  ' Demonstrate the various possibilites when loading data into
  ' a DataTable that already contains data.
  Console.WriteLine(" ============================= ")
  Console.WriteLine("Demonstrate data considerations:")
  Console.WriteLine("Current value, Original value, (RowState)")
  Console.WriteLine(" ============================= ")
  Console.WriteLine("Original table:")

  table = SetupModifiedRows()
  DisplayRowState(table)

  Console.WriteLine(" ============================= ")
  Console.WriteLine("Data in IDataReader to be loaded:")
  DisplayRowState(GetChangedCustomers())

  PerformDemo(LoadOption.OverwriteChanges)
  PerformDemo(LoadOption.PreserveChanges)
  PerformDemo(LoadOption.Upsert)

  Console.WriteLine("Press any key to continue.")
  Console.ReadKey()
End Sub

Private Sub DisplayRowState(ByVal table As DataTable)
  For i As Integer = 0 To table.Rows.Count - 1
    Dim current As Object = "--"
    Dim original As Object = "--"
    Dim rowState As DataRowState = table.Rows(i).RowState

    ' Attempt to retrieve the current value, which doesn't exist
    ' for deleted rows:
    If rowState <> DataRowState.Deleted Then
      current = table.Rows(i)("Name", DataRowVersion.Current)
    End If

    ' Attempt to retrieve the original value, which doesn't exist
    ' for added rows:
    If rowState <> DataRowState.Added Then
      original = table.Rows(i)("Name", DataRowVersion.Original)
    End If
    Console.WriteLine("{0}: {1}, {2} ({3})", i, _
      current, original, rowState)
  Next
End Sub

Private Function GetChangedCustomers() As DataTable
  ' Create sample Customers table.
  Dim table As New DataTable

  ' Create two columns, ID and Name.
  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(Integer))
  table.Columns.Add("Name", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {0, "XXX"})
  table.Rows.Add(New Object() {1, "XXX"})
  table.Rows.Add(New Object() {2, "XXX"})
  table.Rows.Add(New Object() {3, "XXX"})
  table.Rows.Add(New Object() {4, "XXX"})
  table.AcceptChanges()
  Return table
End Function

Private Function GetCustomers() As DataTable
  ' Create sample Customers table.
  Dim table As New DataTable

  ' Create two columns, ID and Name.
  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(Integer))
  table.Columns.Add("Name", GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {0, "Mary"})
  table.Rows.Add(New Object() {1, "Andy"})
  table.Rows.Add(New Object() {2, "Peter"})
  table.AcceptChanges()
  Return table
End Function

Private Function GetIntegerTable() As DataTable
  ' Create sample table with a single Int32 column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(Integer))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {4})
  table.Rows.Add(New Object() {5})
  table.AcceptChanges()
  Return table
End Function

Private Function GetStringTable() As DataTable
  ' Create sample table with a single String column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {"Mary"})
  table.Rows.Add(New Object() {"Andy"})
  table.Rows.Add(New Object() {"Peter"})
  table.AcceptChanges()
  Return table
End Function

Private Sub PerformDemo(ByVal optionForLoad As LoadOption)

  ' Load data into a DataTable, retrieve a DataTableReader containing
  ' different data, and call the Load method. Depending on the
  ' LoadOption value passed as a parameter, this procedure displays
  ' different results in the DataTable.
  Console.WriteLine(" ============================= ")
  Console.WriteLine("table.Load(reader, {0})", optionForLoad)
  Console.WriteLine(" ============================= ")

  Dim table As DataTable = SetupModifiedRows()
  Dim reader As New DataTableReader(GetChangedCustomers())
  AddHandler table.RowChanging, New _
      DataRowChangeEventHandler(AddressOf HandleRowChanging)

  table.Load(reader, optionForLoad)
  Console.WriteLine()
  DisplayRowState(table)
End Sub

Private Sub PrintColumns( _
   ByVal table As DataTable)

  ' Loop through all the rows in the DataTableReader.
  For Each row As DataRow In table.Rows
    For Each col As DataColumn In table.Columns
      Console.Write(row(col).ToString() & " ")
    Next
    Console.WriteLine()
  Next
End Sub

Private Function SetupModifiedRows() As DataTable
  ' Fill a DataTable with customer info, and 
  ' then modify, delete, and add rows.

  Dim table As DataTable = GetCustomers()
  ' Row 0 is unmodified.
  ' Row 1 is modified.
  ' Row 2 is deleted.
  ' Row 3 is added.
  table.Rows(1)("Name") = "Sydney"
  table.Rows(2).Delete()
  Dim row As DataRow = table.NewRow
  row("ID") = 3
  row("Name") = "Melony"
  table.Rows.Add(row)

  ' Note that the code doesn't call
  ' table.AcceptChanges()
  Return table
End Function

Private Sub HandleRowChanging(ByVal sender As Object, _
      ByVal e As System.Data.DataRowChangeEventArgs)
  Console.WriteLine( _
      "RowChanging event: ID = {0}, action = {1}", e.Row("ID"), e.Action)
End Sub

注解

方法 Load 使用加载 IDataReader的第一个结果集,成功完成后,将读取器的位置设置为下一个结果集(如果有)。 转换数据时, Load 方法使用与 方法相同的转换规则 Fill

从实例加载数据时, Load 方法必须考虑三个 IDataReader 特定问题:架构、数据和事件操作。 使用架构时, Load 方法可能会遇到下表中所述的条件。 架构操作针对所有导入的结果集进行,即使是不包含任何数据的结果集。

条件 行为
没有 DataTable 架构。 方法 Load 根据导入 IDataReader的结果集推断架构。
具有 DataTable 架构,但它与加载的架构不兼容。 方法 Load 引发与尝试将数据加载到不兼容架构时发生的特定错误对应的异常。
架构是兼容的,但加载的结果集架构包含 中不存在的 DataTable列。 方法 Load 将额外的列添加到 DataTable的架构。 如果 中的相应列和加载的结果集中的相应列 DataTable 与值不兼容,则 方法将引发异常。 方法还从结果集中检索所有添加列的约束信息。 除主键约束的情况外,仅当当前 DataTable 在加载操作开始时不包含任何列时,才使用此约束信息。
架构是兼容的,但加载的结果集架构包含的列比 包含的 DataTable列少。 如果缺少的列定义了默认值,或者列的数据类型可以为 null,则 Load 该方法允许添加行,用默认值或 null 值替换缺失列。 如果不能使用默认值或 null,则 Load 该方法将引发异常。 如果未提供特定的默认值,该方法 Load 将使用 null 值作为隐式默认值。

在考虑方法在数据操作方面的行为 Load 之前,请考虑 中的每一 DataTable 行同时保留每列的当前值和原始值。 这些值可能等效,或者如果行中的数据在填充 后已更改, DataTable则这些值可能不同。 有关详细信息 ,请参阅行状态和行版本

在此方法调用中,指定的 LoadOption 参数会影响传入数据的处理。 Load 方法应如何处理加载主键与现有行相同的行? 它应该修改当前值和/或原始值? 这些问题等都由 loadOption 参数控制。

如果现有行和传入行包含相应的主键值,则使用其当前行状态值处理该行,否则将被视为新行。

就事件操作而言,事件发生在 RowChanging 每一行更改之前,事件 RowChanged 在每一行更改后发生。 在每种情况下, Action 传递给事件处理程序的 DataRowChangeEventArgs 实例的 属性都包含与事件关联的特定操作的相关信息。 此操作值因加载操作前行的状态而异。 在每种情况下,这两个事件都会发生,并且每个事件的操作都是相同的。 操作可应用于每行的当前版本或原始版本,或同时应用于两者,具体取决于当前行状态。

下表显示了使用每个 LoadOption 值调用 Load 方法时的行为,还显示了值如何与正在加载的行的行状态交互。 标记为“ (不存在) ”的最后一行 () 描述了与任何现有行不匹配的传入行的行为。 此表中的每个单元格描述行中某个字段的当前值和原始值,以及 DataRowState 方法完成后的值的 Load

现有 DataRowState Upsert OverwriteChanges PreserveChanges (默认行为)
已添加 当前 = <传入>

原始 = -<不可用>

状态 = <已添加>

RowAction = Change
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <现有>

原始 = <传入>

状态 = <已修改>

RowAction = ChangeOriginal
修改时间 当前 = <传入>

原始 = <现有>

状态 = <已修改>

RowAction = Change
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <现有>

原始 = <传入>

状态 = <已修改>

RowAction =ChangeOriginal
Deleted (加载不会影响已删除的行)

当前 = ---

原始 = <现有>

状态 = <已删除>

(添加了具有以下特征的新行)

当前 = <传入>

原始 = <不可用>

状态 = <已添加>

RowAction = Add
撤消删除和

当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <不可用>

原始 = <传入>

状态 = <已删除>

RowAction = ChangeOriginal
不变 当前 = <传入>

原始 = <现有>

如果新值与现有值相同,则

状态 = <未更改>

RowAction = Nothing

Else

状态 = <已修改>

RowAction = Change
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
不存在) 当前 = <传入>

原始 = <不可用>

状态 = <已添加>

RowAction = Add
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal

通过使用 和 AutoIncrementReadOnly属性,可以约束 中的DataColumn值。 方法 Load 以与列的属性定义的行为一致的方式处理此类列。 上的 DataColumn 只读约束仅适用于内存中发生的更改。 如果需要,该方法 Load 的 将覆盖只读列值。

如果在调用 Load 方法时指定 OverwriteChanges 或 PreserveChanges 选项,则假定传入数据来自 DataTable的主数据源,并且 DataTable 跟踪更改,并将更改传播回数据源。 如果选择“Upsert”选项,则假定数据来自一个辅助数据源,例如中间层组件提供的数据,可能由用户更改。 在这种情况下,假设目的是聚合 中 DataTable一个或多个数据源的数据,然后可能将数据传播回主数据源。 参数 LoadOption 用于确定要用于主键比较的行的特定版本。 下表提供了详细信息。

加载选项 用于主键比较的 DataRow 版本
OverwriteChanges 原始版本(如果存在),否则为当前版本
PreserveChanges 原始版本(如果存在),否则为当前版本
Upsert 当前版本(如果存在),否则为原始版本

另请参阅

适用于

Load(IDataReader, LoadOption, FillErrorEventHandler)

Source:
DataTable.cs
Source:
DataTable.cs
Source:
DataTable.cs

通过所提供的使用错误处理委托的 IDataReader,用某个数据源中的值填充 DataTable

public:
 virtual void Load(System::Data::IDataReader ^ reader, System::Data::LoadOption loadOption, System::Data::FillErrorEventHandler ^ errorHandler);
public virtual void Load (System.Data.IDataReader reader, System.Data.LoadOption loadOption, System.Data.FillErrorEventHandler? errorHandler);
public virtual void Load (System.Data.IDataReader reader, System.Data.LoadOption loadOption, System.Data.FillErrorEventHandler errorHandler);
abstract member Load : System.Data.IDataReader * System.Data.LoadOption * System.Data.FillErrorEventHandler -> unit
override this.Load : System.Data.IDataReader * System.Data.LoadOption * System.Data.FillErrorEventHandler -> unit
Public Overridable Sub Load (reader As IDataReader, loadOption As LoadOption, errorHandler As FillErrorEventHandler)

参数

reader
IDataReader

提供结果集的 IDataReader

loadOption
LoadOption

LoadOption 枚举的值,指示 DataTable 中已有的行如何与共享相同主键的传入行合并。

errorHandler
FillErrorEventHandler

加载数据时出现错误的情况下要调用的 FillErrorEventHandler 委托。

示例

static void Main()
{
    // Attempt to load data from a data reader in which
    // the schema is incompatible with the current schema.
    // If you use exception handling, you won't get the chance
    // to examine each row, and each individual table,
    // as the Load method progresses.
    // By taking advantage of the FillErrorEventHandler delegate,
    // you can interact with the Load process as an error occurs,
    // attempting to fix the problem, or simply continuing or quitting
    // the Load process:
    DataTable table = GetIntegerTable();
    DataTableReader reader = new DataTableReader(GetStringTable());
    table.Load(reader, LoadOption.OverwriteChanges, FillErrorHandler);

    Console.WriteLine("Press any key to continue.");
    Console.ReadKey();
}

private static DataTable GetIntegerTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(int));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { 4 });
    table.Rows.Add(new object[] { 5 });
    table.AcceptChanges();
    return table;
}

private static DataTable GetStringTable()
{
    // Create sample Customers table, in order
    // to demonstrate the behavior of the DataTableReader.
    DataTable table = new DataTable();

    // Create two columns, ID and Name.
    DataColumn idColumn = table.Columns.Add("ID", typeof(string));

    // Set the ID column as the primary key column.
    table.PrimaryKey = new DataColumn[] { idColumn };

    table.Rows.Add(new object[] { "Mary" });
    table.Rows.Add(new object[] { "Andy" });
    table.Rows.Add(new object[] { "Peter" });
    table.AcceptChanges();
    return table;
}

static void FillErrorHandler(object sender, FillErrorEventArgs e)
{
    // You can use the e.Errors value to determine exactly what
    // went wrong.
    if (e.Errors.GetType() == typeof(System.FormatException))
    {
        Console.WriteLine("Error when attempting to update the value: {0}",
            e.Values[0]);
    }

    // Setting e.Continue to True tells the Load
    // method to continue trying. Setting it to False
    // indicates that an error has occurred, and the
    // Load method raises the exception that got
    // you here.
    e.Continue = true;
}
Sub Main()
  Dim table As New DataTable()

  ' Attempt to load data from a data reader in which
  ' the schema is incompatible with the current schema.
  ' If you use exception handling, you won't get the chance
  ' to examine each row, and each individual table,
  ' as the Load method progresses.
  ' By taking advantage of the FillErrorEventHandler delegate,
  ' you can interact with the Load process as an error occurs,
  ' attempting to fix the problem, or simply continuing or quitting
  ' the Load process:
  table = GetIntegerTable()
  Dim reader As New DataTableReader(GetStringTable())
  table.Load(reader, LoadOption.OverwriteChanges, _
      AddressOf FillErrorHandler)

  Console.WriteLine("Press any key to continue.")
  Console.ReadKey()
End Sub

Private Sub FillErrorHandler(ByVal sender As Object, _
  ByVal e As FillErrorEventArgs)
  ' You can use the e.Errors value to determine exactly what
  ' went wrong.
  If e.Errors.GetType Is GetType(System.FormatException) Then
    Console.WriteLine("Error when attempting to update the value: {0}", _
      e.Values(0))
  End If

  ' Setting e.Continue to True tells the Load
  ' method to continue trying. Setting it to False
  ' indicates that an error has occurred, and the 
  ' Load method raises the exception that got 
  ' you here.
  e.Continue = True
End Sub

Private Function GetIntegerTable() As DataTable
  ' Create sample table with a single Int32 column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", GetType(Integer))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {4})
  table.Rows.Add(New Object() {5})
  table.TableName = "IntegerTable"
  table.AcceptChanges()
  Return table
End Function

Private Function GetStringTable() As DataTable
  ' Create sample table with a single String column.
  Dim table As New DataTable

  Dim idColumn As DataColumn = table.Columns.Add("ID", _
      GetType(String))

  ' Set the ID column as the primary key column.
  table.PrimaryKey = New DataColumn() {idColumn}

  table.Rows.Add(New Object() {"Mary"})
  table.Rows.Add(New Object() {"Andy"})
  table.Rows.Add(New Object() {"Peter"})
  table.AcceptChanges()
  Return table
End Function

Private Sub PrintColumns( _
   ByVal table As DataTable)

  ' Loop through all the rows in the DataTableReader.
  For Each row As DataRow In table.Rows
    For Each col As DataColumn In table.Columns
      Console.Write(row(col).ToString() & " ")
    Next
    Console.WriteLine()
  Next
End Sub

注解

方法 Load 使用加载 IDataReader的第一个结果集,成功完成后,将读取器的位置设置为下一个结果集(如果有)。 转换数据时, Load 方法使用与 方法相同的转换规则 DbDataAdapter.Fill

从实例加载数据时, Load 方法必须考虑三个 IDataReader 特定问题:架构、数据和事件操作。 使用架构时, Load 方法可能会遇到下表中所述的条件。 架构操作针对所有导入的结果集进行,即使是不包含任何数据的结果集。

条件 行为
没有 DataTable 架构。 方法 Load 根据导入 IDataReader的结果集推断架构。
具有 DataTable 架构,但它与加载的架构不兼容。 方法 Load 引发与尝试将数据加载到不兼容架构时发生的特定错误对应的异常。
架构是兼容的,但加载的结果集架构包含 中不存在的 DataTable列。 方法 Load 将额外的列 () 添加到 DataTable的架构中。 如果 中的相应列和加载的结果集中的相应列 DataTable 与值不兼容,则 方法将引发异常。 方法还从结果集中检索所有添加列的约束信息。 除主键约束的情况外,仅当当前 DataTable 在加载操作开始时不包含任何列时,才使用此约束信息。
架构是兼容的,但加载的结果集架构包含的列比 包含的 DataTable列少。 如果缺少的列定义了默认值,或者列的数据类型可以为 null,则 Load 该方法允许添加行,用默认值或 null 值替换缺失列。 如果不能使用默认值或 null,则 Load 该方法将引发异常。 如果未提供特定的默认值,该方法 Load 将使用 null 值作为隐式默认值。

在考虑方法在数据操作方面的行为 Load 之前,请考虑 中的每一 DataTable 行同时保留每列的当前值和原始值。 这些值可能等效,或者如果行中的数据在填充 后已更改, DataTable则这些值可能不同。 有关详细信息 ,请参阅行状态和行版本

在此方法调用中,指定的 LoadOption 参数会影响传入数据的处理。 Load 方法应如何处理加载主键与现有行相同的行? 它应该修改当前值和/或原始值? 这些问题等都由 loadOption 参数控制。

如果现有行和传入行包含相应的主键值,则使用其当前行状态值处理该行,否则将被视为新行。

就事件操作而言,事件发生在 RowChanging 每一行更改之前,事件 RowChanged 在每一行更改后发生。 在每种情况下, Action 传递给事件处理程序的 DataRowChangeEventArgs 实例的 属性都包含与事件关联的特定操作的相关信息。 此操作值因加载操作前行的状态而异。 在每种情况下,这两个事件都会发生,并且每个事件的操作都是相同的。 操作可应用于每行的当前版本或原始版本,或同时应用于两者,具体取决于当前行状态。

下表显示了使用每个 LoadOption 值调用 Load 方法时的行为,还显示了值如何与正在加载的行的行状态交互。 标记为“ (不存在) ”的最后一行 () 描述了与任何现有行不匹配的传入行的行为。 此表中的每个单元格描述行中某个字段的当前值和原始值,以及 DataRowState 方法完成后的值的 Load

现有 DataRowState Upsert OverwriteChanges PreserveChanges (默认行为)
已添加 当前 = <传入>

原始 = -<不可用>

状态 = <已添加>

RowAction = Change
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <现有>

原始 = <传入>

状态 = <已修改>

RowAction = ChangeOriginal
修改时间 当前 = <传入>

原始 = <现有>

状态 = <已修改>

RowAction = Change
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <现有>

原始 = <传入>

状态 = <已修改>

RowAction =ChangeOriginal
eleted (加载不会影响已删除的行)

当前 = ---

原始 = <现有>

状态 = <已删除>

(添加了具有以下特征的新行)

当前 = <传入>

原始 = <不可用>

状态 = <已添加>

RowAction = Add
撤消删除和

当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <不可用>

原始 = <传入>

状态 = <已删除>

RowAction = ChangeOriginal
不变 当前 = <传入>

原始 = <现有>

如果新值与现有值相同,则

状态 = <未更改>

RowAction = Nothing

Else

状态 = <已修改>

RowAction = Change
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
不存在) 当前 = <传入>

原始 = <不可用>

状态 = <已添加>

RowAction = Add
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal
当前 = <传入>

原始 = <传入>

状态 = <未更改>

RowAction = ChangeCurrentAndOriginal

通过使用 和 AutoIncrementReadOnly属性,可以约束 中的DataColumn值。 方法 Load 以与列的属性定义的行为一致的方式处理此类列。 上的 DataColumn 只读约束仅适用于内存中发生的更改。 如果需要,该方法 Load 的 将覆盖只读列值。

如果在调用 Load 方法时指定 OverwriteChanges 或 PreserveChanges 选项,则假定传入数据来自 DataTable的主数据源,并且 DataTable 跟踪更改,并将更改传播回数据源。 如果选择“Upsert”选项,则假定数据来自一个辅助数据源,例如中间层组件提供的数据,可能由用户更改。 在这种情况下,假设目的是聚合 中 DataTable一个或多个数据源的数据,然后可能将数据传播回主数据源。 参数 LoadOption 用于确定要用于主键比较的行的特定版本。 下表提供了详细信息。

加载选项 用于主键比较的 DataRow 版本
OverwriteChanges 原始版本(如果存在),否则为当前版本
PreserveChanges 原始版本(如果存在),否则为当前版本
Upsert 当前版本(如果存在),否则为原始版本

errorHandler参数是一个FillErrorEventHandler委托,它引用加载数据时发生错误时调用的过程。 FillErrorEventArgs传递给过程的参数提供属性,使你能够检索有关发生的错误、当前数据行和DataTable正在填充的 的信息。 使用此委托机制(而不是更简单的 try/catch 块)可以确定错误、处理情况,并根据需要继续处理。 参数 FillErrorEventArgs 提供属性 Continue :将此属性设置为 true 以指示已处理错误并希望继续处理。 将 属性设置为 false 以指示要停止处理。 请注意,将 属性设置为 false 会导致触发问题的代码引发异常。

另请参阅

适用于