Форум программистов
 

Восстановите пароль или Зарегистрируйтесь на форуме, о проблемах и с заказом рекламы пишите сюда - alarforum@yandex.ru, проверяйте папку спам!

Вернуться   Форум программистов > IT форум > Помощь студентам
Регистрация

Восстановить пароль
Повторная активизация e-mail

Купить рекламу на форуме - 42 тыс руб за месяц

Ответ
 
Опции темы Поиск в этой теме
Старый 03.05.2014, 22:53   #1
Fores
Новичок
Джуниор
 
Регистрация: 03.05.2014
Сообщений: 2
По умолчанию Рассортировать в дин.списке элементы и уравнять их кол-во.

Доброго времени суток, уважаемые форумчане! Прошу консультации по след.задаче:

Все нечетные числа записать в начало данных, четные – в конец данных. Повторяющиеся числа не писать. Уравнять количество четных и нечетных удалением последних значений в своей последовательности. Решить, используя дин.списки

Вся проблема в итоговом списке, точнее в его выводе. При компиляции в 80% случаев выдается след. ошибка:
Ошибка времени выполнения: Ссылка на объект не указывает на экземпляр объекта., в остальных случаях программа компилируется корректно. В чем причина?
Прилагаю следующий код:

Код:
const n=20;
type din=^rec;
rec=record
x:integer;
adr: din;
end;
var p,first,r: din;
mn:set of integer;
f1:file of integer;
i,b,k,buf,ch,nch:integer;
priz:boolean;
begin
assign(f1,'f1.pas');
rewrite(f1);
for i:=1 to n do begin
b:=random(30)+10;
write(f1,b);
end;
reset(f1);
while not eof(f1) do begin
new(p);
read(f1,p^.x);
write(p^.x:4);
first:=p;
for i:=2 to n do begin
new(p^.adr);
p:=p^.adr;
read(f1,p^.x);
write(p^.x:4);
end;
end;
writeln;
k:=n;
repeat
dec(k);
priz:=true;
p:=first;
for i:=1 to k do 
while p^.adr<>nil do begin
if (p^.x mod 2 = 0) and (p^.adr^.x mod 2 = 1) then begin
buf:=p^.x;
p^.x:=p^.adr^.x;
p^.adr^.x:=buf;
priz:=false;
end;
p:=p^.adr;
end;
until priz;
p:=first;
r:=p;
while p<>nil do begin
if not(p^.x in mn) then begin
write(p^.x:4);
mn:=mn+[p^.x];
if (p^.x mod 2 = 0) then inc(ch) else inc(nch);
p:=p^.adr;
end
else begin
r^.adr:=p^.adr;
dispose(p);
p:=r^.adr;
end;
end;
writeln(' Нечетных ', nch, ' Четных ', ch);
writeln;
if ch>nch then begin
p:=first;
r:=p;
for i:=1 to 2*nch do begin
write(p^.x:4);
p:=p^.adr;
end;
end
else begin
p:=first;
r:=p;
for i:=1 to ch do begin
write(p^.x:4);{Здесь выскакивает ошибка}
p:=p^.adr;
end;
for i:=ch+1 to nch do begin
r^.adr:=p^.adr;
dispose(p);
p:=r^.adr;
end;
for i:=nch+1 to nch+ch do begin
write(p^.x:4);{Здесь выскакивает ошибка}
p:=p^.adr;
end;
end;
end.


Заранее благодарю!

Последний раз редактировалось Stilet; 03.05.2014 в 23:45. Причина: Некорректное отображение
Fores вне форума Ответить с цитированием
Старый 04.05.2014, 13:36   #2
Sibedir
Тот ещё
Старожил
 
Аватар для Sibedir
 
Регистрация: 14.11.2007
Сообщений: 2,242
По умолчанию

Бегло.
Ошибка здесь
Цитата:
...
else begin
r^.adr:=p^.adr;
dispose(p);
p:=r^.adr;
end;
...
Предыдущий элемент продолжает хранить ссылку на уже удаленный из памяти дубликат.

