Отсортировать данные в файле - Pascal ABC

Узнай цену своей работы

Формулировка задачи:

В файле data.txt записаны числа, сколько их – неизвестно. Создать из него файл четных чисел и отсортировать их на диске.

Решение задачи: «Отсортировать данные в файле»

textual
Листинг программы
const CR: char = #13;
      LF: char = #10;
 
var F: file of char;
    Pos1, Pos2: longword;
    String1, String2: string;
    N1, N2: longint;
    Symbol: char;
    NoSwap: boolean;
    Error, StringCount, i: integer;
 
//процедура чтения строки из файла с текущей позиции файла
procedure ReadString(var s: string; var n: integer);
var c: char;
begin
  s := '';
  repeat
    read(F, c); //читаем символ из файла
    if not (c in [LF, CR]) then s := s + c //пишем в строку, если символ не LF или CR
  until c = LF; //читаем из файла до LF
  if not (s[1] in ['0'..'9', '-', '+']) then Error := 1;
  //эта проверка для совместимости с диалектами паскаля, в которых процедура val
  //игнорирует (пропускает) неправильное начало строки
  if Error = 0 then val(s, n, Error) //если начало строки верное, пытаемся строку преобразовать в число
end;
 
//процедура печати строки в файл с текущей позиции файла
procedure WriteString(s: string);
var i: integer;
begin
  for i := 1 to length(s) do write(F, s[i]);
  write(F, CR, LF)
end;
 
begin
  assign(F, 'file.txt');
  reset(f);
  //правим невидимое и неверное в конце файла и тестируем на нулевую длину
  while (FileSize(F) > 0) do
    begin
      Pos1 := FileSize(F) - 1; //переходим в конец файла
      seek(F, Pos1);
      read(F, Symbol); //читаем символ
      if not (Symbol in ['0'..'9']) //если последний символ не цифровой, усекаем файл
        then begin
          seek(F, Pos1);
          truncate(F);
        end
        else break
    end;
  write(F, CR, LF); //добавляем разделитель строк в конец файла
  if FileSize(F) = 2 //если файл пустой,
    then writeln('Файл не содержит чисел.') //то печатаем сообщение и сортировку не выполняем
    else begin //иначе сортируем файл
      //Пузырьковая сортировка
      Error := 0; //пока считаем, что ошибок нет
      repeat
        reset(F); //начало очередного прохода: позиция в файле = 0
        Pos1 := 0; //очередная позиция первого числа
        StringCount := 1; //счётчик строк = 1
        NoSwap := TRUE; //перестановок ещё не было
        ReadString(String2, N2); //читаем первую строку во второе число
        while (Error = 0) and not EOF(F) do //цикл очередного прохода сортировки
          begin
            N1 := N2; //переносим второе число в первое
            String1 := String2;
            Pos2 := FilePos(F); //запоминаем позицию второго числа
            inc(StringCount); //счётчик строок + 1
            ReadString(String2, N2); //читаем второе число
            if (Error = 0) and (N1 > N2) //если нет ошибок и первое число больше
              then begin //то меняем числа местами
                NoSwap := false; //был обмен
                seek(f, Pos1); //переходим на позицию первого числа
                WriteString(String2); //выводим в файл сначала второе число
                Pos1 := FilePos(F); //позиция очередного первого числа
                WriteString(String1); //затем выводим в файл первое число
                N2 := N1; //присваиваем второму числу первое
                string2 := String1
              end
              else Pos1 := Pos2 //иначе второе число становится очередным первым
          end;
      until (Error > 0) or NoSwap; //сортировать до тех пор, пока есть обмен
      {Если в файле есть ошибочные строки, печатаем сообщение}
      if Error = 0
        then writeln('Сортировка завершена.')
        else begin
          writeln('Сортировка не завершена, ошибка в строке ', StringCount, ':');
          writeln('"', string2, '"');
          for i := 1 to Error do write(' ');
          writeln('^')
        end
    end;
  close(F);
  write('Нажмите <Enter> для выхода из программы.');
  readln
end.

Объяснение кода листинга программы

  1. Переменная CR содержит символ перевода строки #13.
  2. Переменная LF содержит символ перевода строки #10.
  3. Переменная F представляет собой файловый объект, используемый для чтения и записи данных в файл.
  4. Переменные Pos1 и Pos2 представляют собой длинные слова, используемые для хранения текущих позиций чтения и записи в файле.
  5. Переменные String1 и String2 представляют собой строковые переменные, которые используются для чтения и записи данных в файл.
  6. Переменные N1 и N2 представляют собой длинные целые числа, которые используются для хранения числовых данных, прочитанных из файла.
  7. Переменная Symbol содержит символ, который был прочитан из файла последним.
  8. Переменная NoSwap представляет собой логическую переменную, которая используется для отслеживания того, были ли выполнены какие-либо обмены во время сортировки.
  9. Переменная Error представляет собой целочисленную переменную, которая используется для хранения количества ошибок, обнаруженных при чтении данных из файла.
  10. Переменная StringCount представляет собой целочисленную переменную, которая используется для отслеживания количества строк в файле.
  11. Вложенные списки не используются в данном коде.
  12. Процедура ReadString читает строку из файла и возвращает ее в переменной s. Если начало строки некорректно, то переменная s будет содержать ошибку.
  13. Процедура WriteString записывает строку в файл. Если строка некорректна, то в файл будет добавлен символ CR и символ LF.
  14. В основной части программы используется алгоритм сортировки пузырьком.
  15. Числа в файле сортируются путем обмена первых двух чисел.
  16. Если в файле есть ошибки, программа выводит сообщение об ошибке и номер строки.
  17. Программа завершается после сортировки всех чисел в файле или после вывода сообщения об ошибке.

ИИ поможет Вам:


  • решить любую задачу по программированию
  • объяснить код
  • расставить комментарии в коде
  • и т.д
Попробуйте бесплатно

Оцени полезность:

10   голосов , оценка 4.5 из 5
Похожие ответы