Версия для печати темы

Нажмите сюда для просмотра этой темы в обычном формате

Форум «Всё о Паскале» _ Задачи _ динамические структуры данных

Автор: compiler 19.05.2007 22:05

Добрый день, помогите разобраться с указателями..
необходимо.Компонентам массива целых присваиваются сдвинутые на 65 значения индекса, печатается массив целых. Переменной-указателю на символьный массив присваивается адрес массива целых. Снова распечатывается массив, но по адресам значений. Вместо последовательности чисел будет напечатана последовательность ASCII символов от А до z с пробелами.
собственно есть текст проги, но мне он не ясен помогите пожалуйста..
а вот текст..

Program ReInterpretation;	
Uses Crt;
Type
A = Array [0..99] of char;
Var
X : Array [0..49] of integer;
pA : ^A;
i : integer;
Begin
ClrScr;
for i := 0 to 49 do begin
X[i] := 65+i;
write(X[i], ' ');
End;

pA := @X;

writeln;

for i := 0 to 99 do
write(pA^[i],' ');

readln;
read;
End.

заранее благодарен...



Добавлено через 2 мин.
вроде все стало ясно... прошу прощение что побеспокоил..

Автор: compiler 19.05.2007 23:09

собственно задача из <<той же серии>>...


Uses
Crt;
Var
P : pointer;

Procedure Test(p: pointer);
Begin
p := @P; {Определение адреса локального параметра}
writeln ('', Seg(p^), ':', Ofs(p^));
End;

Begin
ClrScr;
Test(P); {Вызов процедуры}
writeln('', Seg(p^), ':', Ofs(p^));
readln;
read;
End.

ее я точно сам не пойму sad.gif


Автор: volvo 19.05.2007 23:13

Что именно здесь непонятно? Почему в процедуре печатается ненулевое значение, а в основной программе - нули?

Автор: compiler 19.05.2007 23:16

Цитата(volvo @ 19.05.2007 19:13) *
Что именно здесь непонятно? Почему в процедуре печатается ненулевое значение, а в основной программе - нули?
это тоже и где можна прочитать про адресацию подробнее(желательно на русском)

Автор: volvo 19.05.2007 23:24

Цитата
где можна прочитать про адресацию подробнее

Здесь:
http://www.klax.tula.ru/~zet/themes/pointers.html

Автор: compiler 20.05.2007 2:14

Цитата(volvo @ 19.05.2007 19:24) *
Здесь:
оттуда
const
р: ^real = NIL;
begin
if р = NIL then
new(p);
dispose(p);
p := NIL;
end.


не работает(illegal character "'р'" ($F0)) sad.gif почему?

Автор: volvo 20.05.2007 2:24

У тебя 2 символа p - в кириллице (в описании и в If ...)

Поменяй на латинские...

Автор: compiler 20.05.2007 2:26

Цитата(volvo @ 19.05.2007 22:24) *
Поменяй на латинские...
спасибо...
вечно попадаюсь на эту дурацкую ошибку...

Автор: compiler 20.05.2007 20:32

а вот еще одна задача оттуда...

program Primer1;
const
SizeOfReal = 6; {Длина переменной типа REAL}
N = 100; {Количество столбцов}
M = 200; {Количество строк}
var
i, j: integer;
PtrStr: array [1..N] of pointer;
s: real;
type
RealPoint = ^real;
{-----------------}
Function AddrR(i,j: word): RealPoint;
{По сегменту i и смещению j выдает адрес вещественной переменной}
begin
AddrR := ptr(seg(PtrStr[i]^), ofs(PtrStr[i]^)+(j-1)*SizeOfReal)
end; {AddrR}
{-----------------}
Function GetR(i,j: integer): real;
{Выдает значение вещественной переменной по сегменту i
и смещению j ее адреса}
begin
GetR := AddrR(i,j)^
end; {GetR}
{-----------------}
Procedure PutR(i,j: integer; x: real);
{Помещает в переменную, адрес которой имеет сегмент i
смещение j, вещественное значение x}
begin
AddrR(i,j)^ := x
end; {PutR}
{-----------------}

begin {Main}
for i := 1 to N do begin
GetMem (PtrStr[i], M*SizeOfReal);
for j := 1 to M do PutR(i, j, Random)
end;
s := 0;
for i := 1 to N do
for j := 1 to M do
s := s + GetR(i,j);
WriteLn(s / (N * M): 12:10);
end. {Main}

FPC -не компилит, TP-вылетает вовремя исполнения...

добавленно
FAR говорит что необходим параметр какой-то
еще если пытаться запустить из TP то не получится...

Автор: volvo 20.05.2007 20:38

Свят-свят-свят... Что с тобой? Как это "не компилит"? blink.gif

Function AddrR(i,j: word): RealPoint;
begin
AddrR := RealPoint(ptr(seg(PtrStr[i]^), ofs(PtrStr[i]^)+(j-1)*SizeOfReal))
end;

и все smile.gif

Автор: compiler 20.05.2007 20:43

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

Автор: volvo 20.05.2007 21:12

