次の方法で共有


型指定された DataSet による注釈の使用

注釈を使用すると、基になるスキーマを変更せずに型指定された DataSet の要素の名前を変更できます。基になるスキーマの要素の名前を変更すると、データ ソースにあるオブジェクトへの参照が失われるだけでなく、型指定された DataSet がデータ ソースにないオブジェクトを参照することになります。

注釈を使用すると、基になるスキーマを変更せずに、型指定された DataSet のオブジェクトをわかりやすい名前にカスタマイズできるため、コードが読みやすくなり、型指定された DataSet がクライアントで使用しやすくなります。たとえば、次のコード例では、Northwind データベースの Customers テーブルのスキーマ要素は、CustomersRow という名前の DataRow オブジェクト名および Customers という名前の DataRowCollection となります。

<xs:element name="Customers">
  <xs:complexType>
    <xs:sequence>
      <xs:element name="CustomerID" type="xs:string" minOccurs="0" />
    </xs:sequence>
  </xs:complexType>
</xs:element>

Customers という DataRowCollection 名は、クライアント コードでは意味がありますが、CustomersRow という DataRow 名は単一のオブジェクトであるため、誤解が生じます。また、一般的なシナリオでは、CustomersRow オブジェクトは Row ID を指定せずに参照されるため、単に Customer オブジェクトとして参照されます。この問題を解決するには、スキーマに注釈を付け、DataRow オブジェクトと DataRowCollection オブジェクトに新しい名前を指定します。上記のスキーマに注釈を付けたコード例を次に示します。

<xs:element name="Customers" codegen:typedName="Customer" codegen:typedPlural="Customers">
  <xs:complexType>
    <xs:sequence>
      <xs:element name="CustomerID" type="xs:string" minOccurs="0" />
    </xs:sequence>
  </xs:complexType>
</xs:element>

Customer という typedName 値を指定すると、Customer という DataRow オブジェクト名になります。Customers という typedPlural 値を指定すると、Customers という DataRowCollection 名が保存されます。

使用できる注釈を次の表に示します。

注釈 説明
typedName オブジェクト名。
typedPlural オブジェクトのコレクション名。
typedParent 親の関係で参照される場合のオブジェクト名。
typedChildren 子の関係からオブジェクトを返すメソッド名。
nullValue 基になる値が DBNull の場合の値。nullValue の注釈については、次の表を参照してください。既定値は _throw です。

nullValue 注釈に指定できる値を次の表に示します。

nullValue 説明
Replacement Value 返される値を指定します。返された値は要素の型と一致する必要があります。たとえば、整数型フィールドが null の場合に 0 を返すために nullValue="0" を使用します。
_throw 例外をスローします。これは、既定の設定です。
_null プリミティブ型が見つかった場合は、null 参照を返すか、例外をスローします。
_empty 文字列の場合は String.Empty を、それ以外の場合は空のコンストラクタから作成されたオブジェクトを返します。プリミティブ型が見つかった場合、例外をスローします。

型指定された DataSet のオブジェクトの既定値と使用できる注釈を次の表に示します。

オブジェクト/メソッド/イベント 既定値 注釈
DataTable TableNameDataTable typedPlural
DataTable のメソッド NewTableNameRow

AddTableNameRow

DeleteTableNameRow

typedName
DataRowCollection TableName typedPlural
DataRow TableNameRow typedName
DataColumn DataTable.ColumnNameColumn

DataRow.ColumnName

typedName
プロパティ PropertyName typedName
Child Accessor GetChildTableNameRows typedChildren
Parent Accessor TableNameRow typedParent
DataSet イベント TableNameRowChangeEvent

TableNameRowChangeEventHandler

typedName

型指定された DataSet の注釈を使用するには、XML スキーマ定義言語 (XSD) スキーマに次の xmlns 参照を含める必要があります。

xmlns:codegen="urn:schemas-microsoft-com:xml-msprop"

含まれた Orders テーブルと関係のある Northwind データベースの Customers テーブルを表示する注釈の付いたスキーマのコード例を次に示します。