Возможное решение: Пропускать добавление дубликатов уже на этапе формирования списка из файла.
Код:
  Reset(f1);
  while not eof(f1) do begin
    New(p);
    Read (f1, buf);
    p^.x := buf;
    Writeln (p^.x:4);
    first := p;
    mn := mn + [buf];
    for i := 2 to n do begin
      Read (f1, buf);
      if not (buf in mn) then begin
        New (p^.adr);
        p := p^.adr;
        p^.x := buf;
        Writeln (p^.x:4);
        mn := mn + [buf];
      end;
    end;
  end;

Последний раз редактировалось Sibedir; 04.05.2014 в 14:32.
Sibedir вне форума Ответить с цитированием
Старый 05.05.2014, 16:34   #3
Fores
Новичок
Джуниор
 
Регистрация: 03.05.2014
Сообщений: 2
По умолчанию

Цитата:
Сообщение от Sibedir Посмотреть сообщение
Бегло.
Ошибка здесь

Предыдущий элемент продолжает хранить ссылку на уже удаленный из памяти дубликат.
Ваше мнение оказалось верным, за что я Вам искренне благодарен!) Переделанная программа компилируется абсолютно верно.

Для заинтересованных выкладываю полностью рабочий код:

Код:
const n=20;
type din=^rec;
rec=record
x:integer;
adr:din;
end;
var p,first,r:din;
mn:set of integer;
f1:file of integer;
i,b,k,buf,ch,nch:integer;
priz:boolean;
begin
assign(f1,'f1.pas');
rewrite(f1);
for i:=1 to n do begin
b:=random(30)+10;
write(f1,b);
end;
Reset(f1);
  while not eof(f1) do begin
    New(p);
    Read (f1, buf);
    p^.x := buf;
    Write (p^.x:4);
    first := p;
    if (p^.x mod 2 = 0) then inc(ch) else inc(nch);
    mn := mn + [buf];
    for i := 2 to n do begin
      Read (f1, buf);
      if not (buf in mn) then begin
        New (p^.adr);
        p := p^.adr;
        p^.x := buf;
        Write (p^.x:4);
        if (p^.x mod 2 = 0) then inc(ch) else inc(nch);
        mn := mn + [buf];
      end;
    end;
end;
writeln;
k:=n;
repeat
dec(k);
priz:=true;
p:=first;
for i:=1 to k do 
while p^.adr<>nil do begin
if (p^.x mod 2 = 0) and (p^.adr^.x mod 2 = 1) then begin
buf:=p^.x;
p^.x:=p^.adr^.x;
p^.adr^.x:=buf;
priz:=false;
end;
p:=p^.adr;
end;
until priz;
writeln(' Нечетных ', nch, ' Четных ', ch);
if ch>nch then begin
p:=first;
r:=p;
for i:=1 to 2*nch do begin
write(p^.x:4);
p:=p^.adr;
end;
end
else begin
p:=first;
r:=p;
for i:=1 to ch do begin
write(p^.x:4);
p:=p^.adr;
end;
for i:=ch+1 to nch do begin
r^.adr:=p^.adr;
dispose(p);
p:=r^.adr;
end;
for i:=nch+1 to nch+ch do begin
write(p^.x:4);
p:=p^.adr;
end;
end;
end.
Проблема решена, тема закрыта)
Fores вне форума Ответить с цитированием
Ответ


Купить рекламу на форуме - 42 тыс руб за месяц



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
Дан указатель P1 на первый элемент непустого двусвязного списка Продублировать в списке все элементы с нечетными значениями S.I.D. Паскаль, Turbo Pascal, PascalABC.NET 0 23.01.2013 19:08
LISP, рекурсия, кол-во одинаковых эл. в списке mmx358 Помощь студентам 1 21.10.2012 23:15
Файлы и дин. переменные. Изменить с использованием дин. переменных. Маленыч Паскаль, Turbo Pascal, PascalABC.NET 4 07.06.2012 11:17
из дин. дека в дин. стек (Borland С++) mego4el Помощь студентам 1 07.07.2011 14:41
Найти кол-во её стобцов,все элементы которых различны. Delphi. Flashcherry Помощь студентам 1 21.03.2009 00:46