Связь между двумя программами с использованием файла - PullRequest
1 голос
/ 06 мая 2011

Я хочу, чтобы две отдельные программы, написанные на Паскале, общались между собой, используя дополнительный текстовый файл.Он хорошо работает для первых 2-3 сообщений, но затем выдает ошибку времени выполнения в sender.pas или receive.pas. Вы знаете, где моя ошибка, или у вас есть какие-либо предложения?.pas

var
 f : text;
 s : string;
begin
 {I-}
 Assign(f,'main.in');
 while true do
  begin

   reset(f);
   while IOResult<>0 do      //
    begin                    // Wait until the file
     close(f);               //       is closed by sender
     reset(f);               //
    end;                     //

   if eof(f) then
    close(f)
   else
    begin
     readln(f,s);
     close(f);
     rewrite(f);
     close(f);
     writeln(s);
    end;
  end;
 {I+}
end.

вторая программа sender.pas

var
 f : text;
 s : string;
begin
 {I-}
 Assign(f,'main.in');
 while true do
  begin
   readln(s);

   rewrite(f);                //
   while IOResult<>0 do       //
    begin                     // Wait until the file
     close(f);                //        is closed by receiver
     rewrite(f);              //
    end;                      //

   writeln(f,s);
   close(f);
  end;
 {I+}
end.

Ответы [ 2 ]

2 голосов
/ 08 мая 2011

Некоторые вещи, которые я заметил:

  1. Если перезапись не удалась, afaik файл не был открыт, и вам не нужно его закрывать? Закрытие неоткрытого файла может привести к ошибкам во время выполнения (хотя я предполагаю, что assign будет инициализировать его безопасно)
  2. в зависимости от того, как вы их используете, может быть в логике. А именно, что после закрытия файл напрямую готов к открытию другими приложениями. Обычно закрытые файловые дескрипторы задерживаются от нескольких сотен миллисекунд до нескольких секунд (в зависимости от состояния файловой системы). Это может вызвать проблемы с голодом в таких схемах. (хотя он будет работать в обычном режиме, который не задерживается, по крайней мере, не так много)
  3. Сбой чтения, если файл не существует.
  4. Я предполагаю, что {I -} / {I +} - опечатка и что ваш исходный код действительно читает {$ I-} и {$ I +} (обратите внимание на доллар?)
  5. В версиях для Windows на Паскале доступ только для чтения не всегда блокируется. Поместите filemode: = 2 в качестве первой строки во всем.

Какой это компилятор? Delphi, бесплатный Паскаль? Какая версия?

Мой новый (Free Pascal) код получателя становится:

uses sysutils;
var
 f : text;
 s : string;
begin
 filemode := 2; // read-only
 {$I-}
 Assign(f,'main.in');
 while true do
  begin
   reset(f);
   while IOResult<>0 do      //
    begin                    // Wait until the file
     close(f);               //       is closed by sender
     sleep(1000);
     reset(f);
    end;
   if eof(f) then
    begin
      close(f);
      sleep(1000);
    end
   else
    begin
     readln(f,s);
     close(f);
     rewrite(f);
     close(f);
     writeln(s);
    end;
  end;
 {$I+}
end.

Новый код отправителя:

uses sysutils;
var
 f : text;
 s : string;
begin
 filemode := 2; // read-only
 {$I-}
 Assign(f,'main.in');
 while true do
  begin
   reset(f);
   while IOResult<>0 do      //
    begin                    // Wait until the file
     close(f);               //       is closed by sender
     sleep(1000);
     reset(f);
    end;
   if eof(f) then
    begin
      close(f);
      sleep(1000);
    end
   else
    begin
     readln(f,s);
     close(f);
     rewrite(f);
     close(f);
     writeln(s);
    end;
  end;
 {$I+}
end.
1 голос
/ 06 мая 2011

Пара вещей: убедитесь, что вы проверяете IOResult после каждой файловой операции, а не просто перезаписываете / сбрасываете - не вызывайте close, если сбрасываете / перезаписывают неудачу - и вы, вероятно, хотите что-то вроде Sleep (250) в этих повторных попытках петли.

...