pascalabcnet/bin/Lib/LightPT.pas
2022-07-01 12:35:15 +03:00

394 lines
9.8 KiB
ObjectPascal
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

/// Модуль LightPT автоматической легковесной проверки заданий
unit LightPT;
uses __RedirectIOMode;
type
PTException = class(Exception) end;
InputCountException = class(PTException)
Count,n: integer;
constructor (Count,n: integer);
begin
Self.Count := Count;
Self.n := n;
end;
end;
InputCount2Exception = class(InputCountException)
end;
InputTypeException = class(PTException)
n: integer;
ExpectedType, InputType: string;
constructor (n: integer; ExpectedType, InputType: string);
begin
Self.n := n;
Self.ExpectedType := ExpectedType;
Self.InputType := InputType;
end;
end;
TaskStatus = (Completed,NotCompleted,AbsentTask);
var
OutputString := new StringBuilder;
OutputList := new List<object>;
InputList := new List<object>;
var Cur := 0;
function TaskName := ExtractFileName(System.Environment.GetCommandLineArgs[0]).Replace('.exe','');
procedure WriteInfoToDatabase(name: string; result: TaskStatus);
begin
try
System.IO.File.AppendAllText('db.txt',$'{name} {dateTime.Now.ToString(''u'')} {Result.ToString}'+#10);
except
on e: Exception do
Print(e.Message);
end;
end;
procedure CheckInputCount(n: integer);
begin
if InputList.Count < n then
raise new InputCountException(InputList.Count,n)
end;
procedure CheckInput2Count(i: integer);
begin
if InputList.Count <= i then
raise new InputCount2Exception(InputList.Count,i+1)
end;
function IsInt(i: integer) := InputList[i] is integer;
function IsRe(i: integer) := InputList[i] is real;
function IsStr(i: integer) := InputList[i] is string;
function IsBoo(i: integer) := InputList[i] is boolean;
function IsChr(i: integer) := InputList[i] is char;
function Int(i: integer): integer;
begin
CheckInput2Count(i);
if not IsInt(i) then
raise new InputTypeException(i+1,'integer',TypeName(InputList[i]));
Result := integer(InputList[i]);
end;
function Re(i: integer): real;
begin
CheckInput2Count(i);
if not IsRe(i) then
raise new InputTypeException(i+1,'real',TypeName(InputList[i]));
Result := real(InputList[i]);
end;
function Str(i: integer): string;
begin
CheckInput2Count(i);
if not IsStr(i) then
raise new InputTypeException(i+1,'string',TypeName(InputList[i]));
Result := string(InputList[i]);
end;
function Boo(i: integer): boolean;
begin
CheckInput2Count(i);
if not IsBoo(i) then
raise new InputTypeException(i+1,'boolean',TypeName(InputList[i]));
Result := boolean(InputList[i]);
end;
function Chr(i: integer): char;
begin
CheckInput2Count(i);
if not IsChr(i) then
raise new InputTypeException(i+1,'char',TypeName(InputList[i]));
Result := char(InputList[i]);
end;
function Int: integer;
begin
Result := Int(Cur);
Cur += 1;
end;
function Re: real;
begin
Result := Re(Cur);
Cur += 1;
end;
function Str: string;
begin
Result := Str(Cur);
Cur += 1;
end;
function Boo: boolean;
begin
Result := Boo(Cur);
Cur += 1;
end;
function Chr: char;
begin
Result := Chr(Cur);
Cur += 1;
end;
function Int2: (integer,integer) := (Int,Int);
function Re2: (real,real) := (Re,Re);
function IntArr(n: integer): array of integer := (1..n).Select(x->Int).ToArray;
function ReArr(n: integer): array of real := (1..n).Select(x->Re).ToArray;
function Random(a, b: integer): integer;
begin
Result := PABCSystem.Random(a,b);
InputList.Add(Result);
end;
function Random(a, b: real): real;
begin
Result := PABCSystem.Random(a,b);
InputList.Add(Result);
end;
function Random2(a, b: integer): (integer, integer);
begin
Result := PABCSystem.Random2(a,b);
InputList.Add(Result[0]);
InputList.Add(Result[1]);
end;
function Random2(a, b: real): (real, real);
begin
Result := PABCSystem.Random2(a,b);
InputList.Add(Result[0]);
InputList.Add(Result[1]);
end;
function ReadString: string;
begin
Result := PABCSystem.ReadString;
InputList.Add(Result);
end;
function ReadlnString := ReadString;
function ReadString2 := (ReadString,ReadString);
function ReadlnString2 := ReadString2;
function ReadInteger(prompt: string): integer;
begin
Result := PABCSystem.ReadInteger(prompt);
OutputList.RemoveAt(OutputList.Count-1);
OutputList.RemoveAt(OutputList.Count-1);
end;
function ReadInteger2(prompt: string): (integer,integer);
begin
Result := PABCSystem.ReadInteger2(prompt);
OutputList.RemoveAt(OutputList.Count-1);
OutputList.RemoveAt(OutputList.Count-1);
end;
procedure Print(params args: array of object);
begin
foreach var ob in args do
begin
PABCSystem.Print(ob);
OutputList.RemoveAt(OutputList.Count-1)
end;
end;
procedure Println(params args: array of object);
begin
Print(args);
Writeln;
end;
procedure Print(ob: object);
begin
PABCSystem.Print(ob);
OutputList.RemoveAt(OutputList.Count-1)
end;
procedure Print(s: string);
begin
PABCSystem.Print(s);
OutputList.RemoveAt(OutputList.Count-1)
end;
type
IOLightSystem = class(__ReadSignalOISystem)
public
procedure write(obj: object); override;
begin
inherited write(obj);
OutputString += obj.ToString;
OutputList += obj;
end;
procedure writeln; override;
begin
inherited writeln;
OutputString += NewLine;
end;
procedure read(var x: integer); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: real); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: char); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: string); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: byte); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: shortint); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: smallint); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: word); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: longword); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: int64); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: uint64); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: single); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: boolean); override;
begin
inherited Read(x);
InputList.Add(x);
end;
procedure read(var x: BigInteger); override;
begin
inherited Read(x);
InputList.Add(x);
end;
end;
function CompareElements(o1,o2: Object): boolean;
begin
if (o1 is real) and (o2 is real) then
begin
var r1 := real(o1);
var r2 := real(o2);
Result := Abs(r1-r2)<0.0001;
exit;
end;
Result := (o1.GetType = o2.GetType) and o1.Equals(o2);
end;
function ToObjArray(a: array of integer) := a.Select(x->object(x)).ToArray;
function ToObjArray(a: array of real) := a.Select(x->object(x)).ToArray;
function ToObjArray(a: array of string) := a.Select(x->object(x)).ToArray;
function ToObjArray(a: array of char) := a.Select(x->object(x)).ToArray;
function ToObjArray(a: array of boolean) := a.Select(x->object(x)).ToArray;
function CompareWithOutput(params a: array of object): TaskStatus;
begin
Result := NotCompleted;
if a.Length <> OutputList.Count then
exit;
Result := if a.Zip(OutputList,(x,y) -> CompareElements(x,y)).All(x->x)
then Completed
else NotCompleted;
{Result := Completed;
for var i:=0 to a.Length-1 do
if not CompareElements(a[i],OutputList[i]) then
begin
Result := NotCompleted;
exit;
end;}
end;
function CompareSeqWithOutput(a: sequence of integer) := CompareWithOutput(ToObjArray(a.ToArray));
function CompareSeqWithOutput(a: sequence of real) := CompareWithOutput(ToObjArray(a.ToArray));
function CompareSeqWithOutput(a: sequence of string) := CompareWithOutput(ToObjArray(a.ToArray));
function CompareSeqWithOutput(a: sequence of char) := CompareWithOutput(ToObjArray(a.ToArray));
function CompareSeqWithOutput(a: sequence of boolean) := CompareWithOutput(ToObjArray(a.ToArray));
procedure ClearOutputListFromSpaces;
begin
OutputList := OutputList.Where(s -> (not (s is string)) or ((s as string) <> ' ')).ToList;
end;
procedure FilterOnlyNumbers;
begin
OutputList := OutputList.Where(x -> (x is integer) or (x is real)).ToList;
end;
var CheckTask: function(name: string): TaskStatus;
procedure CheckMyPT;
begin
if CheckTask = nil then
exit;
try
var b := CheckTask(TaskName);
case b of
Completed: Writeln(#10'Задание выполнено');
NotCompleted: Writeln(#10'Задание не выполнено');
end;
except
on e: InputCount2Exception do
begin
if e.Count = 0 then
Writeln(#10+$'Требуется ввести по крайней мере {e.n} значения')
else Writeln(#10+$'Введено {e.Count} значения, а требуется ввести по крайней мере {e.n}');
end;
on e: InputCountException do
begin
if e.Count = 0 then
Writeln(#10+$'Требуется ввести {e.n} значения')
else Writeln(#10+$'Введено {e.Count} значения, а требуется ввести {e.n}');
end;
on e: InputTypeException do
begin
Writeln(#10+$'Неверно указан тип при вводе исходных данных');
Writeln($'При вводе {e.n}-го элемента типа {e.ExpectedType} использована переменная типа {e.InputType}');
end;
end;
end;
initialization
CurrentIOSystem := new IOLightSystem;
finalization
CheckMyPT
end.