Помощь - Поиск - Пользователи - Календарь
Полная версия: Не получается вставить цикл.
Форум «Всё о Паскале» > Pascal, Object Pascal > Задачи
garry_m
Привет всем! Я недавно начал работать с Паскалем и у меня возникли некоторые вопросы... Вы не могли бы подсказать как правильно поступить?
Допустим есть такой код:

uses crt;
var
  x:integer;
  y:integer;
  z:integer;
begin
  clrscr;
      
    write('Vvedite X: ');
    readln(x);
    write('Vvedite Y: ');
    readln(y);
    write('Vvedite Z: ');
    readln(z);

    if(x=y) and (y=z) then writeln('X=0 Y=0 Z=0');
    if(x<y) and (x<z) then writeln('X=0',' Y=',y,' Z=',z);
    if(y<x) and (y<z) then writeln('X=',x,' Y=0 ','Z=',z);
    if(z<x) and (z<y) then writeln('X=',x,' Y=',y,' Z=0');

    write('Nazhmite Enter...');
    readln;
end.


Как сделать так, при вводе X,Y,Z не цифр, а СИМВОЛОВ программа не выкидывала меня в редактор с ошибкой "Invalid numeric format", а скажем выдавала сообщение типа ERROR и предлагала ввести ввести данные заново? Заранее спасибо!
volvo
Вот общий принцип (чтобы не было ошибок при неверном вводе):
var
  X: integer;
  ok: boolean;
begin
  repeat
    {$I-} { отключаем "вылет" из программы }
      write('enter X'); readln(X);
    {$I+}
    ok := (ioresult = 0); { и проверяем состояние ошибки }
    if not ok then writeln('error... try one more');
  until ok;
end.

Сможешь его применить для своей программы?
garry_m
Ну применить это у меня получилось, но только для переменной X. А вот когда я ввожу в Y некорректное значение (символы), он меня выкидывает с ошибкой. (Invalid numeric format)


uses crt;
var
  x:integer;
  y:integer;
  z:integer;
  ok:boolean;
begin
  clrscr;
     repeat
     {$I-}
     write('Vvedite X: '); readln(x);
     {$I+}
     ok:= (ioresult=0);
     if not ok then writeln('Error! Try again!');
     until ok;

     repeat
     {SI-}
     write('Vvedite Y: '); readln(y);
     {SI+}
     ok:= (ioresult=0);
     if not ok then writeln('Error! Try again!');
     until ok;

     repeat
     {$I-}
     write('Vvedite Z: '); readln(z);
     {$I+}
     ok:= (ioresult=0); {i prov sost oshibki}
     if not ok then writeln('Error! Try again!');
     until ok;

    if(x=y) and (y=z) then writeln('X=0 Y=0 Z=0');
    if(x<y) and (x<z) then writeln('X=0',' Y=',y,' Z=',z);
    if(y<x) and (y<z) then writeln('X=',x,' Y=0 ','Z=',z);
    if(z<x) and (z<y) then writeln('X=',x,' Y=',y,' Z=0');

    write('Nazhmite Enter...');
    readln;
end.
volvo
А если {SI-} поменять на {$I-} ? И с плюсом то же самое?
garry_m
Сорри! Подвела невнимательность! Пасиб большое! :-)
garry_m
Тут составил еще одну программку... никто не подскажет как вставить цикл? Т. е. требуется чтобы после того, как программа закончит все действия, задавался вопрос типа: "Хотите ли вы попробовать еще? (Y/N)". Соответственно, если "Y", то опять ввод данных по новой, а если "N", то выход в редактор. Сам пробовал - ничего не вышло...

Код:

uses crt;
  var
  N,k:integer;
  ok:boolean;
begin
  clrscr;

    repeat

    repeat
    {$I-}
  write('VVEDITE NOMER DNJA V GODU -> ');
  readln(k);
    {$I+}
    ok:=(ioresult=0);
    if not ok then writeln('* * * ERROR! WRONG INPUT! PLEASE TRY AGAIN! * * *');
    until ok;


   if(k>365) then writeln('NEVERNIJ VVOD! POVTORITE!');
    until(k>=0) and (k<=365);
    N:=k mod 7;
    case N of
  1:writeln ('PONEDELNIK');
  2:writeln ('VTORNIK');
  3:writeln ('SREDA');
  4:writeln ('CHETVERG');
  5:writeln ('PJATNICA');
  6:writeln ('SUBBOTA');
  7,0:writeln ('VOSKRESENJE');