program Primer1;
const
SizeOfReal = 6; {Длина переменной типа REAL}
N = 100;
M = 200;
var
i, j: integer;
PtrStr: array [1..N] of pointer;
s: real;
type
RealPoint = ^real;
{-----------------}
Function AddrR(i,j: word): RealPoint;
// По индексу в массиве указателей i и индексу элемента внутри i-го массива
// выдает адрес вещественной переменной
begin
AddrR := RealPoint(
// "собираем" адрес из сегмента : смещения, где
ptr(
seg(PtrStr[i]^), // сегмент = сегменту области памяти, на которую
// указывает ptrstr[i]
ofs(PtrStr[i]^)+(j-1)*SizeOfReal // смещение = смещению этой же
// области памяти + количеству байт, предшествующих
// элементу с заданным индексом (j)
)
)
end; {AddrR}
{-----------------}
Function GetR(i,j: integer): real;
// Выдает значение вещественной переменной по индексу массива - контейнера
// и номеру элемента в этом массиве
begin
GetR := AddrR(i,j)^
// для того, чтобы получить значение самой переменной достаточно
// просто разыменовать указатель, поскольку он уже приведен к типу
// "указатель на Real" в функции
end; {GetR}
{-----------------}
Procedure PutR(i,j: integer; x: real);
// Помещает в позицию J массива-контейнера I значение X
begin
AddrR(i,j)^ := x
end; {PutR}
{-----------------}

begin {Main}

// Выделяем память для N массивов-контейнеров (каждый - на M элементов типа Real)
for i := 1 to N do begin
GetMem (PtrStr[i], M*SizeOfReal);
// и заполняем их случайными значениями...
for j := 1 to M do PutR(i, j, Random)
end;

// Ну, дальше я думаю все понятно?
s := 0;
for i := 1 to N do
for j := 1 to M do
s := s + GetR(i,j);
WriteLn(s / (N * M): 12:10);
end. {Main}

Автор: compiler 20.05.2007 21:31

спасибо, буду разбираться...

оффтоп но перед этим отдохну... погодка чудная

Автор: compiler 20.05.2007 23:08

еще вот вопрос по CSEG( Возвращает значение, хранящееся в регистре CS микропроцессора (в начале работы программы в регистре CS содержится сегмент начала кода программы). )...
что надо сделать в программе что б возращался не ноль?

Автор: volvo 20.05.2007 23:25

Ты компилируешь в FPC? Тогда ничего не поможет:

Цитата(rtl.pdf)
29.9.37 Cseg
Synopsis: Return code segment
Declaration: function Cseg : Word
Visibility: default
Description: CSeg returns the Code segment register. In Free Pascal, it returns always a zero, since Free Pascal is a 32 bit compiler.
Errors: None.

Автор: compiler 20.05.2007 23:29

спасибо...

Автор: compiler 22.05.2007 20:11

вот есть еще такая программка... по ней пару вопросов...

type
ar=array[0..100000] of longint; //большой массив
Var
j:^char;
i:integer;
a: ^ar; //указатель на наш вектор.
Begin
readln;
read;
new(a); //прыжок по использованию памяти..
for i:=200 to 300 do begin
(*j:=Addr(i);*) j:=@i; //если какая-то разница?
writeln(j^);
end;
readln;
read;
DISPOSE(a); //не замечаем обратного прыжка... почему?
readln;
read;
End.


заранее благодарен.

Автор: volvo 22.05.2007 20:38

Цитата
(*j:=Addr(i);*)	j:=@i;    //если какая-то разница?
Абсолютно никакой - Addr(X) и @X возвращают адрес объекта X... Вся разница - Addr это функция, а @ - оператор...

Цитата
//не замечаем обратного прыжка... почему?
Это ты о чем? Кстати, что ты думаешь будет делать твоя программа?

Автор: compiler 22.05.2007 21:25

Цитата(volvo @ 22.05.2007 16:38) *
Это ты о чем?

о виртуальной памяти... при создании массива ее использование возрастает почти в 3 раза, но при обратном действии ничего не происходит...

Цитата(volvo @ 22.05.2007 16:38) *
Кстати, что ты думаешь будет делать твоя программа?
печатать символы и пищеть :) (код 7)..

Автор: volvo 22.05.2007 21:32

Цитата
о виртуальной памяти...
А что, твоя программа сама управляет виртуальной памятью? Вообще-то этим должна заниматься OC, вот когда она решит освободить память, тогда и уменьшится размер...

Автор: compiler 22.05.2007 21:38

Цитата(volvo @ 22.05.2007 17:32) *
А что, твоя программа сама управляет виртуальной памятью?
просто надеялся что пишу DISPOSE не зря...

Цитата(volvo @ 22.05.2007 17:32) *
Вообще-то этим должна заниматься OC, вот когда она решит освободить память, тогда и уменьшится размер...
а как можно прогнозировать время ее решения?

Автор: compiler 22.05.2007 22:04

и еще пару вопросов... по GETMEM (Р, SIZE), в чем в каких единицах задается SIZE и какие пороги у этого числа(максимум/минимум)?

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

добавленно
и последний вопрос на сегодня..

Var 
l:longint;
Begin
readln;
read;
l:=MAXAVAIL();
writeln(l);
readln;
read;
End.

где ошибка?

Автор: volvo 22.05.2007 22:23

Ты все время путаешь TP и FPC... Что для FPC (под Win32, я имею в виду) значит "существующая свободная память"? Физически свободная? Виртуальная?

Цитата
в чем в каких единицах задается SIZE
В байтах...
Цитата
какие пороги у этого числа
0 .. maxlongint

Автор: compiler 24.05.2007 21:21

Цитата(volvo @ 22.05.2007 18:23) *
Ты все время путаешь TP и FPC...

так получается... компилятор FPC, а литература в основном по TP ибо по FPC на русском я ничего не находил...

Цитата(volvo @ 22.05.2007 18:23) *
Что для FPC (под Win32, я имею в виду) значит "существующая свободная память"? Физически свободная? Виртуальная?
наверное сколько есть места в файле на винте , который именуется - Виртуальная память..

Автор: compiler 25.05.2007 22:14

и еще вопрос: в чем разница процедур NEW-DISPOSE и GETMEM-FREEMEM ?