Работа со списком. Переносим первый элемент в начало списка
---- Исходный текст программы ----
Program Spiski1;
uses crt;
type PElem = ^TElem;
TElem = record {простейшая анкета}
GodRojden: Integer; {год рождения}
FIO: string[50]; {ФИО}
Next: PElem; {указатель на следующий элемент списка}
end;
var e1,e2: PElem; d1,Nacalo:TElem;
Function Pusto(PP: Pointer):Boolean;
begin
if PP=nil then
begin writeln('Список пустой. Жми Enter'); readln;
Pusto := true; textattr:= $07; clrscr;
end else Pusto:= false;
end;
procedure Control(Nac: TElem; Messa:string);{выводит на экран весь список}
var elem: PElem;
begin
writeln(' --------- ',Messa, ' --------------- ');
elem:= Nac.Next; {elem указывает на начальный элемент списка
(тот, который введен последним)}
if Pusto(elem) then halt(1); { выход в систему с кодом завершения = 1 (сигнал ошибки)}
Repeat
writeln ('Ф.И.О. = ',elem^.FIO);
writeln('Год рождения = ',elem^.GodRojden);
elem:= elem^.Next; {после выполнения elem содержит адрес следующего
элемента списка}
until elem = nil; {если elem=nil => дошли до конца списка}
writeln('Для продолжения жми Enter'); readln;
end;
procedure perenos(Nac: TElem);
var elem,elem2: Pelem;
begin
elem:= Nac.Next;
{elem содержит адрес начала списка (где содержится ПОСЛЕДНИЙ введенный
элемент)}
if Pusto(elem) then halt(1);
Repeat
elem2:= elem;
elem:= elem^.Next;{переходим на следующий элемент списка}
until elem^.next = nil; { после завершения
цикла elem^.next = nil. То есть elem указывает
на последний элемент списка (т е elem хранит адрес в памяти,
где хранятся данные (т е запись типа TElem)
последнего элемента этого списка). При этом elem2 указывает
на предпоследний элемент списка, который после переноса
последнего элемента станет последним, поэтому нужно
присвоить elem2^.next:= nil обозначив конец преобразованного списка}
elem2^.next:= nil;
{ Теперь нужно сделать чтобы поле Next этой записи указывало на
первую запись списка т е elem^.next:= Nacalo.Next
Далее нужно чтобы Nacalo.Next указывало на эту запись т е
Nacalo.Next:= elem;
}
elem^.next:= Nacalo.Next;
Nacalo.Next:= elem;
end;
begin textattr:= $1F; {Атрибуты текст экрана - синий фон, белые символы}
clrscr;
{ Началом списка считаем элемент, на который указывает Nacalo.Next
Здесь реализован список, в который новые элементы вставляются перед
начальным элементом
}
Nacalo.Next:= nil; {Подготовка к вставке элементов в список.
Последний элемент (т е наиболее удаленный от начала) своим указателем
.Next должен указывать на nil, т е хранить значение = nil}
Repeat
write('Введи ФИО -> '); readln(d1.FIO);
if d1.FIO = '' then break;
write('Введи год рождения -> '); readln(d1.GodRojden);
New(e1); {выделяем память для хранения данных нового элемента списка}
e1^ := d1; {копируем данные, введенные в запись d1 в этот новый элемент}
e1^.Next:= Nacalo.Next;
{указатель .Next вставляемого нового элемента должен указывать
на элемент, который до этого был началом списка}
Nacalo.Next:= e1; {указатель начала списка должен указывать на
вставленный новый элемент}
until false;
Control(Nacalo, 'КОНТРОЛЬ введенного списка');
perenos(Nacalo);
Control(Nacalo, 'КОНТРОЛЬ после переноса');
textattr:= $07; clrscr; {черный фон, серые буквы - стандартно}
end.