end;
readln;
end.
volvo
garry_m, я немного подправил твою программку, она так будет немного проще:
1) проверка на правильность ввода данных производится в одном месте, один лишний цикл убираем...
2) результат операции К mod 7 не может быть равным 7, я убрал этот вариант
Ну, и добавил тот самый цикл, который ты просил...

uses crt;
var
  N,k:integer;
  ok:boolean;
  ans: char;
begin

clrscr;
repeat
  repeat
    {$I-}
    write('VVEDITE NOMER DNJA V GODU -> '); readln(k);
    {$I+}
    ok:=(ioresult=0) and (k <= 365) and (k > 0);
    if not ok then writeln('* * * ERROR! WRONG INPUT! PLEASE TRY AGAIN! * * *');
  until ok;

  N:=k mod 7;
  case N of
    1:writeln ('PONEDELNIK');
    2:writeln ('VTORNIK');
    3:writeln ('SREDA');
    4:writeln ('CHETVERG');
    5:writeln ('PJATNICA');
    6:writeln ('SUBBOTA');
    0:writeln ('VOSKRESENJE');
  end;
  writeln('do you want to repeat? (Y/N)');
  ans := readkey;
until UpCase(ans) = 'N';

end.
garry_m
volvo, все работает как надо! Кстати я только что этот цикл внедрил еще в одну программку! Спасибо огромное!
garry_m
Блин тут возникла проблема небольшая... программу-то я составил, но только она не выполняет поставленную задачу... Да и поправьте меня pls что я не так в программе сделал... Мне кажется я накосячил в самом начале программы.

ПОСТАВЛЕННАЯ ЗАДАЧА: Переставляя столбцы действительной матрицы размера M x N, упорядочить ее по невозрастанию элементов последней строки.

Сорри за небольшое отклонение от темы про цикл, т. к. данная задача на массивы.


КОД:
uses crt;
const
  {Razmernost matrici MxN}
  M=5;N=5;
type
  Tmat=array[1..N,1..M] of integer;
var
  mat,str:tmat; {Matrici nachalnije i konechnije}
  i:string; {Peremennaja podtverzdenija}
  schM,schN:integer; {Peremennije schetchika}
begin
  clrscr;
  {Zapolnenije matrici}
  write('Vi hotite zapolnit matricu vruchnuju ili avtomaticheski? (Y,N): ');
  readln(i);
  if (i='Y') or (i='y') then
    {Zapolnenije matrici vruchnuju}
    begin
      for schM:=1 to M do
        for schN:=1 to N do
          begin
            write('Vvedite element M=',schM,' N=',schN, ' ');{Zapolnenije elementa}
            readln(mat[schM,schN]);
          end;
    end
  else
    {Avtomaticheskoje zapolnenije matrici}
    begin
      for schM:=1 to M do
        begin
          for schN:=1 to N do
            mat[schM,schN]:=schM*schN;{Tablica umnozhenija}
        end;
    end;
  {Vivod nachalnoj matrici}
  writeln('Nachalnaja matrica ',M,'x',N,':');
  for schM:=1 to M do
    begin
      for schN:=1 to N do
        write(mat[schM,schN]:5);
        writeln('');


{Perestanovka strok}

write('Dlja vivoda konechnoj matrici nazhmite Enter...');
  readln;
  writeln('Konechnij rezultat:');
  for schM:=1 to M do
    for schN:=1 to N do
      str[M-schM+1,schN]:=mat[schM,schN];



  {Vivod konechnoj matrici}
  for schM:=1 to M do
    begin
      for schN:=1 to N do
        write(str[schM,schN]:5);
        writeln('');
    end;
  write('Dlja prodolzhenija nazhmite Enter...'); readln;

    end;

