Top.Mail.Ru
Мастера DELPHI, Delphi programming community Титульная страница Поиск, карта сайта Написать письмо 
| Новости | Поиск | FAQ | Статьи | Книги | Новости VCL |
| Форумы ЧАТ | Орешник | KOL и MCK |
Форумы -» Основная («Начинающим»)/ Базы / WinAPI / Компоненты / Сети / Media / Игры / Corba и COM / KOL / FreePascal / .Net / Прочее / RSDN.ORG

« предыдущая ветвь | форум | следующая ветвь »

array [0..0] of ... [D7]


Страницы:   1 2

Прима ©   (2009-09-18 12:49:00) 


type

 TElem = packed record
   S1:Byte;
   S2:Byte;
   D1:DWord;
 end;

 TMArr = array [0..0] of TElem;

 TFuck = record
   B:Byte;
   Q:TMArr;
 end;

procedure TForm1.Button1Click(Sender: TObject);
 var Q:TFuck;
 I:Integer;
begin
 Q.B:=1;
 Q.Q[0].S1:=1;
 Q.Q[0].S2:=1;
 Q.Q[0].D1:=1;
 Q.Q[1].S1:=2; <=Constant expression violates subrange bounds
 Q.Q[1].S2:=2;
 Q.Q[1].D1:=2;
 //
 for I:=0 to Length(Q.Q)-1 do
 begin
   Memo1.Lines.Add(Format('%d %d',[Q.Q[I].S1, Q.Q[I].S2]));
 end;
end;


В чем я не прав ? Необходимо заранее указывать размер массива?
Тогда как ?

Спасибо !


Anatoly Podgoretsky   (2009-09-22 13:38:00) [1]

> Sapersky  (22.09.2009 13:08:25)  [25]

Ничего писать не надо, в системе уже объявлены нужные константы.


Leonid Troyanovsky   (2009-09-22 13:26:00) [2]


> Sapersky   (22.09.09 13:08) [25]

> писать что-то вроде [0..(MaxInt div SizeOf(TElement))-1].

const
 MaxElem = MaxInt div SizeOf(TElem);

--
Regards, LVT.


Sapersky   (2009-09-22 13:08:00) [3]

Ну пусть будет 0..много, не принципиально. Хотя несколько громоздко получается, чтобы получить макс. размер приходится писать что-то вроде [0..(MaxInt div SizeOf(TElement))-1]. 0..MaxInt-1 компилятор не пропускает, слишком большой размер типа (кроме массива байтов, ест-но).


Anatoly Podgoretsky   (2009-09-22 09:51:00) [4]

> Sapersky  (22.09.2009 03:59:23)  [23]

Хорошо, но зачем для этого 0..0, а не 0..много


Sapersky   (2009-09-22 03:59:00) [5]

Иногда бывает удобно, например, если некий API возвращает нетипизированный указатель, но мы точно знаем, что там массив - можно откастить к массиву и работать с относительным комфортом. Также можно "вырезать" фрагмент массива без копирования, просто сдвинув указатель.

Хотя я в большинстве случаев использую дин. массивы, в основном потому, что их содержимое можно посмотреть при отладке.


Германн   (2009-09-22 02:05:00) [6]


> Прима   (18.09.09 13:35) [8]
>
> Это понятно.
> Я хочу для себя разобраться как работать с [0..0]

А не надо с этим способом объявления "разбираться". Надо его не использовать никогда.


Sapersky   (2009-09-21 23:40:00) [7]

Она нужна, чтобы обмануть "Range check error".

Чем обманывать, так проще вообще отключить (хотя бы локально, $R-). Быстрее работать будет.

Что она должна возвращать - это дело вкуса.

Вообще да, но в примере [11] - нет. Вы же там пытаетесь задать элементам значения через GetItem. Естественно, ничего не задаётся, поскольку всё пишется в возвращаемую переменную, а не в массив.


Прима   (2009-09-21 21:53:00) [8]


> Так и кричит благим матом? "неработаю" мол...


