Знаки вопроса при получении текстовых данных из MS Access
Модератор: Модераторы
Знаки вопроса при получении текстовых данных из MS Access
Доброго времени суток.
Есть следующая проблема с кодировками. При получении данных из текстового поля MS Access символы из диапазонов Unicode "Расширенная латиница - A", "Расширенная латиница - B", "Фонетические значки", "Греческий основной" транслируются в виде знаков вопроса. UTF8Encode не помог.
SQLQuery1.SQL.Clear;
SQLQuery1.SQL.Add('SELECT * FROM Table1 WHERE Nomer=:param1 ;');
SQLQuery1.Params.ParamByName('param1').AsInteger:=1;
SQLQuery1.Open;
Label1.Caption:=SQLQuery1.FieldByName('Field1').AsString;
SQLQuery1.Close;
Подобная тема обсуждалась на форуме по поводу кириллицы. С русскими буквами у меня вопрос решился применением AnsiToUTF8, а вот с символами юникода из указанных выше диапазонов функции преобразования не помогают.
Что-нибудь подскажете по решению данной проблемы?
Lazarus 1.0.2, FPC 2.6.0, WinXPSP3, MS Access 2000
Есть следующая проблема с кодировками. При получении данных из текстового поля MS Access символы из диапазонов Unicode "Расширенная латиница - A", "Расширенная латиница - B", "Фонетические значки", "Греческий основной" транслируются в виде знаков вопроса. UTF8Encode не помог.
SQLQuery1.SQL.Clear;
SQLQuery1.SQL.Add('SELECT * FROM Table1 WHERE Nomer=:param1 ;');
SQLQuery1.Params.ParamByName('param1').AsInteger:=1;
SQLQuery1.Open;
Label1.Caption:=SQLQuery1.FieldByName('Field1').AsString;
SQLQuery1.Close;
Подобная тема обсуждалась на форуме по поводу кириллицы. С русскими буквами у меня вопрос решился применением AnsiToUTF8, а вот с символами юникода из указанных выше диапазонов функции преобразования не помогают.
Что-нибудь подскажете по решению данной проблемы?
Lazarus 1.0.2, FPC 2.6.0, WinXPSP3, MS Access 2000
Вообще в целом я бы проблему охарактеризовал как "Месье, вы любитель извращений"? (С)
MS Access, да еще и версия давным давно вышедшая из поддержки... Нда...
Но, приближаясь ближе к теме: не ждите, что кто-то ответит корректно. Сделайте сами.
Для начала, присвойте строковой переменной то, что вы получили через SQLQuery1.FieldByName('Field1').AsString да, с тес текстом, какой проблемен.
Сделайте шестнадцатиричный дамп этой строки (если не знаете как - возьмите функцию PrintByte отсюда: http://sirserge.altai.info/articles/?id=45 )
Вычислите, что именно и в какой кодировке пришло, а потом уже применяйте соответствующие функции. Если будет к чему применять. У меня есть большие подозрения, что Access 2000 работает на внешние запросы в кодовой странице системы, а следовательно, никаких греческих знаков передать внешней программе не в состоянии.
Ну и если действительно передается не уникод, проверьте строку соединения с базой. Для MySQL, например, это весьма существенно - не задали кодировку трансфера, не получили нужного.
MS Access, да еще и версия давным давно вышедшая из поддержки... Нда...
Но, приближаясь ближе к теме: не ждите, что кто-то ответит корректно. Сделайте сами.
Для начала, присвойте строковой переменной то, что вы получили через SQLQuery1.FieldByName('Field1').AsString да, с тес текстом, какой проблемен.
Сделайте шестнадцатиричный дамп этой строки (если не знаете как - возьмите функцию PrintByte отсюда: http://sirserge.altai.info/articles/?id=45 )
Вычислите, что именно и в какой кодировке пришло, а потом уже применяйте соответствующие функции. Если будет к чему применять. У меня есть большие подозрения, что Access 2000 работает на внешние запросы в кодовой странице системы, а следовательно, никаких греческих знаков передать внешней программе не в состоянии.
Ну и если действительно передается не уникод, проверьте строку соединения с базой. Для MySQL, например, это весьма существенно - не задали кодировку трансфера, не получили нужного.
Sserge, cделал так:
В поле MS Access находится строка из шести различных букв греческого алфавита, идущих подряд. Вывелось: 630630630630630630000013240173186 (насколько я понял, к моей строке имеет отношение только 630630630630630630)
63 – это десятичный аналог шестнадцатиричного числа 3F, которое соответствует знаку вопроса в таблице Юникода.
Если в поле MS Access находятся шесть букв кириллицы абвгде, выводится: 484494504514524534000013240173186
Как получаются числа 48, 49, 50, 51, 52, 53 и четвёрка между ними, не сообразил.
Добавлено спустя 21 минуту 52 секунды:
Re: Знаки вопроса при получении текстовых данных из MS Access
Если немного изменить код
то:
для строки "абвгде" в цикле выводится 1072, 1073, 1074, 1075, 1076, 1077, что соответствует шестнадцатиричным кодам букв а,б,в,г,д,е в Юникоде;
для строки из шести греческих букв выводится 63,63,63,63,63,63.
Код: Выделить всё
type Type1 = Array[1..20] of byte;
var
S1: String;
Pointer1: Pointer;
SQLQuery1.SQL.Clear;
SQLQuery1.SQL.Add('SELECT * FROM Table1 WHERE Nomer=1 ;');
SQLQuery1.Open;
Pointer1:=Pointer( WideString(SQLQuery1.FieldByName('Field1').Value) );
S1:='';
for i:=1 to 20 do
begin
S1:=S1+IntToStr(Type1(Pointer1^)[i]);
end;
Label1.Caption:=S1;
SQLQuery1.Close;В поле MS Access находится строка из шести различных букв греческого алфавита, идущих подряд. Вывелось: 630630630630630630000013240173186 (насколько я понял, к моей строке имеет отношение только 630630630630630630)
63 – это десятичный аналог шестнадцатиричного числа 3F, которое соответствует знаку вопроса в таблице Юникода.
Если в поле MS Access находятся шесть букв кириллицы абвгде, выводится: 484494504514524534000013240173186
Как получаются числа 48, 49, 50, 51, 52, 53 и четвёрка между ними, не сообразил.
Добавлено спустя 21 минуту 52 секунды:
Re: Знаки вопроса при получении текстовых данных из MS Access
Если немного изменить код
Код: Выделить всё
type Type1 = Array[1..20] of WideChar;
var
V1: Variant;
Pointer1: Pointer;
SQLQuery1.SQL.Clear;
SQLQuery1.SQL.Add('SELECT * FROM Table1 WHERE Nomer=1 ;');
SQLQuery1.Open;
Pointer1:=Pointer( WideString(SQLQuery1.FieldByName('Field1').Value) );
for i:=1 to 20 do
begin
V1:=Type1(Pointer1^)[i];
ShowMessage(V1);
end;
SQLQuery1.Close;то:
для строки "абвгде" в цикле выводится 1072, 1073, 1074, 1075, 1076, 1077, что соответствует шестнадцатиричным кодам букв а,б,в,г,д,е в Юникоде;
для строки из шести греческих букв выводится 63,63,63,63,63,63.
dimmm писал(а):Pointer( WideString(SQLQuery1.FieldBy
Так нельзя. Вы что-то, являющееся результатом функции FieldBy, принудительно приводите к WideString.
Результат к тому же печатаете какой-то десятичной кашей, даже значения не разделяя.
В шестнадцатиричном виде выведите чтоли, я ж гтовый код дал.
и БЕЗ преобразований!
Код: Выделить всё
Var s:string;
s:=SQLQuery1.FieldByName('Field1').AsString;
....
Label1.Caption:=PrintByte(@s[1],6);
С функцией PrintByte:
Для строки из шести греческих букв выводится: 3F 3F 3F 3F 3F 3F .
Для строки абвгде выводится: E0 E1 E2 E3 E4 E5 .
Добавлено спустя 5 минут 12 секунд:
Re: Знаки вопроса при получении текстовых данных из MS Access
По поводу строки соединения с базой, в dsn-файле ничего имеющего отношения к кодировкам не указывается.
В TODBCConnection есть ещё свойство CharSet, в которое я пробовал вводить разные значение "UNICODE", "UCS2", "UCS-2" и которое, по-моему, ни на что не влияет, я туда вводил даже "блаблабла" и ошибки не было.
Код: Выделить всё
type AAB=array [0..65535] of byte;
PAAB=^AAB;
var S1:String;
SQLQuery1.SQL.Clear;
SQLQuery1.SQL.Add('SELECT * FROM Table1 WHERE Nomer=1 ;');
SQLQuery1.Open;
S1:=SQLQuery1.FieldByName('Field1').AsString;
Label1.Caption:=PrintByte(@S1[1],6));
SQLQuery1.Close;
function PrintByte(p:PAAB; len:integer):string;
var i:integer;
begin
Result:='';
for i:=0 to len-1 do
begin
Result:=Result+Format('%2.2x ',[p^[i]]);
end;
Result:=Trim(Result);
end;
Для строки из шести греческих букв выводится: 3F 3F 3F 3F 3F 3F .
Для строки абвгде выводится: E0 E1 E2 E3 E4 E5 .
Добавлено спустя 5 минут 12 секунд:
Re: Знаки вопроса при получении текстовых данных из MS Access
По поводу строки соединения с базой, в dsn-файле ничего имеющего отношения к кодировкам не указывается.
В TODBCConnection есть ещё свойство CharSet, в которое я пробовал вводить разные значение "UNICODE", "UCS2", "UCS-2" и которое, по-моему, ни на что не влияет, я туда вводил даже "блаблабла" и ошибки не было.
- Little_Roo
- энтузиаст
- Сообщения: 639
- Зарегистрирован: 27.02.2009 18:56:36
- Откуда: Санкт-Петербург
Может ZEOS поможет?
Там с кодировками нормально...
Там с кодировками нормально...
dimmm писал(а):Для строки абвгде выводится: E0 E1 E2 E3 E4 E5
Это однобайтовая Windows-1251/cp1251 http://ru.wikipedia.org/wiki/Cp1251, греческих символов в ней нет, поэтому 3F -- обычные знаки вопроса.
Нужно искать способ подключения в Юникоде, иначе получить одновременно символы за пределами одной кодовой таблицы не получится.
Little_Roo,
установил компоненты Zeos. ZConnection коннектиться с БД MS Access не хочет - выдаёт ошибку "Requested Database driver was not found". На сайте разработчиков Zeos нашёл на форуме вот такую тему http://zeos.firmos.at/viewtopic.php?t=2702, там говорится (если я конечно всё правильно понял), что такая ошибка при подключении к базе MS Access в среде Lazarus совершенно нормальное явление и что на данном этапе связать программу написанную в Lazarus с базой данных MS Access в принципе невозможно, потому что в Lazarus нет возможности работать через ADO. В документации к Zeos сказано, что для баз данных с которыми Zeos не умеет работать напрямую (а именно такой базой данных является MS Access) рекомендуется использовать ADO-мост.
Установил Zeos в Delphi 7. При попытке подключиться к той же базе данных вылезла точно такая же ошибка. Хотя может быть я что-то не так настроил, например в ZConnection есть свойство LibraryLocation, может быть там надо указать адрес каких-то dll.
Добавлено спустя 4 минуты 1 секунду:
Re: Знаки вопроса при получении текстовых данных из MS Access
Ищу. Пока безуспешно.
установил компоненты Zeos. ZConnection коннектиться с БД MS Access не хочет - выдаёт ошибку "Requested Database driver was not found". На сайте разработчиков Zeos нашёл на форуме вот такую тему http://zeos.firmos.at/viewtopic.php?t=2702, там говорится (если я конечно всё правильно понял), что такая ошибка при подключении к базе MS Access в среде Lazarus совершенно нормальное явление и что на данном этапе связать программу написанную в Lazarus с базой данных MS Access в принципе невозможно, потому что в Lazarus нет возможности работать через ADO. В документации к Zeos сказано, что для баз данных с которыми Zeos не умеет работать напрямую (а именно такой базой данных является MS Access) рекомендуется использовать ADO-мост.
Установил Zeos в Delphi 7. При попытке подключиться к той же базе данных вылезла точно такая же ошибка. Хотя может быть я что-то не так настроил, например в ZConnection есть свойство LibraryLocation, может быть там надо указать адрес каких-то dll.
Добавлено спустя 4 минуты 1 секунду:
Re: Знаки вопроса при получении текстовых данных из MS Access
bormant писал(а):Нужно искать способ подключения в Юникоде
Ищу. Пока безуспешно.
- Little_Roo
- энтузиаст
- Сообщения: 639
- Зарегистрирован: 27.02.2009 18:56:36
- Откуда: Санкт-Петербург
dimmm писал(а):установил компоненты Zeos
Откуда? Из SVN?
dimmm писал(а):Хотя может быть я что-то не так настроил, например в ZConnection есть свойство LibraryLocation
А в свойстве Protocol - что?
