![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
хитрый массив [D7]
race1 © (2004-07-28 18:12:00)я хочу перевернуть массив наоборот, т.е. [1, 2, 3] превратить в [3, 2, 1]. т.к. это действо встречается часто, задумал я это дело в процедуру вынести
процедура принимает аргументом адрес переменной (байты которой являются элементами массива), и устанавливает адрес локального массива процедуры переданному адресу. т.е.
procedure proc(pnt: Pointer);
type
TMyArray = Array of Byte;
PMyArray = ^TMyArray;
var
MyArrayP: PMyArray;
MyArray: TMyArray;
begin
MyArrayP := pnt;
MyArray := MyArrayP^;
...
но дальше все действия с MyArray'ем приводят к ошибке. а почему?
SergP (2004-07-29 20:57:00) [1]А какой смысл переворачивания массива?
Не проще ли "перевернуть" индекс и таким образом обращаться к элементам масссива?
Типа например имеем массив A:array[1..10] of Mytype;
Обращаемся к нему A[i] - будет обычным (относительно i)
А обращаемся так: A[11-i] - будет типа "перевернутым" (относительно i)?
nikkie (2004-07-29 20:33:00) [2]>вобщем есть переменная, например, интегер, в ней хранятся 4 байта (01 00 00 00), а мне нужно эти байты перевернуть, т.е. сделать 00 00 00 01. думаю так: если массив на самом деле указатель, то установить адрес начала массива (кстати, array of byte) на адрес нашей integer переменной. в таком случае вроде должен получиться массив из 4 байтов.
плохая идея. здесь неявно подразумевается порядок представления integer байтами. на другой архитектуре можно получить совершенно неожиданный результат. арифметическую перестановку байтов надо реализовывать арифметическими операторами.
Kurtevich (2004-07-29 10:45:00) [3]
> Интересная мысль. Знаете фокус? Вы выполняете
> ShowMessage(IntToStr(SizeOf(array)))
> , а я угадываю результат! Очень круто!
ну да, ОК, я прогнал - тут надо length или шото такое вызывать -мне просто влом в документаию лезть смотреть... я же сказал, что все это накалякано сходу - экспромтом за пол минуты!
фокусник тоже мне... [7]
Anatoly Podgoretsky (2004-07-29 10:24:00) [4]Увидел, что испточник и приемник разные, а то бы был Двойной реверс, а так все нормально.
1-4
2-3
3-2
4-1
Digitman (2004-07-29 10:14:00) [5]
> Anatoly Podgoretsky © (29.07.04 10:03) [30]
?
мы же не слова меняем, а байты ..
Anatoly Podgoretsky (2004-07-29 10:03:00) [6]Digitman © (29.07.04 09:37) [22]
for i:= 0 to 1do //Length div 2
Sandman25 (2004-07-29 10:03:00) [7][28] Digitman © (29.07.04 10:01)
Все правильно. Это я чего-то недопонял. Посчитал, что нам нужно изменить Data. Поэтому же написал и [25].
Digitman (2004-07-29 10:01:00) [8]
> Sandman25 © (29.07.04 09:45) [24]
зачем VAR ? это уже косвенная ссылка получается, т.е. указатель на указатель ... в процедуру, как я понял, нужно передать адрес переменной типа Integer и, рассматривая заначение этой переменной как стат.массив из 4-х байт, зеркально поменять его элементы "на месте" .. или я чего-то недопонял
ЮЮ (2004-07-29 09:50:00) [9]>Например, циклический сдвиг массива...
если только СДВИГ, то - да, причем ПО ФАЗЕ :)
а изменить порядок обхода будет труднее?
Sandman25 (2004-07-29 09:47:00) [10]Вру, [25] игнорируем :)
Sandman25 (2004-07-29 09:46:00) [11]И кстати, все равно неправильно - получаем указатель на стек.
Sandman25 (2004-07-29 09:45:00) [12][22] Digitman © (29.07.04 09:37)
procedure Mirror( varData: PInteger);
Romkin (2004-07-29 09:44:00) [13]ЮЮ © (29.07.04 03:52) [17] Не лучше :))
С помошью процедуры реверсирования порядка элементов много чего делается :))
Например, циклический сдвиг массива...
Digitman (2004-07-29 09:37:00) [14]
> race1
procedure Mirror(Data: PInteger);
var
i, Out: Integer;
begin
for i:= 0 to 3 do
PByte(@Out)[i] := PByte(Data)[3 - i];
Data^ := Out;
end;
Romkin (2004-07-29 09:37:00) [15]Вашу Машу! Ну нафига работать с указателем? При этом не понимая, как надо с ним работать, и не понимая, что динамический массив - уже указатель!
procedure Reverse(var A: Array of integer);
var
i, n: integer;
T: integer;
begin
if not assigned(A)
then Exit;
n := High(A);
for i := Low(A) to n div 2 do
begin
T := A[i];
A[i] := A[n - i];
A[n - i] := T;
end;
end;
Вроде не ошибся. Перед вызовом процедуры массив должен быть создан
ЮЮ (2004-07-29 07:34:00) [16]>если массив на самом деле указатель, то установить адрес начала массива ...
такие фокусы можно, пожалуй, с array[0..3] of byte провернуть, но никак не с динамическим массивом
race1 (2004-07-29 06:24:00) [17]вобщем есть переменная, например, интегер, в ней хранятся 4 байта (01 00 00 00), а мне нужно эти байты перевернуть, т.е. сделать 00 00 00 01. думаю так: если массив на самом деле указатель, то установить адрес начала массива (кстати, array of byte) на адрес нашей integer переменной. в таком случае вроде должен получиться массив из 4 байтов. далее переворачиваем массив вверх ногами, но на самом деле изменяем и значение переменной интегер, т.к. массив и интегер находятся по одному и тому же адресу
но почему-то EInvalidPointer, если так:
MyArray := Pnt;
...
// работа с MyArray как с массивом
...
race1 (2004-07-29 06:24:00) [18]ах, да, нам не нуен массив, нам нужна переменная интегер, массив временный
ЮЮ (2004-07-29 03:52:00) [19]>я хочу перевернуть массив наоборот, т.е. [1, 2, 3] превратить в [3, 2, 1].
не лучше ли
1) создавать его сразу в нужном порядке
2) при использовании учитывать, что он перевернут, т.е. не
myarray[i], a myarray[Length(a) - i];
Anatoly Podgoretsky (2004-07-29 00:02:00) [20]Ну какой же это хитрый массив?