我已将阿拉伯数据存储在具有拉丁校对的字段中的MS SQL数据库中。我可以使用旧的SqlDrv32.dll驱动程序和odbc读取它。有没有办法将这些数据转换成具有正确数据的阿拉伯语排序规则?
答案 0 :(得分:3)
您需要做的是确保使用nvarchar
而不是varchar
存储您的列。不同的是
假设您要存储文本:“مرحبا”
如果您(正确地)将其存储到nvarchar
列中,该表将包含“مرحبا”。
但我认为您无法将数据库更改为正确的列类型,您仍然无法使用varchar
,而您只需要使用{ Latin-1排序规则中的{1}}列。
在这种情况下,您需要使用您的编程语言直接将“مرحبا”的字节解释为Latin-1:
varchar
所以为了保存:
| Character | Windows 1256 Hex Code | Windows-1252 |
|-----------|-----------------------|--------------|
| م | E3 | ã |
| ر | D1 | Ñ |
| ح | CD | Í |
| ب | C8 | È |
| ا | C7 | Ç |
مرحبا
当您将其保存到数据库时,它将作为ãÑÍÈÇ
存储在varchar
Latin-1列中。
现在你还需要加载它。这意味着您必须使用字符串:
ãÑÍÈÇ
当您假设它是Windows-1252编码时,它是如何显示的,并且假设它是Windows-1256编码的。
我不知道您使用的编程语言,但我们可以假设一种现代语言,它能够将文本转换为编码的字节序列。
最终你的目标是写下:
ãÑÍÈÇ
首先,您必须将dbConnection.ExecuteNonQuery("INSERT INTO Users (Name) VALUES (`مرحبا`)");
从“مرحبا”转换为Windows-1256编码版本:
string
现在您可以编写SQL语句:
String name = "مرحبا";
//Convert the string into a Windows-1256 encoded byte sequence
Encoding arabic = Encoding.GetEncoding(1256);
byte[] nameAsBytes = arabic.GetBytes(name); //e.g. E3 D1 CD C8 C7
//Convert the byte sequence back to a string, but assume it is Windows-1252
Encoding latin1 = Encoding.GetEncoding(1252);
String latinName = latin1.GetString(nameAsBytes); //e.g. "ãÑÍÈÇ"
现在,当您从数据库中读回值时,它将作为dbConnection.ExecuteNonQuery("INSERT INTO Users (Name) VALUES ('ãÑÍÈÇ')");
来到您的身边:
string
然后,您必须将该文本(Windows-1252)解释为Windows-1256:
SELECT Name FROM Users
Name
----------
ãÑÍÈÇ
1 row(s) affected
神奇的是假设您的文本是Windows-1252编码。我们可以转换辅助函数来强制文本进出Latin1:
String latinName = reader.GetString("Name"); //"ãÑÍÈÇ"
Encoding latin1 = Encoding.GetEncoding(1252);
byte[] nameAsBytes = latin1.GetBytes(latinName);
Encoding arabic = Encoding.GetEncoding(1256);
String name = arabic.GetString(nameAsBytes);
//name is now مرحب
所以它就像:
String ToLatin1(String s)
{
//"مرحب" ==> "ãÑÍÈÇ"
//(1256) ==> (1252)
Encoding from = Encoding.GetEncoding(1256);
byte[] hex = from.GetBytes(s);
Encoding to = Encoding.GetEncoding(1252);
String result = to.GetString(hex);
return result;
}
String FromLatin1(String s)
{
//"ãÑÍÈÇ" ==> "مرحب"
//1252 ==> 1256
Encoding from = Encoding.GetEncoding(1252);
byte[] hex = from.GetBytes(s);
Encoding to = Encoding.GetEncoding(1256);
String result = to.GetString(hex);
return result;
}
和
dbConnection.ExecuteNonQuery("INSERT INTO Users(Name) VALUES (@name)",
ToLatin1("مرحب")
);