4

タイプ DataTable のオブジェクトを SQL 2005 データベースのタイプ varbinary のフィールドに保存しました。元に戻したいのですが、型キャストできませんでした。これが私がそれを保存した方法です。

MemoryStream memStream = new MemoryStream();
    StreamWriter sw = new StreamWriter(memStream);

sw.Write(dt);
con.Open();
using (SqlCommand cmd = new SqlCommand("INSERT INTO Tables(TableName, TableData, QuestionID) VALUES (@TableName, @TableData, @QuestionID)", con))
{
    cmd.Parameters.Add("@TableName", SqlDbType.VarChar).Value = "a new table";
    cmd.Parameters.Add("@TableData", SqlDbType.VarBinary,Int32.MaxValue).Value = memStream.GetBuffer();
    cmd.Parameters.Add("@QuestionID", SqlDbType.VarChar).Value = "2";
    cmd.ExecuteNonQuery();

}

「dt」は DataTable オブジェクト インスタンスです。

4

4 に答える 4

7

あなたが話しているのは、バイナリシリアライゼーションとデシリアライゼーションです。多分これが役立つでしょう。

using System;
using System.IO;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Formatters.Binary;
using System.Data;
using System.Text;

namespace Serial
{
    public class Ser
    {
        public static byte[] StrToByteArray(string str)
        {
            UTF8Encoding  encoding = new UTF8Encoding ();
            return encoding.GetBytes(str);
        }

        public static string ByteArrayToStr(byte[] barr)
        {
            UTF8Encoding  encoding = new UTF8Encoding ();
            return encoding.GetString(barr, 0, barr.Length);
        }

        public static void Main(String[] args)
        {
            DataTable dt = new DataTable();
            DataRow dr;

            dt.Columns.Add(new DataColumn("IntegerValue", typeof(Int32)));
            dt.Columns.Add(new DataColumn("StringValue", typeof(string)));
            dt.Columns.Add(new DataColumn("DateTimeValue", typeof(DateTime)));
            dt.Columns.Add(new DataColumn("BooleanValue", typeof(bool)));

            for (int i = 1; i <= 1; i++) 
            {

                dr = dt.NewRow();

                dr[0] = i;
                dr[1] = "Item " + i.ToString();
                dr[2] = DateTime.Now;
                dr[3] = (i % 2 != 0) ? true : false;

                dt.Rows.Add(dr);
            }

            //Serialize
            BinaryFormatter bformatter = new BinaryFormatter();
            MemoryStream  stream = new MemoryStream();

            string s;
            bformatter.Serialize(stream, dt);
            byte[] b = stream.ToArray();
            s = ByteArrayToStr(b);
            stream.Close();
            dt = null;

            //Now deserialise
            bformatter = new BinaryFormatter();
            byte[] d;
            d = StrToByteArray(s);
            stream = new MemoryStream(d);
            dt = (DataTable)bformatter.Deserialize(stream);
            stream.Close();
        }
    }
}
于 2009-08-19T13:58:42.620 に答える
1

残念ながら、少なくともデータ テーブルを処理する StreamWriter クラスの拡張メソッドを作成したという報告があるまでは、期待を裏切らなければなりません。

WriteDataTable インスタンスを受け入れるメソッドの唯一のオーバーロードは、オブジェクトを受け取るものであり、 MSDN のドキュメントに従って、オブジェクトの "テキスト表現" のみを保存します。

したがって、DataTable の .ToString メソッドが、DataTable インスタンスのすべてのコンテンツを含む形式で文字列を出力することを期待しましょう。.ToString メソッドは、TableName プロパティの内容と表示式 (存在する場合) のみを返します。

したがって、保存したのは、DataTable インスタンスのすべての内容ではなく、テーブルの名前だけです。

Serializationを調べる必要があります。DataTable オブジェクトのすべてのコンテンツのバイナリ表現または XML 表現を生成できるはずです。

于 2009-08-19T13:57:43.090 に答える
0

あなたのコードはデータテーブルをシリアル化したばかりで、逆シリアル化する必要があると思います。どのフォーマッターが使用されたかわからないため、バイナリ フィールドの内容を確認する必要があります。バイナリの場合は、BinaryFormaterを使用します(ページの下のサンプル コードを参照してください)。バイナリでない場合は、SoapFormatterXmlSerializerを試してください。

于 2009-08-19T14:00:11.760 に答える
0

XmlSerializer または BinaryFormatter を使用して DataTable をシリアル化し、バイナリ列に格納することをお勧めします。

それを行うためのリンク:
http://sadeveloper.net/forums/p/439/1772.aspx
http://bytes.com/topic/net/answers/428472-serializing-datatable

于 2009-08-19T14:01:28.920 に答える