IPB
ЛогинПароль:

> ВНИМАНИЕ!

Прежде чем задать вопрос, смотрите FAQ.
Рекомендуем загрузить DRKB.

 
 Ответить  Открыть новую тему 
> Задача на рекурсию
antonioSP
сообщение 26.03.2006 14:54
Сообщение #1


Новичок
*

Группа: Пользователи
Сообщений: 16
Пол: Мужской

Репутация: -  0  +


Помогите решить задачу на рекурсию. В строке записанно выражение следующего вида:
<формула>::=<индетификатор>/(<формула><знак><формула>)
<знак>::= +/-/*
<индетификатор>::=<буква>/<буква><цифра>
<цифра>::=0/1/2/3/4/5/6/7/8/9
Проверить правильность сочетания.
Не получается процедура проверки на истинность, может кто подскажет как это сделать. Вот мои наработки процедура ввода (скорее всего и там косяк есть).
Код

procedure TForm1.Button1Click(Sender: TObject);
type
tl=(form,buk,sko,skz,znak,cif);
var a:string[20];
i:integer;
begin
i:=1;
function read(var s:string; var i:integer):tl;
begin
  if s[i] in ['A'..'z'] then result:=buk;
  if s[i] in ['0'..'9'] then
   result:=cif
  else
   case s[i] of
    '+':result:=znak;
    '-':result:=znak;
    '(':result:=sko;
    ')':result:=skz;
    else
     result:=err;
   end;
   i:=i+1;
end;
end;
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
hardcase
сообщение 26.03.2006 16:50
Сообщение #2


code warrior
****

Группа: Пользователи
Сообщений: 484
Пол: Мужской
Реальное имя: Славен

Репутация: -  8  +


Честно говоря, у тебя написано не очень правильно....
Попробуй вот этот вариант:
function Test(const S: string): boolean;
  var Cur: integer; // индекс следующего символа
      Len: integer; // длина строки входной
      Look: char; // текущий символ

// вернёт истину, если достигнут конец строки
      function LineEnd: boolean;
        begin
          Result:=Cur > Len;
        end;

// вернёт истину, если символ удалось считать
      function GetChar: boolean;
        begin
          if Cur <= Len then begin
              Look:=S[Cur];
              inc(Cur);
              Result:=true
          end else begin
              Look:=#0;
              Result:=false
          end
        end;

// проверяет, является ли символ + - или *
      function IsOperator(C: Char): boolean;
        begin
          Result:=C in ['+','*','-']
        end;

// является ли символ буквой (латиница)
      function IsAlpha(C: char): boolean;
        begin
          Result:=UpCase( С ) in ['A'..'Z']
        end;

// является ли цифрой (арабской 

      function IsDigit(C: char): boolean;
        begin
          Result:=C in ['0'..'9']
        end;

// <идентификатор>
      function IsIdentifer: boolean;
        begin
          if IsAlpha(Look) then begin // <индетификатор>::=<буква>
             while GetChar do //<индетификатор>::=<буква><цифра>
                 if not (IsAlpha(Look) or IsDigit(Look)) then Break;
             Result:=true
          end else Result:=false
        end;

// <формула>
      function IsFormula: boolean;
        begin
          if IsIdentifer then begin // <формула>::=<идентификатор>
              Result:=true
          end else if Look = '(' then begin // <формула>:=(<формула><знак><формула>)
              GetChar; // пропускаем '('
              if IsFormula then
                  if IsOperator(Look) then begin
                      GetChar; //пропускаем знак
                      if IsFormula then
                          if Look = ')' then begin
                              GetChar; // пропускаем ')'
                              Result:=true;
                              Exit;
                          end;
                  end;
              Result:=false;
          end else Result:=false;
        end;

// инициализирует переменные и закачивает первый символ
      procedure Init;
        begin
          Cur:=1;
          Len:=Length(S);
          GetChar;
        end;

  begin
    Init;
// условие правильности: формула обнаружена и достигнут конец строки
    Result:=IsFormula and LineEnd;
  end;

распознаёт выражения типа:
Цитата
a
(aaa1+bbb1)
(x*(a+b))


--------------------
ИзВ ин ИтЕ зА нЕ рОв НЫй П оч ЕРк
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
antonioSP
сообщение 26.03.2006 20:29
Сообщение #3


Новичок
*

Группа: Пользователи
Сообщений: 16
Пол: Мужской

Репутация: -  0  +


Я вот тут написал свой вариант, он понимает вроде всё кроме выражения такого типа:4 или (4+6) , пишет что good, а должно быть bad, не могу правильно определить идентификатор. Подскажите плз, что и на что надо исправить в программе.

Код

procedure TForm1.Button1Click(Sender: TObject);
type
spisok=(ind, cif, znak, sko, skz);
var
res:spisok;
str:string;
i:byte;

function chit(var str:string; var i:byte):spisok;
begin
i:=i+1;
  if str[i] in ['A'..'z'] then result:=ind;
  if str[i] in ['0'..'9'] then result:=cif;
  case str[i] of
  '+':result:=znak;
  '-':result:=znak;
  '*':result:=znak;
  '(':result:=sko;
  ')':result:=skz
  else
     edit2.text:='bad';
  end;
end;

// вероятно косяк здесь
procedure indetif(var str:string; var i:byte);
begin
if str[i+1] in ['0'..'9'] then i:=i+1
end;

procedure proverka(var str:string; var i:byte; var res:spisok);
begin
res:=chit(str,i);
if res=ind then
  if i<>length(str) then indetif(str,i)
  else exit;
if res=sko then
  begin
  proverka(str,i,res);
  res:=chit(str,i);
  if res=znak then
   begin
   proverka(str,i,res);
   res:=chit(str,i);
   if res=skz then exit
    else edit2.Text:='bad';
   end
   else edit2.Text:='bad';
  end
else edit2.Text:='bad';
end;

begin
str:=edit1.text;
i:=0;
proverka(str,i,res);
if i=length(str) then edit2.Text:='good';
end;
end.  


Сообщение отредактировано: antonioSP - 26.03.2006 21:39
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 
hardcase
сообщение 26.03.2006 20:53
Сообщение #4


code warrior
****

Группа: Пользователи
Сообщений: 484
Пол: Мужской
Реальное имя: Славен

Репутация: -  8  +


в коде разобраться - нереально :-))
погоняй лучше мой вариант


--------------------
ИзВ ин ИтЕ зА нЕ рОв НЫй П оч ЕРк
 Оффлайн  Профиль  PM 
 К началу страницы 
+ Ответить 

 Ответить  Открыть новую тему 
1 чел. читают эту тему (гостей: 1, скрытых пользователей: 0)
Пользователей: 0

 

- Текстовая версия 29.07.2025 9:24
Хостинг предоставлен компанией "Веб Сервис Центр" при поддержке компании "ДокЛаб"