end.
volvo
garry_m, поставленная тобой (или тебе, неважно) задача решается так:
(см. также Пузырьковая сортировка, именно этот алгоритм применялся для сортировки столбцов, и Как задать матрицу, чтобы ... - это использовалось для самого описАния матрицы...)
uses crt;
const
  {Razmernost matrici MxN}
  m = 5; { columns }
  n = 5; { lines }

type
  TColumn = array[1 .. n] of integer;
  Tmat = array[1 .. m] of TColumn;
var
  mat: Tmat; {Matrici nachalnije i konechnije}
  ch: Char;  {Peremennaja podtverzdenija}
  j_m, i_m, i_n: integer;

  cnt: integer;
  T: TColumn;
begin
  clrscr;

  { Zapolnenije matrici }
  write('Vi hotite zapolnit matricu vruchnuju [Y] ili avtomaticheski [N]?: ');
  Ch := ReadKey; cnt := 0;

  writeln;
  for i_m:=1 to m do
    for i_n:=1 to n do

      if UpCase(Ch) = 'Y' then begin
        write('mat[',i_m:2,', ',i_n:2, '] = ');
        readln(mat[i_n][i_m]);
      end
      else
        mat[i_n][i_m] := i_m * i_n;


  {Vivod nachalnoj matrici}
  writeln('Nachalnaja matrica ',M,'x',N,':');
  for i_m:=1 to M do begin
    for i_n:=1 to N do
      write(mat[i_n][i_m]:5);
    writeln;
  end;


  {Perestanovka strok}
  write('Dlja vivoda konechnoj matrici nazhmite Enter...'); readln;


  writeln('Konechnij rezultat:');
  For i_m := 1 To m Do
    For j_m := m DownTo i_m + 1 Do
      If mat[Pred(j_m)][n] > mat[j_m][n] Then { < } Begin
        T := mat[j_m - 1]; mat[j_m - 1] := mat[j_m]; mat[j_m] := T
      End;


  {Vivod konechnoj matrici}
  for i_m:=1 to M do begin
    for i_n:=1 to N do
      write(mat[i_n][i_m]:5);
    writeln;
  end;

  write('Dlja prodolzhenija nazhmite Enter...'); readln;

end.


P.S. В следующий раз вопросы на другие темы задавай в новом топике...
garry_m
Странно... а почему в программе, которую ты написал начальная и конечная матрицы совпадают? (они абсолютно одинаковые)
volvo
А потому, что таблица умножения уже упорядочена по возрастанию blum.gif

А какие данные ты вводил? Вручную?
garry_m
И вручную и автоматически... так мне нужно еще вставить процедуру как должны переставляться элементы строки? Или ее нужно как-то по-другому заполнять?
Я что-то не догоняю... :-(
volvo
Приведи данные, которые ты вводил !!! Почему когда я прогоняю программу, все работает, а как только кто-то другой запускает - у них обязательно появляются баги? dry.gif

Для теста - попробуй, например, задать НЕ таблицу умножения, а вот это:
      else
        mat[i_n][i_m] := - i_m * i_n; { <--- Добавь минус }

, и убедись, что все работает ...
garry_m
Ну я вводил данные вручную...
Вводил числа 1,2,3,4,5, ... 25 по порядку...


1 2 3 4 5
6 7 8 9 10
11 12 13 14 15
16 17 18 19 20
21 22 23 24 25
volvo
garry_m, а как ты думаешь, числа, образующие последнюю строку (т.е. 21, 22, 23, 24, 25) не упорядочены по неубыванию?

Попробуй ввести от 25 до 1, и почувствуй разницу...
volvo
Стоп... Тебе нужно по невозрастанию... blink.gif Тогда там, где знак закомментирован, поменяй условие:
If mat[Pred(j_m)][n] < mat[j_m][n] Then ...
garry_m
Ну разница есть... :-)
Но задача стояла упорядочить по невозрастанию элементов последней строки...
Или я не правильно понял поставленную задачу?
garry_m
Отлично! Теперь все пучком! Пасиб!
Это текстовая версия — только основной контент. Для просмотра полной версии этой страницы, пожалуйста, нажмите сюда.