<?xml version="1.0" encoding="utf-8"?>
<xs:schema id="CustomerDataSet" 
      xmlns:codegen="urn:schemas-microsoft-com:xml-msprop"
       
      xmlns:xs="http://www.w3.org/2001/XMLSchema" 
      xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
  <xs:element name="CustomerDataSet" msdata:IsDataSet="true">
    <xs:complexType>
      <xs:choice maxOccurs="unbounded">
        <xs:element name="Customers" codegen:typedName="Customer" codegen:typedPlural="Customers">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="CustomerID" codegen:typedName="CustomerID" type="xs:string" minOccurs="0" />
              <xs:element name="CompanyName" codegen:typedName="CompanyName" type="xs:string" minOccurs="0" />
              <xs:element name="Phone" codegen:typedName="Phone" codegen:nullValue="" type="xs:string" minOccurs="0" />
            </xs:sequence>
          </xs:complexType>
        </xs:element>
        <xs:element name="Orders" codegen:typedName="Order" codegen:typedPlural="Orders">
          <xs:complexType>
            <xs:sequence>
              <xs:element name="OrderID" codegen:typedName="OrderID" type="xs:int" minOccurs="0" />
              <xs:element name="CustomerID" codegen:typedName="CustomerID" codegen:nullValue="" type="xs:string" minOccurs="0" />
              <xs:element name="EmployeeID" codegen:typedName="EmployeeID" codegen:nullValue="0" type="xs:int" minOccurs="0" />
              <xs:element name="OrderDate" codegen:typedName="OrderDate" codegen:nullValue="1980-01-01T00:00:00" type="xs:dateTime" minOccurs="0" />
            </xs:sequence>
          </xs:complexType>
        </xs:element>
      </xs:choice>
    </xs:complexType>
    <xs:unique name="Constraint1">
      <xs:selector xpath=".//Customers" />
      <xs:field xpath="CustomerID" />
    </xs:unique>
    <xs:keyref name="CustOrders" refer="Constraint1" codegen:typedParent="Customer" codegen:typedChildren="GetOrders">
      <xs:selector xpath=".//Orders" />
      <xs:field xpath="CustomerID" />
    </xs:keyref>
  </xs:element>
</xs:schema>

サンプル スキーマから作成された厳密に型指定された DataSet を次のコード例で使用します。また、一方の DataAdapter を使用して Customers テーブルを、他方の DataAdapter を使用して Orders テーブルを作成します。厳密に型指定された DataSet により、DataRelations が定義されます。

Dim nwindConn As SqlConnection = New SqlConnection("Data Source=localhost;Integrated Security=SSPI;" & _
                                                   "Initial Catalog=northwind")
Dim custDA As SqlDataAdapter = New SqlDataAdapter("SELECT CustomerID, CompanyName, Phone FROM Customers", &
                                                  nwindConn)
Dim orderDA As SqlDataAdapter = New SqlDataAdapter("SELECT OrderID, CustomerID, EmployeeID, OrderDate FROM Orders", &
                                                   nwindConn)

' Populate a strongly typed DataSet.
nwindConn.Open()
Dim custDS As CustomerDataSet = New CustomerDataSet()
custDA.Fill(custDS, "Customers")
orderDA.Fill(custDS, "Orders")
nwindConn.Close()

' Add a strongly typed event.
AddHandler custDS.Customers.CustomerChanged, &
           New CustomerDataSet.CustomerChangeEventHandler(AddressOf OnCustomerChanged)

' Add a strongly typed DataRow.
Dim newCust As CustomerDataSet.Customer = custDS.Customers.NewCustomer()
newCust.CustomerID = "NEW01"
newCust.CompanyName = "My New Company"
custDS.Customers.AddCustomer(newCust)

' Navigate the child relation.
Dim customer As CustomerDataSet.Customer
Dim order As CustomerDataSet.Order

For Each customer In custDS.Customers
  Console.WriteLine(customer.CustomerID)
  For Each order In customer.GetOrders()
    Console.WriteLine(vbTab & order.OrderID)
  Next
Next

Private Shared Sub OnCustomerChanged(sender As Object, e As CustomerDataSet.CustomerChangeEvent)

End Sub
[C#]
SqlConnection nwindConn = new SqlConnection("Data Source=localhost;Integrated Security=SSPI;Initial Catalog=northwind");
SqlDataAdapter custDA = new SqlDataAdapter("SELECT CustomerID, CompanyName, Phone FROM Customers", nwindConn);
SqlDataAdapter orderDA = new SqlDataAdapter("SELECT OrderID, CustomerID, EmployeeID, OrderDate FROM Orders", nwindConn);

// Populate a strongly typed DataSet.
nwindConn.Open();
CustomerDataSet custDS = new CustomerDataSet();
custDA.Fill(custDS, "Customers");
orderDA.Fill(custDS, "Orders");
nwindConn.Close();

// Add a strongly typed event.
custDS.Customers.CustomerChanged += new 
  CustomerDataSet.CustomerChangeEventHandler(OnCustomerChanged);

// Add a strongly typed DataRow.
CustomerDataSet.Customer newCust = custDS.Customers.NewCustomer();
newCust.CustomerID = "NEW01";
newCust.CompanyName = "My New Company";
custDS.Customers.AddCustomer(newCust);

// Navigate the child relation.
foreach(CustomerDataSet.Customer customer in custDS.Customers)
{
  Console.WriteLine(customer.CustomerID);
  foreach(CustomerDataSet.Order order in customer.GetOrders())
    Console.WriteLine("\t" + order.OrderID);
}

protected static void OnCustomerChanged(object sender, CustomerDataSet.CustomerChangeEvent e)
{

}

参照

型指定された DataSet の使用 | DataSet の作成および使用 | DataColumnCollection クラス | DataSet クラス