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

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

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

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

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

Ответ
 
Опции темы Поиск в этой теме
Старый 27.09.2009, 10:53   #1
KingOfNothing
Пользователь
 
Регистрация: 06.02.2009
Сообщений: 89
По умолчанию Delphi кольцевой список

Мне нужно сделать кольцевой список, я написал процедуры добавления в начало списка и удаление элемента по ключу. Но, блин, где-то ошибка - не могу найти. Помогите пожалуйста!!

Странно, что когда в дебагере смотрю функцию Add, то при выходе из нее список вроде бы правильный, а после выхода нарушается связность. В функции ремов может быть нету бага, просто из-за нарушения в Add, она тоже неправильно работает.

Сам список:
Код:
unit list;

interface

uses dysc;

type


  TListNode = class
      public
        constructor Create(e:disc);
        function Add(e:disc):TListNode;
        function Remove(e:disc):TListNode;
        function getElement: disc;
        function getNext: TListNode;
        function getPrev: TListNode;
      private
          next:TListNode;
          prev:TListNode;
          element:disc;
  end;



implementation

constructor TListNode.Create(e:disc);
begin
  element:= e;
  next:=self;
  prev:= self;
end;

function TListNode.getElement: disc;
begin
  getElement := element;
end;

function TListNode.getNext: TListNode;
begin
  getNExt := next;
end;

function TListNode.getPrev: TListNode;
begin
  getPRev := prev;
end;

function TListNode.Add(e:disc):TListNode;
var temp:TListNode;
begin
  temp:=TListNode.Create(e);
  temp.next := self;
  temp.prev := self.prev;
  self.prev := temp;
  if (self.next = self) then
      self.next := temp;
  Add:=temp;
end;

function TListNode.Remove(e:disc):TListNode;
var
  l:TListNode;
begin
  l := self;
  Remove := self;
  repeat
    if (l.element.KodDysc = e.KodDysc) then
        begin
          if (l = self) then
            Remove := l.next;
          l.prev.next := l.next;
          l.next.prev := l.prev;
          l.Free;
          break;
        end;
    l := l.next;
  until l=self;
end;


end.
Вызовы:
Код:
disc = record
    KodDysc: string[5];
    NazvDysc: string[80];
    KodCycl: integer;
    ObsDysCred: real;
    LabRob: boolean;
  end;

function View(l:TListNode):string;
var
  temp:TListNode;
  s:string;
begin
  temp := l;
  repeat
    s:= s + temp.getElement.KodDysc + #10#13;
    temp := temp.getNext;
  until temp<>l;
  View := s;
end;

procedure TForm1.Button1Click(Sender: TObject);
var
  s:tListNode;
  e:disc;
begin
e.KodDysc:='1';
s:=TListNode.Create(e);
e.KodDysc:='2';
s:= s.Add(e);
e.KodDysc:='3';
s:= s.Add(e);
e.KodDysc:='1';
s:= s.Remove(e);
Memo1.Text := View(s);
end;
Если вдруг захотите сказать мне спасибо - воспользуйтесь кнопкой "Добавить отзыв"
KingOfNothing вне форума Ответить с цитированием
Старый 27.09.2009, 11:33   #2
alexBlack
Участник клуба
 
Регистрация: 12.10.2007
Сообщений: 1,204
По умолчанию

Остальное не проверял, но как минимум нет

self.prev.next := temp

не забудьте проверить ссылку как Вы это сделали с self.next
alexBlack вне форума Ответить с цитированием
Старый 27.09.2009, 11:42   #3
KingOfNothing
Пользователь
 
Регистрация: 06.02.2009
Сообщений: 89
По умолчанию

Цитата:
Сообщение от alexBlack Посмотреть сообщение
Остальное не проверял, но как минимум нет

self.prev.next := temp

не забудьте проверить ссылку как Вы это сделали с self.next

self.prev.next := temp ? это в Add? кажется, self.prev.next == temp.next, если поставить его вот так:
Код:
function TListNode.Add(e:disc):TListNode;
var temp:TListNode;
begin
  temp:=TListNode.Create(e);
  temp.next := self;
  temp.prev := self.prev;
  self.prev := temp;
  if (self.next = self) then
      self.next := temp;
  self.prev.next := temp 
  Add:=temp;
end;
Не вижу в этом смысла, если я правильно вас понял
Если вдруг захотите сказать мне спасибо - воспользуйтесь кнопкой "Добавить отзыв"
KingOfNothing вне форума Ответить с цитированием
Старый 27.09.2009, 11:58   #4
alexBlack
Участник клуба
 
Регистрация: 12.10.2007
Сообщений: 1,204
По умолчанию

Код:
  temp:=TListNode.Create(e);
  temp.next := self;                     // вставили перед текущим
  temp.prev := self.prev;              // указатель на предыдущий
  temp.prev.next := temp;            // предыдущий теперь указывает на нас
//или, что тоже самое
//  self.prev.next = temp, т.к. self.prev мы еще не меняли
  self.prev = temp;                      // мы являемся предыдущим для self
Нарисуйте карандашом на бумаге стрелки, стирайте их по мере выполнения фрагмента и ставьте новые.

Это без проверки начального варианта, когда первый элемент ссылается сам на себя.
alexBlack вне форума Ответить с цитированием
Ответ


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



Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
КОЛЬЦЕВОЙ ОДНОСВЯЗНЫЙ СПИСОК __FIRST__ Помощь студентам 0 01.11.2008 17:16
Кольцевой список counter Общие вопросы C/C++ 4 20.10.2008 08:09
Кольцевой список blade288 Помощь студентам 3 02.12.2007 20:53