DataRelation 탐색

DataRelation의 기본 기능 중 하나는 DataTable 내에서 DataSet를 하나씩 탐색할 수 있도록 하는 것입니다. 따라서 연관된 DataTableDataRow가 하나 주어지면 하나의 DataTable에서 연관된 모든 DataRow 개체를 검색할 수 있습니다. 예를 들어, 고객 테이블과 주문 테이블 사이에 DataRelation을 설정한 다음, GetChildRows를 사용하여 특정 고객 행에 대한 모든 주문 행을 검색할 수 있습니다.

다음 코드 예제에서는 DataSetCustomers 테이블과 Orders 테이블 사이에 DataRelation을 만들고 각 고객의 모든 주문을 반환합니다.

DataRelation customerOrdersRelation =
    customerOrders.Relations.Add("CustOrders",
    customerOrders.Tables["Customers"].Columns["CustomerID"],
    customerOrders.Tables["Orders"].Columns["CustomerID"]);

foreach (DataRow custRow in customerOrders.Tables["Customers"].Rows)
{
    Console.WriteLine(custRow["CustomerID"].ToString());

    foreach (DataRow orderRow in custRow.GetChildRows(customerOrdersRelation))
    {
        Console.WriteLine(orderRow["OrderID"].ToString());
    }
}
Dim customerOrdersRelation As DataRelation = _
   customerOrders.Relations.Add("CustOrders", _
   customerOrders.Tables("Customers").Columns("CustomerID"), _
   customerOrders.Tables("Orders").Columns("CustomerID"))

Dim custRow, orderRow As DataRow

For Each custRow In customerOrders.Tables("Customers").Rows
    Console.WriteLine("Customer ID:" & custRow("CustomerID").ToString())

    For Each orderRow In custRow.GetChildRows(customerOrdersRelation)
        Console.WriteLine(orderRow("OrderID").ToString())
    Next
Next

다음 예제에서는 이전 예제를 기반으로 네 개의 테이블을 모두 연관시키고 각각의 관계를 탐색합니다. 이전 예제에서와 마찬가지로, CustomerIDCustomers 테이블을 Orders 테이블에 연관시킵니다. Customers 테이블의 각 고객에 대해 Orders 테이블의 모든 자식 행이 결정되어 특정 고객의 주문 개수와 해당 OrderID 값이 반환됩니다.

확장된 예제에서는 OrderDetailsProducts 테이블의 값도 반환됩니다. Orders 테이블은 각각의 고객 주문에서 주문된 제품과 수량을 확인하기 위해 OrderID를 사용하여 OrderDetails 테이블에 연관됩니다. OrderDetails 테이블에는 주문된 제품의 ProductID만 들어 있으므로 OrderDetailsProductName을 반환하기 위해 ProductID를 사용하여 Products에 연관됩니다. 이 관계에서 Products 테이블은 부모 테이블이고 Order Details 테이블은 자식 테이블입니다. 그 결과, OrderDetails 테이블을 반복하여 검색하면 GetParentRow가 호출되어 연관된 ProductName 값이 검색됩니다.

CustomersOrders 테이블에 대해 DataRelation을 만들면 createConstraints 플래그(기본값은 true)의 값이 지정되지 않습니다. 이 경우에는 Orders 테이블의 모든 행이 Customers 부모 테이블에 존재하는 CustomerID 값을 가지고 있다고 가정합니다. Customers 테이블에 없는 CustomerIDOrders 테이블에 있으면 ForeignKeyConstraint에서 예외가 throw됩니다.

부모 열에 포함되어 있지 않은 값이 자식 열에 있는 경우 DataRelation을 추가할 때 createConstraints 플래그를 false로 설정합니다. 이 예제에서 createConstraints 플래그는 Orders 테이블과 OrderDetails 테이블 간의 DataRelation에 대해 false로 설정됩니다. 그러면 애플리케이션에서는 런타임 예외를 발생시키지 않고 OrderDetails 테이블의 모든 레코드와 Orders 테이블 레코드의 하위 세트만 반환할 수 있습니다. 확장된 예제는 다음과 같은 형식의 출력을 생성합니다.

