3

SQLステートメント(文字列)を受け取り、結果を組織のコレクションであるArrayList(organisationList)にロードする次のコードがあります。

public void FillDataGridView(DataGridView grid, string SQLCommand)
{
    SqlCommand dataCommand = new SqlCommand();
    dataCommand.Connection = dataConnection;
    dataCommand.CommandType = CommandType.Text;
    dataCommand.CommandText = SQLCommand;

    SqlDataReader dataReader = dataCommand.ExecuteReader();

    while (dataReader.Read())
    {
        Organisation org = new Organisation();

        org.OrganisationId = (int)dataReader["OrganisationId"];
        org.OrganisationName = (string)dataReader["OrganisationName"];

        organisationList.Add(org);
    }

    grid.DataSource = organisationList;
    dataReader.Close();
}

渡されたArrayListを埋められるように、このメソッドを適応させたいと思います。

リストをメソッドに渡して、次のようなものにすることは可能ですか?

public void FillArrayList(DataGridView grid, SqlDataReader reader, ArrayList list)
{
    //Fill the list with the contents of the reader
    while (reader.Read())
    {
        Object  obj = new Object

        for(int i; i = 0; i < obj.NoOfProperties)
        {
            obj.Property[i] = reader[i];
        }

        list.Add(obj);
    }
}

これが少し曖昧な場合は申し訳ありませんが、私はOOPにまったく慣れておらず、少し迷っています。

編集:Darren Daviesのアドバイスに基づいて、メソッドを次のように変更しました。

public void FillArrayList<T>(DataGridView grid, SqlDataReader reader, List<T> list)
{
    //Fill the list with the contents of the reader
    while (reader.Read())
    {
        Object obj = new Object();
        Type type = typeof(T);

        FieldInfo[] fields = type.GetFields(); // Get the fields of the assembly
        int i = 0;

        foreach(var field in fields)
        {
            field.SetValue(obj, reader[i]); // set the fields of T to the reader's value
            // field.setValue(obj, reader[field.Name]); // You can also set the field value to the explicit reader name, i.e. reader["YourProperty"]
            i++;
        }

        list.Add((T)obj);
    }

    grid.DataSource = list;
}

コードを実行すると、オブジェクトをタイプTにキャストするときにエラーが発生します。

タイプ「System.Object」のオブジェクトをタイプ「TestHarness.Organisation」にキャストできません。

オブジェクトは何でも保存できるという印象を受けました。このキャストが実行できない理由について誰かにアドバイスしてもらえますか?

ありがとう、

アンディ

4

4 に答える 4

6

ArrayList.NET 1.1を使用しているのでない限り、おそらく;を使用すべきではありません。ジェネリックList<T>が望ましいです。

メンバーを追加することはできませんobject-拡張できません。作成するオブジェクトのタイプを知る必要があります。ジェネリックは妥当なオブジェクトです。ただし、時間を節約するために、 dapperを確認することをお勧めします。

var list = dataConnection.Query<YourType>(SQLCommand).ToList();

これは、列名からメンバー名への直接マッピングを使用して、すべてを実行します。YourType期待するプロパティ(適切に入力された)を使用してクラスを作成する必要があります。

4.0を使用している場合、dapperは以下もサポートしますdynamic

var list = dataConnection.Query(SQLCommand).ToList();

これはを使用するdynamicので、(タイプを宣言せずに)引き続き実行できます。

foreach(var obj in list) {
    Console.WriteLine(obj.OrganisationId);
    Console.WriteLine(obj.OrganisationName);
}

個人的にはdynamic、データがアクセスされる場所の非常に近くで使用される場合にのみ、このアプローチを使用します。メソッドから戻るには、一般的なアプローチが推奨されます。同様に、dynamicではうまく機能しませんDataGridView

最後に、パラメーターがないことに気付きました。連結ではなく、常にパラメーターを使用する必要があります。Dapperもそれをサポートしています:

string foo = ...;
var list = dataConnection.Query<YourType>(
    "select * from SomeTable where Foo = @foo", new { foo }).ToList();
于 2012-05-19T11:40:09.063 に答える
2

C#2.0を使用している場合。またはGenericsではなく、より多くの使用ArrayList

Reflection渡すタイプのプロパティを取得するために使用できます。

public void FillArrayList<T>(DataGridView grid, SqlDataReader reader, List<T> list)
{
    //Fill the list with the contents of the reader
    while (reader.Read())
    {
       Object  obj = new Object();
       Type type = typeof(T); // get the type of T (The paramter you passed in, i.e. Organisations)

       FieldInfo[] fields = type.GetFields(); // Get the fields of the assembly
       int i = 0;

        foreach(var field in fields) // Loop round the fields 
        {
            field.setValue(obj, reader[i]); // set the fields of T to the readers value
            // field.setValue(obj, reader[field.Name]); // You can also set the field value to the explicit reader name, i.e. reader["YourProperty"] 
            i++;
        }

        list.Add(obj);
    }
}

それを呼び出すには:

 FillArrayList(grid, reader, list);

ここで、listは組織のリストタイプです。

 List<Organisations> list = new List<Organisations>();

http://msdn.microsoft.com/en-us/library/ms379564(v=vs.80).aspx

于 2012-05-19T11:47:40.530 に答える
1

返されたデータセットの列と同じ名前でクラスのプロパティを作成する場合、リフレクションを使用して、データリーダーまたはデータテーブルから任意のタイプのオブジェクトを構築できます(データリーダーまたはデータテーブルの列とオブジェクトのプロパティが一致)。

あなたはこのリンクをたどることを見ることができます。データテーブルをカスタムクラスのコレクションに変換する方法を示します。データリーダーの操作も同じです。

于 2012-05-19T11:29:48.033 に答える
0

DataContextを使用して接続文字列を指定してから、Linqを使用することもできませんか?

http://msdn.microsoft.com/en-us/library/bb399375.aspx

于 2012-05-19T12:07:54.477 に答える