6

sqliteテーブルに\0文字とテキストフィールドを持つUTF文字列があります。
文字列をテーブルのテキストフィールドに挿入してデータベースから読み取ろうとすると、文字列の値が\0文字の後に切り捨てられていることに気付きました。

質問:\ 0以降のデータを失うことなく、そのような文字列をsqliteに保存/復元することは可能ですか?

コードスニペット:

 public static void IssueWith0Character()
    {
        const string sql = "DROP TABLE IF EXISTS SomeTable;" +
                           "CREATE TABLE SomeTable (SomeField TEXT not null);"
                           + "INSERT INTO SomeTable (SomeField) Values ( :value )";

        var csb = new SQLiteConnectionStringBuilder
                      {DataSource = "stringWithNull.db", Version = 3};

        // string with '0' character
        const string stringWithNull = "beforeNull\0afterNull";

        using (var c = new SQLiteConnection(csb.ConnectionString))
        {
            c.Open();

            using (var cmd = c.CreateCommand())
            {
                var p = new SQLiteParameter(":value", DbType.String) {Value = stringWithNull};
                cmd.CommandText = sql;
                cmd.Parameters.Add(p);
                cmd.ExecuteNonQuery();
            }

            using (var cmd = c.CreateCommand())
            {
                cmd.CommandText = "SELECT SomeField FROM SomeTable;";
                var restoredValue = (string) cmd.ExecuteScalar();
                Debug.Assert(stringWithNull == restoredValue);
            }
        }
    }    

UPDATE#1問題は読書段階にあるようです。文字列の少なくとも「afterNull」部分がデータベースファイルに存在します。

UPDATE#2これはSystem.Data.SQLiteのバグ(<1.04.84)と見なされていました。http://system.data.sqlite.org/index.html/tktview/3567020edf12d438cb7cf757b774ff3a04dc381e

4

1 に答える 1

-2

SQLite では、\0 文字は無効と見なされます。

このような文字列をデータベースに入れることは可能ですが (さまざまな関数のポインタ + 長さ形式を使用)、文字列を操作する多くの関数は \0 に遭遇すると停止します。したがって、ドキュメントには次のように記載されています。

NUL が埋め込まれた文字列を含む式の結果は未定義です。

本当に null バイトのデータを保存する必要がある場合は、blob ( DbType.Binary) として保存する必要があります。

于 2013-03-05T18:04:56.003 に答える