Текущий архив: 2004.12.19;
Скачать: CL | DM;
Вниз
Почему один кусок кода работает а второй нет ведь они эквивалентн Найти похожие ветки
← →
MegaVolt © (2004-12-03 17:07) [0]Это работает:
var
temp,Data:ByteArray;
...
temp:=ByteArray(@Data[i*128]);
AT17LV010.Write(i,temp);
...
AT17LV010.Write(i:integer;const Buf);
Это нет. Говорит переменную хочу. А зачем переменная ведь я вроде как константу передаю?
var
Data:ByteArray;
...
AT17LV010.Write(i,ByteArray(@Data[i*128]));
...
AT17LV010.Write(i:integer;const Buf);
← →
Verg © (2004-12-03 17:25) [1]
> AT17LV010.Write(i:integer;const Buf);
Это передача нетипизированной ссылки на что-то.
В первом случае ты передаешь ссылку на переменную temp.
Во втором - непонятно на что.
Слово const указывает в данном случае, что само значение переменной на которую передается ссылка изменятся на самом деле не будет. Это может помочь оптимизатору.
То же самое, только без "помощи оптимизатору":
AT17LV010.Write(i:integer; var Buf);
> temp:=ByteArray(@Data[i*128]);
> AT17LV010.Write(i,temp);
А что тебе не дает написать по-простому, без выкручивания рук себе и компилеру:
AT17LV010.Write(i, Data[i*128]);
← →
MegaVolt © (2004-12-03 17:56) [2]Data[i*128] не работает :( Я пробовал. В функцию передаётся массив без первого элемента :(
← →
MegaVolt © (2004-12-03 19:12) [3]есди в
AT17LV010.Write();
Buf описать как ByteArray тоAT17LV010.Write(i,ByteArray(@Data[i*128]));
проходитAT17LV010.Write(i, Data[i*128]);
непроходит.
← →
MegaVolt © (2004-12-03 19:47) [4]гы... а дальнейшие эксперименты показали что и ByteArray(@Data[i*128]) глючит :(
Короче осталось только Copy(Data,i*128,128); вроде работает без проблем.
Либо отказыватся от array of byte и переходить к кускам динамически выделенной памяти с ней уж точно такие фокусы проходят.
← →
Verg © (2004-12-03 19:59) [5]
> [2] MegaVolt © (03.12.04 17:56)
> Data[i*128] не работает :( Я пробовал. В функцию передаётся
> массив без первого элемента :(
А тебе чего надо-то. С какого элемента?
Ты смысл того, что ты задумал можешь объяснить?
А то сумбур какой-то прет,.... черт ногу сломит....
← →
MegaVolt © (2004-12-06 09:17) [6]Смысл прост: Есть большой массив есть функция которая принимает на обработку маленький массив. Хотелось бы обработать большой массив без предварительного копирования маленьких кусков во временную переменную.
Например массив от 0 до 19
В функцию необходимо передать
0-4
5-9
10-14
15-19
При передаче очень бы хотелось не исспользовать копирование.
← →
Digitman © (2004-12-06 09:24) [7]var
temp: PByteArray;
Data:TByteArray;
...
temp:=@Data[i*128];
AT17LV010.Write(i,temp^);
← →
MegaVolt © (2004-12-06 09:29) [8]TByteArray=array[0..32767] of Byte;
Я же говорю про array of byte т.е. про динамический массив.
← →
Digitman © (2004-12-06 09:34) [9]
> MegaVolt © (06.12.04 09:29) [8]
а какая разница ?
ну тогда сделай так
var
temp: PByte;
Data: Array of byte;
...
temp:=@Data[i*128];
AT17LV010.Write(i,temp^);
← →
MegaVolt © (2004-12-06 09:42) [10]А вот и не пашет :(
← →
Digitman © (2004-12-06 10:01) [11]
> MegaVolt © (06.12.04 09:42) [10]
"не пашет" - это детский сад.
"вызывает ошибку компиляции" и "вызывает ошибку в ран-тайм или неправильно работает в ран-тайм" - две разные разницы
практически эквивалентный вариант у меня компилируется безо всяких проблем :
procedure Write(i:integer;const Buf);
begin
end;
var
temp: PByte;
Data: Array of byte;
i: Integer;
..
temp:=@Data[i]; //получили адрес элемента с индексом i
Write(i,temp^); //передали индекс и адрес элемента в проц-ру
← →
MegaVolt © (2004-12-06 10:05) [12]Выдаёт run-time error AV.
Вот мой пример:
ByteArray=array of byte;
....
Mas:ByteArray;
...
procedure TForm1.FormCreate(Sender: TObject);
begin
SetLength(Mas,20);
Mas[0]:=100;
Mas[1]:=101;
Mas[2]:=102;
Mas[3]:=103;
Mas[4]:=104;
Mas[5]:=105;
Mas[6]:=106;
Mas[7]:=107;
Mas[8]:=108;
Mas[9]:=109;
Mas[10]:=110;
Mas[11]:=111;
Mas[12]:=112;
Mas[13]:=113;
Mas[14]:=114;
Mas[15]:=115;
Mas[16]:=116;
Mas[17]:=117;
Mas[18]:=118;
Mas[19]:=119;
end;
procedure Obr1(var Buf);
var
i:integer;
s:string;
begin
s:="";
for i:=0 to 3 do
s:=s+IntToStr(ByteArray(Buf)[i])+" ";
Form1.RichEdit1.Lines.Add(s);
end;
procedure TForm1.Button5Click(Sender: TObject);
var
i:integer;
temp:PByte;
begin
for i:=0 to 4 do
begin
temp:=@Mas[i*4];
Obr1(temp^);
end;
end;
Вылетает в функции Obr1 при обращении к нулевому элементу.
Если в Obr Buf определить явно как ByteArray то даже не компилится.
← →
Digitman © (2004-12-06 10:16) [13]вот это :
ByteArray(Buf)
с какого перепугу ты приводишь Buf к типу ByteArray ?
тебе в процедуру передан не адрес дин.массива, а адрес некоего его элемента !
в ДАННОМ случае д.б. так :
s:=s+IntToStr(PByteArray(@Buf)[i])+" ";
или
s:=s+IntToStr(TByteArray(Buf)[i])+" ";
← →
MegaVolt © (2004-12-06 10:24) [14]А почему я могу писать вместо ByteArray(Buf) TByteArray(Buf)? Или для фиксированного массива такое возможно а для динамического нет? А что делать если куски данных больше 32К?
← →
Erik1 © (2004-12-06 10:32) [15]Каша у тебя в голове и неправильна организована передача и хранение данных. Ты бы лучше привел, что тебе надо хранить, тебе подскажут как это лучше передовать и хранить.
← →
MegaVolt © (2004-12-06 10:44) [16]Мне не нужно быстрое решение которое я вставлю и забуду о нём до следующего раза. Я хочу ПОНЯТЬ в чём я ошибаюсь, что я делаю не так и почему. Если есть желание помочь помоги. Буду очень благодарен. Если ты видишь кашу приведи нестыковки которые ты заметил. Я попробую пояснить из чего они возникают.
← →
Digitman © (2004-12-06 10:55) [17]
> почему я могу писать вместо ByteArray(Buf) TByteArray(Buf)
в дан.случае вместо ByteArray(Buf) ты волен писать практически все что угодно, в т.ч. и TByteArray(Buf) - это просто явное приведение типа, т.е. указание компилятору о том КАК ему следует интерпретировать нетипизированную ссылку на параметр Buf
суть же состоит в том, что дин.массив является не просто шматком памяти, содержащей содержимое элементов некоего типа - это спец.структура, содержащая кроме всего прочего заголовочную инф-цию, описывающую собственно массив (число элементов, размер элемента и пр.)
> что делать если куски данных больше 32К?
да тоже самое и делать - разницы никакой
← →
MegaVolt © (2004-12-06 12:08) [18]В смысле никакой разницы? Т.е. я смогу выйти за границу массива и дельфи не ругнётся?
Где можно посмотреть внутреннюю организацию переменных разных типов в дельфи? Т.е. где прочитать про то что в динамическом массиве есть какая то инфа в начале а в статическом она находится где то ещё или её вообще нету?
← →
ЮЮ © (2004-12-06 12:14) [19]А почему бы в процедуру не передать указатель на динамический массив и не парить никому мозги? И никакую память копировать никуда не надо, и все знают, что это динамический массив?
← →
Digitman © (2004-12-06 12:19) [20]
> MegaVolt © (06.12.04 12:08) [18]
> Т.е. я смогу выйти за границу
> массива и дельфи не ругнётся?
и снова детский сад.
ты о чем речь ведешь - о дизайн-тайм или ран-тайм ?
> где прочитать про то что в динамическом массиве есть какая
> то инфа в начале
system.pas, описание структуры TDynArrayTypeInfo
> в статическом она находится где то ещё или её вообще нету?
ее вообще нету, потому что все характеристики (и содержимое на момент старта) будущего массива известны компилятору и линкеру
← →
MegaVolt © (2004-12-06 12:42) [21]
> > MegaVolt © (06.12.04 12:08) [18]
> > Т.е. я смогу выйти за границу
> > массива и дельфи не ругнётся?
>
> и снова детский сад.
> ты о чем речь ведешь - о дизайн-тайм или ран-тайм ?
Выход за пределы массива проверяется вроде в рантайме так что вопрос: почему компилятор разрешит выходить за границу массива который определён размером 32К?
> system.pas, описание структуры TDynArrayTypeInfo
Спасибо :) Только сразу возникают ещё вопросы.
Как ты нашел эту структуру? Ведь она даже в хелпе не описана.
Что означают поля?
← →
Digitman © (2004-12-06 14:44) [22]
> Выход за пределы массива проверяется вроде в рантайме
не только в ран-тайм.
компилятор способен сгенерировать предупреждение, если индекс эл-та массива ему заранее известен и этот индекс выходит за объявленные границы индексов массива
> Как ты нашел эту структуру?
а что ее искать-то ? достаточно задаться вопросом, что происходит, когда в ран-тайм происходит вызов setLength()
> Что означают поля?
в большинстве случаев об этом даже знать не нужно - достаточно понять, что содержимое переменной типа "дин.массив" есть на самом деле не собственно блок памяти с содержимым эл-тов этого массива, а именно указатель на начало упр.структуры этого массива в памяти процесса
← →
MegaVolt © (2004-12-06 15:29) [23]Спасибо огромнейшее :)
Страницы: 1 вся ветка
Текущий архив: 2004.12.19;
Скачать: CL | DM;
Память: 0.53 MB
Время: 0.025 c