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

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

Форум «Всё о Паскале» _ Задачи _ Бинарное дерево для работы с записями

Автор: Рэнэ 10.06.2007 9:08

Условие:
Автоматезированная инфомационная система система на железнодорожном вокзале содержит сведения от отправлении поездов дальнего следования. Данные в информационной системе организованы в виде двоичного дерева.
Для каждого поезда указывают:
1)номер поезда
2)Станцию назначения
3)Время отправления
Написать программу которая:
1) обеспечивает первоначальный ввод данных в информационную систему и формирование двоичного дерева.
2) Производит вывод всего дерева (и как это сделать?)
3) Вводит название станции назначения и выводит данные обо всех поездах, следующих до этой станции.
Программа должна обеспечивать диалог с помощью меню и контроль ошибок при вводе (аналогично 2, ну по крайней мере относительно контроля ошибок) blum.gif

Ну первый пункт он у меня вроде как выполняет и по станции сортирует, только вот когда речь заходит о нескольких поездах идуших до одной станции, вместо того чтобы вывести их всех, он выводит только один mega_chok.gif blum.gif И как же с этим быть?

Цитата
Program Derevo;
Uses Crt;
Type
St12 = string[12];
Pstruct = ^Struct;
Struct = Record
Nz : 57..90;
Stancia : St12;
Vremia : integer;
Left, Right : Pstruct;
end;
Const c : array[1..7] of String = ('Сведенья о поездах',
'ЪДДДДДДДВДДДДДДДДДДДДДВДДДДДДДДДДДДДї',
'і Номер і Станция і Время і',
'і поезда і назначения і отправления і',
& #39;ГДДДДДДДДЕДДДДДДДДДДДДДЕДДДДДДДДДДДДДґ
',
& #39;ГДДДДДДДДЕДДДДДДДДДДДДДЕДДДДДДДДДДДДДґ
',
& #39;АДДДДДДДДБДДДДДДДДДДДДДБДДДДДДДДДДДДДЩ
');

Var Tree : Pstruct;
F2, F1 :TEXT;

{-------Вывод данных одной строки таблицы----------}
Procedure P(Z:STRUCT);
Begin
Writeln(F1,#179, Z.Nz:5,#179:4,' ',Z.Stancia,#179:13-length(Z.Stancia),' ', Z.Vremia:5,#179:8,' ');
Writeln(#179, Z.Nz:5,#179:4,' ',Z.Stancia,#179:13-length(Z.Stancia),' ', Z.Vremia:5,#179:8,' ');
end;
{-------------Вывод шапки таблицы----------}
Procedure Shapka;
Var
i : Byte;
Begin
For i := 1 to 5 do
Writeln (C[i]);
End;
{-------------Удаление пробелов в начале и в конце строки----------}
Function Filtr (Str:St12):St12;
var
i,j,l:integer;
Begin
l:=length(Str);
For i:=1 to l do
if Str[i]<>' ' then
For j:=l downto i do
If Str[j] <> ' ' then
begin
Filtr:=copy (Str,i,j-i+1);
Exit
End;
Filtr:='';
end;
{-------------Включение нового элимента в дерево----------}
Procedure Form (Var TR:Pstruct; z:struct);
Begin
If TR = Nil Then
Begin new(TR);
TR^ :=Z;
End
Else
If z.Stancia < TR^.Stancia Then Form(TR^.Left,z)
Else
Form(TR^.Right,z);
End;
{-------------Ввод всех записей в дерево----------}
Procedure Vvod (NF: String);
Var
z: Struct;
b: Char;
Begin
Assign(F2, NF);
Reset (F2);
Writeln (F1,'Заполнение дерева новыми записями');
Shapka;
While not Seekeof(F2) DO
With z do
Begin
Readln(F2,Nz,b,Stancia,b,Vremia);
Stancia:=Filtr(Stancia);
Left :=Nil;
Right:=Nil;
P(z);
Form(Tree,z)
End;
Close(F2);
End;
{-------Обход дерева для вывода сортировочных данных дерева----------}
Procedure Sort(TR:Pstruct);
Begin
If TR<>Nil Then
Begin
Sort(TR^.Left);
P(TR^);
Sort(TR^.Right);
End;
End;
{-------Поиск по дереву----------}
Procedure Poisk_TR (TR: Pstruct; TFM : St12);
Begin
While TR<>Nil do
If TFM = TR^.Stancia Then
Begin
P(TR^);
Exit;
End
Else
If TFM < TR^.Stancia Then
TR:=TR^.Left
Else
TR:= TR^.Right;
Writeln (F1,'Станция введена не верно');
End;
{-------Поиск по дереву по заданному значению станции----------}
Procedure Poisk;
Var
TStancia : St12;
Begin
Assign(F2,'c:\TRPOI.DAT');
Reset (F2);
While not Seekeof(F2) do
Begin
Readln (F2,TStancia);
TStancia := Filtr (TStancia);
If TStancia = '' Then
Begin
Writeln(F1,'Нет станции для поиска');
Continue
End;
Writeln(F1,'Поиск',TStancia);
Poisk_TR(Tree,TStancia);
End;
End;
{-------Основная программа----------}
Begin
Clrscr;
Assign(F1,'c:\TR.Res');
Rewrite(F1);
Writeln(F1,'Создание дерева:');
Tree := Nil;
Vvod('c:\TR.DAT');
Writeln (F1,'Сортировка деревом:');
Shapka;
Sort(Tree);
Readln;
Poisk;
Close(F1);
end.

Автор: volvo 10.06.2007 12:30

Цитата
когда речь заходит о нескольких поездах идуших до одной станции, вместо того чтобы вывести их всех, он выводит только один
Потому, что сама просила (Exit после первой же найденной записи)...

{-------Поиск по дереву----------}
Procedure Poisk_TR (TR: Pstruct; TFM : St12);
var count: integer;
Begin
count := 0;
While TR<>Nil do Begin
If TFM = TR^.Stancia Then Begin
P(TR^); Inc(count);
end;

If TFM < TR^.Stancia Then TR:=TR^.Left
Else TR:= TR^.Right;

End;

if count = 0 then Writeln (F1,'Станция введена не верно');
End;

Вот так, если я не ошибаюсь, будет искать все поезда до заданной станции...

Автор: Гость 10.06.2007 17:26

Спасибо, теперь все заработало... give_rose.gif

Вот мне такой же поиск надо сделать для Номера поезда, я так понимаю что процедура "поиска по заданному значению " аналогична, той что у меня есть, но и в Procedure Poisk_TR тоже нужно добавить записи по параметру Nz... вот тут и возникает такая несостыковка как (Несоответствие типов)... что мне с этим делать?

Кстати не подскажите как мне здесь произвести вывод бинарного дерева...? а то я находила примеры, но соотнести их с текстом прграммы пока не смогла... wacko.gif

Автор: -Рэнэ- 10.06.2007 17:29


Цитата(Гость @ 10.06.2007 13:26) *

Спасибо, теперь все заработало... give_rose.gif

Вот мне такой же поиск надо сделать для Номера поезда, я так понимаю что процедура "поиска по заданному значению " аналогична, той что у меня есть, но и в Procedure Poisk_TR тоже нужно добавить записи по параметру Nz... вот тут и возникает такая несостыковка как (Несоответствие типов)... что мне с этим делать?

Кстати не подскажите как мне здесь произвести вывод бинарного дерева...? а то я находила примеры, но соотнести их с текстом прграммы пока не смогла... wacko.gif


Автор: volvo 10.06.2007 17:33

Цитата
вот тут и возникает такая несостыковка как (Несоответствие типов)... что мне с этим делать?
Можно посмотреть, как ты пыталась сделать (приведи код измененной процедуры, в котором возникает такая ошибка)?

Автор: Рэнэ 10.06.2007 17:37

Ой совсем запуталась с этими сообщениями...

А вообще я просто пыталась написать такое:
If TFM = TR^.Nz Then Begin

(просто заменяла Stancia на Nz)
Видимо зря norespect.gif

Автор: volvo 10.06.2007 17:56

Цитата
А вообще я просто пыталась написать такое:
А вот этого делать нельзя... Целое число и строка - несовместимы... Делай еще одну процедуру:
Procedure Poisk_TR_num(TR: Pstruct; search_num: integer);
Begin
if TR <> nil Then Begin
If search_num = TR^.Nz Then P(TR^);

Poisk_TR_num(TR^.Left, search_num);
Poisk_TR_num(TR^.Right, search_num);
End;
End;

(поиск по всему дереву, потому что у тебя Nz - не ключевое поле...)

Автор: Рэнэ 10.06.2007 18:21

Из-за этой несовместимости и Поиск мой неверен, что тут нужно поменять? blum.gif

Цитата
Procedure Poisk2;
Var
TNz : St12;
Begin
Assign(F2,'c:\TRPOISK.DAT');
Reset (F2);
While not Seekeof(F2) do
Begin
Readln (F2,TNz );
TNz := Filtr (TNz);
If TNz = '' Then
Begin
Writeln(F1,'Net NOMERA POEZDA dla poiska');
Continue
End;
Writeln(F1,'Poisk ',TNz);
Poisk_TR_num(Tree,TNz);
End;
End;

Автор: Рэнэ 11.06.2007 18:06

Вывела бинарное дерево, вроде как похоже на правду, хотя я и не уверена blum.gif

Цитата
procedure PrintTree(t:Pstruct; h:integer);
var
i:integer;
begin
if t<>nil then
begin
PrintTree(t^.Left,h+1);
for i:=1 to h do write(' ');
WriteLn (t^.Nz,' ',t^.Stancia,' ',t^.Vremia);
PrintTree(t^.right,h+1);
end;
end;


Автор: Рэнэ 12.06.2007 14:11

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

И еще, как мне во второй поиск поставит это пресловутое 'Номер поезда введен не верно' ? give_rose.gif give_rose.gif give_rose.gif

Только это и осталось сделать mega_chok.gif

Цитата
{-------Поиск по дереву----------}
Procedure Poisk_TR (TR: Pstruct; TFM : St12);
var count: integer;
Begin
count := 0;
While TR<>Nil do
Begin
If TFM = TR^.Stancia Then
Begin
P(TR^);
Inc(count);
end;
If TFM < TR^.Stancia Then
TR:=TR^.Left
Else
TR:= TR^.Right;
End;
if count = 0 then
Writeln (F1,'Станция введена не верно');
Writeln ('Станция введена не верно');
End;

Цитата
{-------Второй поиск по дереву ----------}
Procedure Poisk_TR_num(TR: Pstruct; search_num: integer);
Begin
If TR <> nil Then
Begin
If search_num = TR^.Nz Then
P(TR^);
Poisk_TR_num(TR^.Left, search_num);
Poisk_TR_num(TR^.Right, search_num);
end;
End;

Автор: volvo 12.06.2007 14:29

if count = 0 then BEGIN { <--- Не забыла, что у тебя несколько операторов? }
Writeln (F1,'Станция введена не верно');
Writeln ('Станция введена не верно');
END; { <--- }


Цитата
как мне во второй поиск поставит это пресловутое 'Номер поезда введен не верно'


Var count_trains: integer; { Глобальная переменная }

Procedure Poisk_TR_num(TR: Pstruct; search_num: integer);
Begin
If TR <> nil Then Begin
If search_num = TR^.Nz Then Begin
P(TR^); Inc(count_trains);
End;
Poisk_TR_num(TR^.Left, search_num);
Poisk_TR_num(TR^.Right, search_num);
end;
End;


Перед вызовом Poisk_TR_num обнулять count_trains, а после возврата - проверять значение, и если оно = 0, то печатать сообщение...

Автор: Рэнэ 12.06.2007 19:37

Спасибо, теперь все работает нормально give_rose.gif good.gif