Вверх ↑
Этот топик читают: Гость
Ответов: 4621
Рейтинг: 746
#31: 2015-09-24 16:58:49 ЛС | профиль | цитата
Во-первых, в коде можно делать всё, что позволяет язык и компилятор, с учетом критериев читабельности, производительности, портабельности и т.п.
Во-вторых, оператор Delete не изменяет строку в том контексте, который тут обсуждается, иначе бы этот код не работал:

#pas
var
S: string;
begin
S := '123456789';
Delete(S, 1, 1);
_debug(S);
end;
Грубо говоря:

#pas
var
S1, S2: string;
begin
S1 := '123456789';
S2 := S1;
// Здесь S2 = S1, точнее, строки не только равны побуквенно, а это одна и та же строка
Delete(S2, 1, 1);
// Здесь S2 <> S1, что значит, что в S2 произошло копирование строки S1 и затем в S2 была присвоена обработанная строка
end;
карма: 26

0
Ответов: 2059
Рейтинг: 131
#32: 2015-09-25 08:56:07 ЛС | профиль | цитата
Netspirit писал
Tad, это никак не противоречит тому, что присвоение String := PChar приводит к копированию.

Да, - вообще, никаких действий не происходит. (даже не увеличивается счётчик ссылок на строку "string(счётчик-длина-(PChar(строка-0)))
Грубо говоря PChar это кусок той же String.
Netspirit писал
Грубо говоря:
var
S1, S2: string;
begin
S1 := '123456789';
S2 := S1;
// Здесь S2 = S1, точнее, строки не только равны побуквенно, а это одна и та же строка
Delete(S2, 1, 1);
// Здесь S2 <> S1, что значит, что в S2 произошло копирование строки S1 и затем в S2 была присвоена обработанная строка
end;

Железно.


карма: 6

0
Ответов: 4621
Рейтинг: 746
#33: 2015-09-25 10:49:23 ЛС | профиль | цитата
flint2 писал(а):
вообще, никаких действий не происходит

flint2, при присвоении String := PChar - происходит.



PChar - не string. PChar - это указатель на блок памяти, который должен быть ограничен 0-вым байтом. А String кроме подобного блока символов содержит ещё и служебные данные. Именно поэтому происходит копирование (создание новой string) при присвоении String := PChar. А поскольку у String тоже есть "блок памяти, ограниченный 0-вым байтом", то получение PChar из string не приводит ни к каким последствиям для string.

[offtop]Оговорка по поводу @S[1]. Хотя @S[1] можно передавать в функции, которым нужен PChar, но, как я понял, Delphi перестраховывается в этом случае и делает копию строки S (на случай изменения символов в вызываемой функции)[/offtop]
карма: 26

0
Ответов: 2059
Рейтинг: 131
#34: 2015-09-25 11:21:32 ЛС | профиль | цитата
Netspirit, Я Ничего не понял.
"Любой блок памяти" это и есть счётчик и длина, PChar об этом без понятия. Ноль уже не обсуждается он везде есть по определению.
Если строка не изменяется, а только кто-то упомянул её, то счётчик +/- , если изменяется то выделяется кусок памяти в куче и она копируется туда(уже изменённая в виде string, или pchar - как её определили).


карма: 6

0
Ответов: 4621
Рейтинг: 746
#35: 2015-09-25 11:42:57 ЛС | профиль | цитата
Раз "PChar об этом без понятия", то "любой блок памяти" это не есть "счётчик и длина", но всё равно правильный PChar, поэтому я так и нарисовал. А string - это счетчик и длина, да.
карма: 26

0
Ответов: 2059
Рейтинг: 131
#36: 2015-09-25 14:19:45 ЛС | профиль | цитата
Netspirit,
Согласен, что масло масленое.
карма: 6

0
Ответов: 9906
Рейтинг: 351
#37: 2015-09-25 14:37:15 ЛС | профиль | цитата
Netspirit писал(а):
то получение PChar из string не приводит ни к каким последствиям для string

За исключением случая нулевой длины.
pchar(Str) гарантированно <>nil, даже для случая Str=nil

Как бы pchar(Str) не всегда совпадает с @Str[1]
карма: 9

0
Ответов: 2059
Рейтинг: 131
#38: 2015-09-25 14:50:47 ЛС | профиль | цитата
Galkov,
Ну надо в идиллию ложку дёгтя?
Операция Ы
Надо Федя, надо!

карма: 6

0
Ответов: 4621
Рейтинг: 746
#39: 2015-09-25 15:53:32 ЛС | профиль | цитата
Вот демонстрация некоторых обсуждаемых аспектов: code_36301.txt
Заметьте, что после обращения к символу строки строка копируется (адрес отличается).

Переменные типа string - это указатели на первый символ строки, поэтому последняя строчка - это указатель на указатель.
карма: 26

0
файлы: 1code_36301.txt [1.2KB] [530]
Разработчик
Ответов: 26066
Рейтинг: 2120
#40: 2015-09-25 16:45:12 ЛС | профиль | цитата
Netspirit писал(а):
Переменные типа string - это указатели на первый символ строки

Какой же это указатель на первый символ, когда это record? Сам же на картинке нарисовал именно Packed Record
карма: 22

0
Ответов: 4621
Рейтинг: 746
#41: 2015-09-25 16:51:06 ЛС | профиль | цитата
Это они в памяти похожи на record, но переменная имеет размер 4 байта и является указателем на первый символ. Как и dynamic array, class (но не object).
карма: 26

0
Ответов: 2059
Рейтинг: 131
#42: 2015-09-25 16:52:04 ЛС | профиль | цитата
Переменные типа string - это указатели на первый символ строки

Кто скажет, что это не так, - пусть бросит в меня камень,
указатель на указатель
это вопрос философский, но очень даже понятный.
Я извиняюсь, но есть вопрос в силу моей необразованности, -
но переменная имеет размер 4 байта

а какие ещё переменные бывают? (в рамках 32 компиляторов)
карма: 6

0
Ответов: 16884
Рейтинг: 1239
#43: 2015-09-25 16:57:29 ЛС | профиль | цитата
Netspirit, покажи где у меня происходит копирование в другую область памяти
code_36302.txt
при изменении текста.
карма: 25
Немного терпения! Дежурный экстрасенс скоро свяжется с Вами!
0
файлы: 1code_36302.txt [1.9KB] [429]
Ответов: 4621
Рейтинг: 746
#44: 2015-09-25 17:24:10 ЛС | профиль | цитата
А я и не говорил, что в коде невозможно этого добиться. Мои замечания касались только работы этого кода на уровне схемы.
карма: 26

0
Ответов: 16884
Рейтинг: 1239
#45: 2015-09-25 17:37:16 ЛС | профиль | цитата
А вот (на пальцах) то, что делает PChar(S)
code_36303.txt
И никаких копирований при использовании "обыкновенных" строк.
При работе с WideString копирование происходит "при любом чихе" и только потому, что у них нет счётчика ссылок.
карма: 25
Немного терпения! Дежурный экстрасенс скоро свяжется с Вами!
0
файлы: 1code_36303.txt [985B] [482]
Сообщение
...
Прикрепленные файлы
(файлы не залиты)