Нет...она работает, но возвращаемые значения не те.


Юрий Зотов   (2009-09-21 20:48:00) [9]

> Sapersky   (21.09.09 17:56) [17]

1. Она нужна, чтобы обмануть "Range check error".
2. Что она должна возвращать - это дело вкуса.
3. Вот SetElem здесь как раз будет лишней.


Sha   (2009-09-21 20:29:00) [10]

> Anatoly Podgoretsky ©   (18.09.09 15:03) [13]
> Правильнее указать диапазон с запасом, чем с недостатком.

Это хоть обойти можно, а вот отрицательный индекс (константу) написать не дают.


Sapersky   (2009-09-21 17:56:00) [11]

ИМХО не нужна она там, разве что для контроля индексов. Проще прямо обращаться к элементам, иначе зачем вся эта возня с объявлением типов.
А если уж использовать функцию, то возвращать она должна указатель (PElem), или для модификации элементов должна быть отдельная функция SetElem.


Юрий Зотов   (2009-09-21 16:40:00) [12]

> Прима   (21.09.09 15:09) [14]

А как Вы думаете, зачем понадобилась функция GetElem?


Palladin   (2009-09-21 16:12:00) [13]


> Прима   (21.09.09 15:09) [14]

Так и кричит благим матом? "неработаю" мол...


Прима   (2009-09-21 15:09:00) [14]

2 Юрий Зотов ©   (18.09.09 14:07) [11]

Я конечно извиняюсь, но пример не работает.
Вывожу так :

for I:=0 to 9 do
   with R.Q[I] do
   begin
     Memo1.Lines.Add(Format('%d %d %d',[I,S1,S2]));
   end;


Anatoly Podgoretsky   (2009-09-18 15:03:00) [15]

> Юрий Зотов  (18.09.2009 14:07:11)  [11]

Так у него проблема как раз с
TMArr = packed array [0..0] of TElem;
Массив размером на 1 элемент и проверка диапазонов ругается на это.
Эта техника из СИ и некоторое время успешнь использовалась в Паскале.
Правильнее указать диапазон с запасом, чем с недостатком.


Прима   (2009-09-18 14:36:00) [16]

Спасибо.


Юрий Зотов   (2009-09-18 14:07:00) [17]

> Прима   (18.09.09 12:49)  

type
 TElem = packed record
   S1:Byte;
   S2:Byte;
   D1:DWord;
 end;
 PElem = ^TElem

 TMArr = packed array [0..0] of TElem;
 PMArr = ^TMArr;

 TRec = record
   B: Byte;
   Q: PMArr;
 end;

function GetElem(R: TRec, Index: integer): TElem;
begin
  Result := PElem(Cardinal(R.Q) + Index * SizeOf(TElem))^
end;

procedure TForm1.Button1Click(Sender: TObject);
var
 R: TRec;
 i: integer;
begin
 R.B:=1;
 GetMem(R.Q, 10 *  SizeOf(TElem)); // Выделили память под 10 элементов
 try
   for i := 0 to 9 do
     with GetElem(R, i) do
     begin
       S1 := i;
       S2 := i;
       D1 := i;
     end
 finally
   FreeMem(R.Q, 10 *  SizeOf(TElem));
 end
end;


Anatoly Podgoretsky   (2009-09-18 13:44:00) [18]

P: ^TMArr;

Но в наше время нужды в этом нет, начиная с Д4 есть динамические массивы.


Anatoly Podgoretsky   (2009-09-18 13:41:00) [19]

> Прима  (18.09.2009 13:35:08)  [8]

Работать с [0..0] идеологически неправильно, работай с [0..MaxInt]


Прима   (2009-09-18 13:35:00) [20]

Это понятно.
Я хочу для себя разобраться как работать с [0..0]

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

 var  P:Pointer;
begin
 GetMem(P,SizeOf(TElem)*2);
 Q.Q сопоставить с P как-то


Страницы:   1 2

Наверх

Титульная страница Поиск, карта сайта Написать письмо