Customer ID: NORTS  
  Order ID: 10517  
        Order Date: 4/24/1997 12:00:00 AM  
           Product: Filo Mix  
          Quantity: 6  
           Product: Raclette Courdavault  
          Quantity: 4  
           Product: Outback Lager  
          Quantity: 6  
  Order ID: 11057  
        Order Date: 4/29/1998 12:00:00 AM  
           Product: Outback Lager  
          Quantity: 3  

다음 코드 예제는 확장된 샘플로서 반환되는 Orders 테이블 레코드의 하위 세트만 포함하며, OrderDetailsProducts 테이블의 값을 반환합니다.

DataRelation customerOrdersRelation =
    customerOrders.Relations.Add("CustOrders",
    customerOrders.Tables["Customers"].Columns["CustomerID"],
    customerOrders.Tables["Orders"].Columns["CustomerID"]);

DataRelation orderDetailRelation =
    customerOrders.Relations.Add("OrderDetail",
    customerOrders.Tables["Orders"].Columns["OrderID"],
    customerOrders.Tables["OrderDetails"].Columns["OrderID"], false);

DataRelation orderProductRelation =
    customerOrders.Relations.Add("OrderProducts",
    customerOrders.Tables["Products"].Columns["ProductID"],
    customerOrders.Tables["OrderDetails"].Columns["ProductID"]);

foreach (DataRow custRow in customerOrders.Tables["Customers"].Rows)
{
    Console.WriteLine("Customer ID: " + custRow["CustomerID"]);

    foreach (DataRow orderRow in custRow.GetChildRows(customerOrdersRelation))
    {
        Console.WriteLine("  Order ID: " + orderRow["OrderID"]);
        Console.WriteLine("\tOrder Date: " + orderRow["OrderDate"]);

        foreach (DataRow detailRow in orderRow.GetChildRows(orderDetailRelation))
        {
            Console.WriteLine("\t Product: " +
                detailRow.GetParentRow(orderProductRelation)["ProductName"]);
            Console.WriteLine("\t Quantity: " + detailRow["Quantity"]);
        }
    }
}
Dim customerOrdersRelation As DataRelation = _
   customerOrders.Relations.Add("CustOrders", _
   customerOrders.Tables("Customers").Columns("CustomerID"), _
   customerOrders.Tables("Orders").Columns("CustomerID"))

Dim orderDetailRelation As DataRelation = _
   customerOrders.Relations.Add("OrderDetail", _
   customerOrders.Tables("Orders").Columns("OrderID"), _
   customerOrders.Tables("OrderDetails").Columns("OrderID"), False)

Dim orderProductRelation As DataRelation = _
   customerOrders.Relations.Add("OrderProducts", _
   customerOrders.Tables("Products").Columns("ProductID"), _
   customerOrders.Tables("OrderDetails").Columns("ProductID"))

Dim custRow, orderRow, detailRow As DataRow

For Each custRow In customerOrders.Tables("Customers").Rows
    Console.WriteLine("Customer ID:" & custRow("CustomerID").ToString())

    For Each orderRow In custRow.GetChildRows(customerOrdersRelation)
        Console.WriteLine("  Order ID: " & orderRow("OrderID").ToString())
        Console.WriteLine(vbTab & "Order Date: " & _
          orderRow("OrderDate").ToString())

        For Each detailRow In orderRow.GetChildRows(orderDetailRelation)
            Console.WriteLine(vbTab & "   Product: " & _
              detailRow.GetParentRow(orderProductRelation) _
              ("ProductName").ToString())
            Console.WriteLine(vbTab & "  Quantity: " & _
              detailRow("Quantity").ToString())
        Next
    Next
Next

참고 항목