Дерево в паскале

Ответить
Horita
Сообщения: 14
Зарегистрирован: 06 окт 2008, 11:18

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

Ладно несуть, подскажите как удобнее всего задать в файле дерево и как потом его списать в память, чтобы больше к файлу не обращатся, а брать инфу о сыновьях.
Я хотела делать указателями, но хз как в файле задать удобно его :)
Хыиуду
Сообщения: 2442
Зарегистрирован: 06 мар 2005, 21:03
Откуда: Москва
Контактная информация:

Так же, как в базе данных - каждому узлу дать свой уникальный id, и ссылки на него в файле делать как указание id. А при считывании из файла в память уже брать реальные указатели на область памяти, в которой он лежит.
Искусство программирования - заставить компьютер делать все то, что вам делать лень.
Для "спасибо" есть кнопка "Спасибо" в виде звездочки внизу под ником автора поста.
Аватара пользователя
Naeel Maqsudov
Сообщения: 2570
Зарегистрирован: 20 фев 2004, 19:17
Откуда: Moscow, Russia
Контактная информация:

можно без ссылок (это же не граф в всего лишь дерево)
1.Адам
1.1.Авель
1.2.Каин
считывать в пямять можно рекурсивной процедурой

Еще одно текстовое представление деревьев - это скобки
(Адам(Авель,Каин(...))
Тоже рекурсивной процедурой можно загрузить это в память в виде дерева
Horita
Сообщения: 14
Зарегистрирован: 06 окт 2008, 11:18

Мне преподаватель дал пример программы по считыванию дерева в память. Я добавила в него функцмю разбиения строки на слова, для того чтобы разделить имя статьи и дату. Можете мне помочь дописать программу так чтобы она находила одинаковые статьи и проверяла на правильность дерево(т.е. более старая статья не могла быть выше более новой)

Дерево у меня задается так:
.Статья1 (12.2008)
..Источник1 (1.2008)
...Ссылка1 (1.2000)
....Аннотация1 (1.1990)
...Ссылка2 (2.1999)
....Аннотация2 (2.1991)
..Источник2 (2.2008)
.Статья2 (11.2008)
..Источник2 (2.2008)
...Ссылка5 (5.2001)
....Аннотация2 (2.1991)
...Ссылка6 (6.2005)
....Аннотация4 (4.1985)
..Источник5 (5.2006)
...Ссылка1 (1.2000)
....Аннотация6 (6.1970)
.....Первоисточник1 (4.1940)
......Первоисточник1 (1.1930)
Вот код:

Код: Выделить всё

Program TreeIO;
USES CRT;

TYPE
  ukaz=^uzel;
  uzel=record
         name: string;     {имя вершины}
         Date: STRING;     {Дата статьи}
         left,right: ukaz; {сыновья}
         fath: ukaz;       {отец в исходном дереве}
         urov: integer;    {уровень исходного дерева, начиная с 0}
         Flag: boolean;    {признак последнего сына}
       end;
Var
  result: STRING;
  t,kon,root,p: ukaz;
  i,k,m,Len: integer;
  S, R, D, D1: string;
  Fin,Fout: text;
  Delims: STRING;
function strtok(var s:string;delims:string):string;
{Функция разбивает строку s на слова, разделенные символами-разделителями,
указанными в строке delims. Функция возвращает первое найденное слово, при
этом из строки s удаляется начальная часть до следующего слова}
var res:string; state:byte; i:integer;
begin
  state:=1;
  res:='';
  if s='' then
  begin
    result:='';
    exit;
  end;
  while pos(s[state],delims)<>0 do
  begin
    inc(state);
    if state>length(s) then
    begin
      s:='';
      result:='';
      exit;
    end;
  end;
  while pos(s[state],delims)=0 do
  begin
     res:=res+s[state];
     inc(state);
     if state>length(s) then
     begin
       s:='';
       result:=res;
       exit;
     end;
  end;
  while pos(s[state],delims)<>0 do
  begin
    inc(state);
    if state>length(s) then
    begin
      s:='';
      result:=res;
      exit;
    end;
  end;
  delete(s,1,state-1);
  result:=res;
end;
Begin
  CLRSCR;
  BEGIN
    Assign(Fin,'tree.txt');
    Reset(Fin);
    New(root);
    ReadLn(Fin,S);
    root^.name:=S;
    root^.urov:=0;
    root^.Flag:=true; {признак последнего сына-для корня не обязательно}
    root^.fath:=nil;  {отец}
    m:=0;             {уровень вершины}
    t:=root;          {предыдущая вершина для следующей в файле}
    While not Eof(Fin) do
      begin
        ReadLn(Fin,S);
        k:=0;
        Len:=Length(S);
        While S[k+1]='.'
        do
          k:=k+1;   {k-уровень вершины, начиная с 0}
        R:=Copy(S,k+1,Len-k);         {имя вершины}
        New(kon);
        kon^.name:=R;
        kon^.left:=nil;
        kon^.right:=nil;
        kon^.urov:=k;
        if k>m then               {переход на следующий уровень}
          begin
            t^.left:=kon;
            kon^.fath:=t;
            kon^.Flag:=true;      {признак последнего сына}
          end
        else
          if k=m then             {тот же уровень}
            begin
              t^.right:=kon;
              kon^.fath:=t^.fath; {отец тот же, что у брата}
              t^.Flag:=false;     {снятие признака последнего сына}
              kon^.Flag:=true;    {признак последнего сына}
            end
          else                    {подъем по дереву на m-k уровней}
            begin
              p:=t;
              For i:=1 to m-k do
                p:=p^.fath;
              {p-предыдущая вершина того же уровня}
              kon^.fath:=p^.fath; {отец в исходном дереве тот же, что у брата}
              p^.right:=kon;
              p^.Flag:=false;     {снятие признака последнего сына}
              kon^.Flag:=true;    {признак последнего сына}
            end;
        m:=k;       {запомнили текущий уровень}
        t:=kon;     {для работы со следующей вершиной}
      end;          {конец While}
    Close(Fin);
  END;
End.
Только сильно не ругайте :)
Ответить