Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "Начинающим";
Текущий архив: 2005.12.25;
Скачать: [xml.tar.bz2];

Вниз

Const - параметры функции   Найти похожие ветки 

 
gdaujk ©   (2005-12-10 15:59) [0]

Вомногих книгах, да и в справке написано, что кроме запрета на напосредственное изменение const-параметра в теле функции, он ещё и каким-то особенным, "оптимизированным" способом передаётся в функцию (имеются в виду строки и записи). Не объясните, в чём именно состоит оптимизация?


 
palva ©   (2005-12-10 16:02) [1]

Оптимизация состоит в том, что передается адрес данных. Если const не указано, то адрес данных передавать опасно, поскольку функция может изменить данные. Поэтому приходится копировать данные в отдельную область и передавать адрес этой области, либо передавать сами данные, что тоже накладно.


 
Ihor Osov'yak ©   (2005-12-10 16:10) [2]

в дополнение.

ключевое слово const в параметрах заставляет следить компилятор за кодом, чтобы не происходило изменения значения параметра в коде процедуры. Хотя это не абсолютная панацея - от изменеия по указателю,  либо низкоуровневыми функциями типа move компилятор не защитит.

Оптимизация же в части строк и рекордов состои в том, что вместо выделения буфера на копию и последующем копировании происходит просто передача адреса, то есть засылка 4 байт в стек - то есть намного быстрее.


 
gdaujk ©   (2005-12-10 16:13) [3]

Мне вот просто кажется, что при передании функци параметра-строки без const тоже передаётся адрес. Только потом, если параметр изменяется, то создаётся копия строки.

Или, возможно, компилятор, если видит, что не-const-параметр в теле функции не изменяется, то организует просто передачу адреса, как как если бы параметр был const. Я прав?


 
Ihor Osov'yak ©   (2005-12-10 16:22) [4]

2 gdaujk ©   (10.12.05 16:13) [3]

> Мне вот просто кажется, что при передании функци параметра-строки без const тоже передаётся адрес.

Передается адрес. Все верно. Но уже на копию. Которая создается непосредственно перед передачей адреса. Посмотрите на код, которій генерирует компилятор. делов то на две минуты.

> Или, возможно, компилятор, если видит, что не-const-параметр в теле функции не изменяется, то организует просто передачу адреса, как как если бы параметр был const. Я прав?

Нет, не прав. Ибо дело обстоит не так. А так как Вы говорите - вряд ли на практике кто-то реализует - так как очень сложнымы и неочевидными будут соглашения о передачи параметров в процедуру. Ну, разве что какой-то любитель наступать на грабли будет делать  свою реализацию системы прорамирования. Но, обычно, такие любители  или вылечиваются до того, или не доживают..


 
begin...end ©   (2005-12-10 16:48) [5]

> Ihor Osov"yak ©   (10.12.05 16:10) [2]

> происходит просто передача адреса, то есть засылка 4 байт
> в стек

Почему обязательно в стек?

> Ihor Osov"yak ©   (10.12.05 16:22) [4]

> Передается адрес. Все верно. Но уже на копию. Которая создается
> непосредственно перед передачей адреса.

Неверно. Копия создаётся не перед передачей адреса, а после его передачи (уже внутри вызываемой подпрограммы).


 
Ihor Osov'yak ©   (2005-12-10 17:20) [6]

> Почему обязательно в стек?

Если засылка, то в стек :-). Конечно, есть еще передача через регистры, и она имеет место для первіх параметров для определенных  моделей вызова, но это уже ньюансы, не отражающиеся на основном сабже..

> Неверно. Копия создаётся не перед передачей адреса, а после его передачи (уже внутри вызываемой подпрограммы).

В принципе - да. Не совсем верно проанализировал код созданный компилятором. Кстати, похоже на то, что все же gdaujk ©   (10.12.05 16:13) [3]  частично прав - если передавать без const и не изменять в процедуре - то там интересные танцы с _LStrAddRef - тохоже, что копия в таком случае тупо не создается.. Хотя сейчас более детально влом разбираться..


 
jack128 ©   (2005-12-10 17:47) [7]

Ihor Osov"yak ©   (10.12.05 16:22) [4]
Но уже на копию. Которая создается непосредственно перед передачей адреса.

А каких строках говорим?? Если о длинных, то при передаче по значению происходит увеличение счетчика ссылок, а при  передаче по константной ссылке - такого увеличения не происходит. Вот и вся разница. ПО поводу передаче указателя при указании const - то это происходит, только если SizeOf(Параметр) > SizeOf(Pointer).


 
gdaujk ©   (2005-12-10 18:22) [8]

Передается адрес. Все верно. Но уже на копию.

А мне всё-таки кажется, что не на копию. Приведу пример. Есть функция:

function gdaExample(Str: string): string;
var
 P: PChar;
begin
 P := PChar(Str);
 P^ := "A";
 Result := Str;
end;


1) вызываю её так: gdaExample("dfdfdfdfdf") - выдаётся ошибка, по видимому - обращение к памяти, выделенной только для чтения.

2) делаю так:

Str := "dfdfdfdfdf";
gdaExample("dfdfdfdfdf");


Появляется тоже ошибка.

3) хитрю, делаю так:

 Str := "dfdfdfdfdf"; //Str пока только ссылается на "dfdfdfdfdf"
 Str := Str + "f";    //а вот сдесь уже выделяется READWRITE память под Str
 gdaExample(Str);    //нет ошибки

То есть, если бы создавалась копия, она бы была READWRITE и ошибки бы не возникало. Или может это можно как-то по другому объяснить?

PS: опытным путём, понимаишь :-)))


 
Lamer@fools.ua ©   (2005-12-10 19:51) [9]

>>gdaujk ©   (10.12.05 18:22) [8]

>То есть, если бы создавалась копия, она бы была READWRITE и ошибки бы не возникало. Или может это можно как-то по другому объяснить?

Можно. Для этого достаточно открыть окно дизассемблера, а также почитать System.pas, раз уж не верите и хотите (не)опытным путём.



Страницы: 1 вся ветка

Форум: "Начинающим";
Текущий архив: 2005.12.25;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.47 MB
Время: 0.013 c
2-1133810801
ZefiR
2005-12-05 22:26
2005.12.25
Помогите! Мой Дельфак выкидывает ошибку!


14-1133281204
beglec
2005-11-29 19:20
2005.12.25
Подскажите компонент или что ни будь еще для сортировки данных


2-1133957542
Aleks
2005-12-07 15:12
2005.12.25
Как узнать существует папка или нет??


5-1117790468
Никита
2005-06-03 13:21
2005.12.25
Как сделать чтобы компонент мог размещать на себе другие Контролы


2-1133963455
Muh
2005-12-07 16:50
2005.12.25
Как удалить папку ..непустую!!!





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский