2

InterBase4.2.1で作成された古いinterbaseデータベースファイルからデータを抽出する必要があります。組み込みバージョンのFirebird(バージョン2.5.1)と.NetProvider(バージョン2.7.0)を使用しています。私はこれまでfirebirdのインターベースで作業したことはなく(ただし、SQL SERVERとSQLiteの経験はあります)、Webをクルージングして2日間実験した後、まだ解決策を見つけていません。

データベースのテーブルには、英語のデータだけでなく、ヘブライ語のデータも含まれています。私は楽観的でしたが、UTF8を使用して接続文字列を作成することから始めました。

FbConnectionStringBuilder builder = new FbConnectionStringBuilder();
builder.Database = m_DatabaseName;
builder.ServerType = FbServerType.Embedded;
builder.Charset = FbCharset.Utf8.ToString();

しかし、それは私に次の例外を与えました:

bad parameters on attach or create database
CHARACTER SET Utf8 is not defined

fbintl.dllを正しく使用しました。(以下のアプリケーションディレクトリとサブディレクトリのファイルを参照してください)。ProcessMonitorを使用して、fbintl.dllがロードされているかどうかを確認しました。

fbembed.dll
firebird.log
firebird.msg
FirebirdSql.Data.FirebirdClient.dll
ib_util.dll
icudt30.dll
icuin30.dll
icuuc30.dll
MyApplication.exe
Microsoft.VC80.CRT.manifest
msvcp80.dll
msvcr80.dll
intl\fbintl.conf
intl\fbintl.dll
udf\fbudf.dll
udf\ib_udf.dll

そこで、各文字セットを列挙FbCharsetして接続しようとすると、半分以上が同じ例外をスローし、他の文字セットと接続してヘブライ語フィールドの1つをクエリすると(を使用してIDataReader.GetString())、結果として常に同じガベージが発生しました。接続文字列でどの文字セットを指定するかは問題ではないようです。文字セットをまったく指定しなくても、結果は常に同じです。

次に、データベースで定義されている文字セットを照会し、SELECT RDB$CHARACTER_SET_NAME FROM RDB$CHARACTER_SETSそれらを列挙して、それぞれに接続しようとしました。例外をスローしたものもあれば、以前と同じ結果を出したものもありました。

データベースが作成された文字セットがわかりませんが、データベースの各フィールドの文字セットを確認したところ、すべてのテキストフィールドの文字セットが「NONE」に設定されています。

SELECT r.RDB$RELATION_NAME, r.RDB$FIELD_NAME, f.RDB$FIELD_NAME, cset.RDB$CHARACTER_SET_NAME
FROM RDB$RELATION_FIELDS r
LEFT JOIN RDB$FIELDS f ON r.RDB$FIELD_SOURCE = f.RDB$FIELD_NAME
LEFT JOIN RDB$CHARACTER_SETS cset ON f.RDB$CHARACTER_SET_ID = cset.RDB$CHARACTER_SET_ID
ORDER BY r.RDB$RELATION_NAME ASC, r.RDB$FIELD_POSITION ASC

しかし、システムテーブルのテキストフィールドの一部に文字セットとしてUNICODE_FSSが含まれていることに気付きました。接続文字列でその文字セットをすでに試しましたが、要求されたテキストフィールドに対してまだgarbadgeが表示されます。

私の最後の試みは(を使用してIDataReader.GetBytes())バイトを取得し、文字列を自分でエンコードすることでしたが、これによりキャスト例外が発生します(Unable to cast object of type 'System.String' to type 'System.Byte[]'.

このデータの読み方について誰かアイデアがありますか?データを抽出するとデータベースは使用されなくなるため、データベースを永続的に変換する必要はありません。

編集:ところで、無料の軽量のInterbase / Firebirdデータベースビューアはありますか?( SQLiteSpyと比較して)良いものを見つけることができないようです?

マーク

4

1 に答える 1

3

私は解決策を見つけました。

元のデータベースは、コードページ1255のウィンドウで書き込まれました。データを読み取ると、c#はデフォルトのエンコーディング(1255ではない)を使用してUnicode文字列を生成します。したがって、デフォルトのエンコーディングを使用して文字列をバイトにデコードしてから、正しいエンコーディングを使用してバイトを文字列に変換します。

Encoding encoding = Encoding.GetEncoding(1255);
...
if (!datareader.IsDBNull(i))
{
    string value = dataReader.GetString(i);
    if (value.Length > 0)
    {
        byte[] bytes = Encoding.Default.GetBytes(value);
        value = encoding.GetString(bytes);
    }
    // store value
 }

この解決策は私にとってはうまく機能しますが、例外を取得せずに接続文字列で文字セットとして「WIN1255」を指定できない理由がまだわかりませんbad parameters on attach or create database - CHARACTER SET WIN1255 is not defined。(文字セット「WINDOWS1255」も試しましたが、例外が発生しますInvalid character set specified)。

于 2012-02-16T15:40:55.993 に答える