Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > Delphi программирование > Общие вопросы Delphi
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 11.02.2009, 23:59   #11
Somebody
Участник клуба
 
Регистрация: 08.10.2007
Сообщений: 1,185
По умолчанию

[QUOTE=Armorer;202906]
Код:
 TestStr := 'Строка1';
 CharToOem( PChar(TestStr), PChar(TestStr) );
 Writeln( TestStr );

 TestStr := 'Строка2';
 CharToOem( @TestStr[1], @TestStr[1] );
 Writeln( TestStr );
View -> Debug Windows -> CPU
Случай второй. Компилятор видит, что передаются 2 адреса символа строки. Создаётся 2 копии строки (именно 2 копии, а изначально строка была в read only памяти), всё хорошо.
Случай первый. Компилятор видит, что передаётся 2 каких-то адреса и передаёт адрес read only памяти, функция пытается туда писать, получается исключение. Это у меня так в Delphi 6, может быть, в других версиях по-другому.
Somebody вне форума Ответить с цитированием
Старый 12.02.2009, 07:31   #12
Armorer
Подтвердите свой е-майл
 
Регистрация: 07.04.2007
Сообщений: 120
По умолчанию

[QUOTE=Somebody;203962]
Цитата:
Сообщение от Armorer Посмотреть сообщение
Код:
 TestStr := 'Строка1';
 CharToOem( PChar(TestStr), PChar(TestStr) );
 Writeln( TestStr );

 TestStr := 'Строка2';
 CharToOem( @TestStr[1], @TestStr[1] );
 Writeln( TestStr );
View -> Debug Windows -> CPU
Случай второй. Компилятор видит, что передаются 2 адреса символа строки. Создаётся 2 копии строки (именно 2 копии, а изначально строка была в read only памяти), всё хорошо.
Случай первый. Компилятор видит, что передаётся 2 каких-то адреса и передаёт адрес read only памяти, функция пытается туда писать, получается исключение. Это у меня так в Delphi 6, может быть, в других версиях по-другому.
Наверно имелись в виду эти функции?
Код:
Function Convert1( S : String ) : String;
begin
 CharToOem( PChar(S), PChar(S) );
 Result := S;
end;

Function Convert2( S : String ) : String;
begin
 CharToOem( @S[1], @S[1] );
 Result := S;
end;
Тот код у меня работает в 6 и 7 нормально. А вот функции нет.


Скорее всего это правильное объяснение, так как в таких видах функция работает:

Код:
Function Convert1(S : String ) : String;
begin
 UniqueString(S1);
 CharToOem( PChar(S), PChar(S) );
 Result := S;
end;

Function Convert1(var S : String ) : String;
begin
 CharToOem( PChar(S), PChar(S) );
 Result := S;
end;

Function Convert1(S : String ) : String;
begin
 S[1] := 'T';
 CharToOem( PChar(S), PChar(S) );
 Result := S;
end;
А вот так ошибка:
Код:
Function Convert2(var S : String ) : String;
begin
 CharToOem( Pointer( S[1] ), Pointer( S[1] ) );
 Result := S;
end;
То есть копия создается только в случае вызова @S[1] и не создаётся в случаях Pointer( S[1] ), Pointer( S ), PChar( S ).

Но вызов функции CharToOem( PChar(S), PChar(S) ); не работает только внутри функции Convert1. И если исходить из того что копирование не происходит то и в программе
Код:
 TestStr := 'Строка1';
 CharToOem( PChar(TestStr), PChar(TestStr) ); //должна быть ошибка
Но ошибки у меня нет. Хотя также константа 'Строка1' создается в памяти которую нельзя менять, на неё устанавливается строка (указатель) TestStr, а за тем в CharToOem передается этот же указатель на память read only. Но ошибки нет и возникает противоречие=)

Теперь вопрос стоит немного по другому - почему это не работает:

Код:
Function Convert1(S : String ) : String;
begin
 CharToOem( PChar(S), PChar(S) );//ошибка
 Result := S;
end;
***
Writeln( Convert1( 'Тест' ) );
а вот это работает:
Код:
Program aaa;
***
var
TestStr  : String;
begin
 TestStr := 'Строка1';
 CharToOem( PChar(TestStr), PChar(TestStr) ); //ошибки нет
 Writeln( TestStr );
***
Вот статья по теме, хотя в ней ответа я не нашел.
http://www.delphikingdom.ru/asp/view...catalogid=1206
Armorer вне форума Ответить с цитированием
Старый 12.02.2009, 20:17   #13
Somebody
Участник клуба
 
Регистрация: 08.10.2007
Сообщений: 1,185
По умолчанию

(Это предположение на основе воспоминаний, не проверял) Похоже, что в случае
TestStr := 'Строка'; Convert1(TestStr);
строка оказывается в секции данных, а в случае
Convert1('Строка');
в секции кода (это такая фича у Borlandовских компиляторов, другие вроде данные в секции кода не размещают)

Последний раз редактировалось Somebody; 12.02.2009 в 20:20.
Somebody вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц

Опции темы Поиск в этой теме
Поиск в этой теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
PChar Роман Радер Общие вопросы Delphi 2 02.11.2008 18:50
String to PChar D7_beginner Общие вопросы Delphi 2 21.11.2007 14:05
Access violation на строке вида StrLCopy(PChar(st1),PChar(st2),10); malor Общие вопросы Delphi 1 11.07.2007 13:39
Добавление к pchar EdNovice Общие вопросы Delphi 2 15.04.2007 17:00
Как из string получить PChar??? sis Компоненты Delphi 4 11.02.2007 16:58