我已经阅读了下面的线程,我能够制作一个转换脚本(基于C#(,将我所有的charset=NONE
数据库转换为charset=UTF8
,其中大部分都很好(我仍然有一些特殊情况,字符被转换为奇怪的符号,但这是边缘的(。
我的问题是,我有很多备份数据库文件(*.fbk
(,我不确定这是UTF8
还是NONE
。在理想的情况下,一旦数据库根据fbk
文件的格式从文件中恢复,我的代码就会处理转换,所以我只在必要时和恢复后进行转换。
这有可能吗?或者,在恢复数据库时是否有定义charset
的方法(通过gback
或通过ADO.NET提供程序(?
通常,Firebird数据库没有单个字符集。每一列都可以有自己的字符集。所以你唯一能做的就是尝试使用启发式方法。
-
使用数据库默认字符集。需要明确的是,只有在未指定显式字符集的情况下创建新列时才使用数据库默认字符集。数据库完全有可能具有默认的字符集UTF8,而所有列都具有字符集WIN1251!
您可以通过以下查询找到数据库默认字符集:
select RDB$CHARACTER_SET_NAME from RDB$DATABASE
注意:如果结果为
NULL
,则表示默认字符集为NONE。 -
对CHAR、VARCHAR和BLOB SUB_TYPE TEXT列的不同字符集进行计数,以查看出现最多的字符集:
select coalesce(cs.RDB$CHARACTER_SET_NAME, 'NONE') as CHARSET, count(*) as CHARSET_COUNT from RDB$RELATIONS r inner join RDB$RELATION_FIELDS rf on rf.RDB$RELATION_NAME = r.RDB$RELATION_NAME inner join RDB$FIELDS f on f.RDB$FIELD_NAME = rf.RDB$FIELD_SOURCE left join RDB$CHARACTER_SETS cs on cs.RDB$CHARACTER_SET_ID = f.RDB$CHARACTER_SET_ID where coalesce(r.RDB$SYSTEM_FLAG, 0) = 0 and r.RDB$VIEW_BLR is null and (f.RDB$FIELD_TYPE in (14, 37) or f.RDB$FIELD_TYPE = 261 and f.RDB$FIELD_SUB_TYPE = 1) group by 1 order by 2 desc
顺便说一句,请注意,如果客户端使用了连接字符集NONE,那么列内容的实际字符集可能与该列定义的字符集不匹配。