ホームに戻る
出典 :
関連 :
目次 :
DataTable とは
表形式のデータを格納できる型。System.Data 名前空間に属する。
データベースから取得したテーブルを格納することを前提としており、集計用の各種メソッドを備えている。
また、DataGridView(WindowsForms)やDataGrid(WPF)とデータバインディングで連携することが可能である。
DataTable と関連クラスの構成

DataTable は DataRelation によって一方を親、他方を子として関連付けることができる。これはデータベースにおける主キーと外部キーの関係に等しい(詳細は割愛)。
DataTable と、DataTable を関連付ける DataRelation は DataSet でまとめて管理することが可能である。DataSet はひとつのデータベースに相当する。
DataTable の任意の列または行を抽出することができ、それぞれ DataColumn 、DataRow 型として取り扱われる。
DataTable のビューとして DataView を作成することもできる。DataView はソートやフィルタリングにより、元データである DataTable の異なる見方(サブセット)を提供できる。
(詳細はリファレンスを参照のこと。)
いずれの型も DataTable 同様、System.Data 名前空間に属する。
まとめると、
- DataTable はデータベースにおけるひとつのテーブル(またはビュー)に相当する
- DataSet はひとつのデータベースに相当し、複数の DataTable と、DataTable 同士の関係である DataRelation を保持できる
- DataTable の列は DataColumn 、行は DataRow である
となる。
DataTable の実装例
テーブルの作成
C#
using System;
using System.Data;
class Program
{
static void Main(string[] args)
{
// DataSet の生成
DataSet dataSet = new DataSet();
// DataTable (テーブル名 : 「成績」)の生成
DataTable table = new DataTable("成績");
// DataTable に列を追加
table.Columns.Add( "教科" );
table.Columns.Add( "点数", Type.GetType("System.Int32") );
table.Columns.Add( "氏名" );
table.Columns.Add( "クラス名" );
// DataTable に行(データ)を追加
// 教科 点数 氏名 クラス名
table.Rows.Add( "数学", 80, "田中 一郎", "A" );
table.Rows.Add( "英語", 70, "田中 一郎", "A" );
table.Rows.Add( "国語", 60, "鈴木 二郎", "A" );
table.Rows.Add( "数学", 50, "鈴木 二郎", "A" );
table.Rows.Add( "英語", 80, "鈴木 二郎", "A" );
table.Rows.Add( "国語", 70, "佐藤 三郎", "B" );
table.Rows.Add( "数学", 80, "佐藤 三郎", "B" );
table.Rows.Add( "英語", 90, "佐藤 三郎", "B" );
// DataSet に DataTable を追加
dataSet.Tables.Add(table);
}
}
上記は DataTable の基本的な実装例である。
作成した DataTable に DataTable.Columns.Add() メソッドで列(属性)を追加している。第1引数は列の名前、第2引数は列に格納する型である。
型を省略した場合は、既定値である string が列の型となる。
同様に DataTable.Rows.Add() で行(データ)を追加している。引数で指定した値が、列の追加順に各列に割り当てられる。
データの抽出と並び替え
C#
:
// DataTable.Select() でデータを抽出
// 「教科」==「国語」、「点数」で降順に並び替え
DataRow[] dRows = table.Select("教科 = '国語'", "点数 DESC");
foreach (var row in dRows)
{
Console.WriteLine( $"点数 : {row[1]}点、氏名 : {row[2]}、クラス : {row[3]}" );
}
実行結果
点数 : 90点、氏名 : 田中 一郎、クラス : A
点数 : 70点、氏名 : 佐藤 三郎、クラス : B
点数 : 60点、氏名 : 鈴木 二郎、クラス : A
DataTable.Select() メソッドで、条件に合致するデータを抽出できる。これはSQLのSELECT文に相当する。
Select() の戻り値は DataRow のコレクションとなる。
[列名]='[値]'
形式で記述する(値を単一引用符で囲む)。
[列名] ASC / DESC
と記述すると、指定した列の値を用いて昇順(ASC)または降順(DESC)で並び替える。
(上記の場合は "点数 DESC" のため、「点数」が降順となるよう並び替える。)
また、データの抽出には Select() のほかにLINQも使用できる。詳細は出典元を参照。
データの集計
C#
:
// DataTable.Compute() でデータを集計
// 「教科」==「国語」の「点数」のうち最大の値
object obj = table.Compute("Max(点数)", "教科 = '国語'");
Console.WriteLine( $"国語の最高点 : {(int)obj}点" );
実行結果
国語の最高点 : 90点
DataTable.Compute() メソッドで、データの最大(Max)、最小(Min)、合計(Sum)、平均(Ave)を算出することができる。
これはSQLのSELECT文で集約関数を用いた場合に相当する。
戻り値は object 型であるため、キャストにより所望の形式に変換している。
(WPF)DataGrid での表示
ViewModel : C#
private DataTable _data;
public DataView Data { get; private set; } //< DataGrid のデータソースとして用いる DataView
:
_data = new DataTable();
_data.Columns.Add("Name");
_data.Columns.Add("Price", typeof(int)); //< ソートを数値順にする
_data.Rows.Add("商品A", 500);
_data.Rows.Add("商品B", 1200);
_data.Rows.Add("商品C", DBNull.Value); //< 金額無し(null)
_data.Rows.Add("商品D", 2000);
// DataTable を基に DataView を作成
Data = new DataView(_data);
View : XAML
<
DataGrid ItemsSource=
"{Binding Data}" AutoGenerateColumns=
"False" >
<
DataGrid.Columns >
<
DataGridTextColumn Header=
"商品名" Binding=
"{Binding Name}" / >
<
DataGridTextColumn Header=
"金額" Binding=
"{Binding Price}, TargetNullValue='値がありません'" / >
</
DataGrid.Columns >
</
DataGrid >
画面表示

DataGrid の ItemsSource に DataTable または DataView を指定することで、データを表形式で表示、編集ことができる。
DataGrid.AutoGenerateColumns の既定値は True で、データソースに基づいて列を自動生成するが、
False に設定することで列の順序やヘッダを自由に設定できる。
列ヘッダをクリックすることで、その列の値を基に昇順・降順に並び替えができるが、
列の属性が string (既定値)だと辞書順のソートとなるので、"Price" 列は数値の大小でソートするため型を明示的に int に指定している。
また、DataGridTextColumn.TargetNullValue に任意の文字列を設定すること、値が無い場合に表示される。
詳細は出典元を参照。