New project
commit
f23a84e409
@ -0,0 +1,5 @@
|
|||||||
|
Manifest-Version: 0.0.1
|
||||||
|
Project-Name: minipas
|
||||||
|
Source: src/main/rascal
|
||||||
|
Require-Libraries:
|
||||||
|
|
@ -0,0 +1,18 @@
|
|||||||
|
# A compiler for MiniPas using Rascal
|
||||||
|
|
||||||
|
* In my compiler construction subject, we made a compiler for a language called
|
||||||
|
`MiniPas` (a subset of `Pascal`) in C. It generates LLIR code from a `.pas`
|
||||||
|
file.
|
||||||
|
|
||||||
|
## Grammar
|
||||||
|
|
||||||
|
* The grammar of the langauge can be found in `src/Syntax.rsc`. We make some
|
||||||
|
comments here.
|
||||||
|
* Since `MiniPas` has notions of both functions and procedures, we refer to either
|
||||||
|
as a `SubProg`.
|
||||||
|
* Keywords are case insensitive but identifiers are case sensitive.
|
||||||
|
|
||||||
|
## Acknowledgements
|
||||||
|
* The grammar of `MiniPas` is from the course `Compiler Construction` in the University of Groningen.
|
||||||
|
The programs in `test/input` for `MiniPas` are from this course as well.
|
||||||
|
* The structure of the `Rascal` code comes from the course `Software Language Engineering` in the University of Groningen
|
@ -0,0 +1,62 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||||
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
||||||
|
<groupId>org.rascalmpl</groupId>
|
||||||
|
<artifactId>minipas</artifactId>
|
||||||
|
<version>0.1.0-SNAPSHOT</version>
|
||||||
|
|
||||||
|
<properties>
|
||||||
|
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||||
|
</properties>
|
||||||
|
|
||||||
|
<repositories>
|
||||||
|
<repository>
|
||||||
|
<id>usethesource</id>
|
||||||
|
<url>https://releases.usethesource.io/maven/</url>
|
||||||
|
</repository>
|
||||||
|
</repositories>
|
||||||
|
|
||||||
|
<pluginRepositories>
|
||||||
|
<pluginRepository>
|
||||||
|
<id>usethesource</id>
|
||||||
|
<url>https://releases.usethesource.io/maven/</url>
|
||||||
|
</pluginRepository>
|
||||||
|
</pluginRepositories>
|
||||||
|
|
||||||
|
<dependencies>
|
||||||
|
<dependency>
|
||||||
|
<groupId>org.rascalmpl</groupId>
|
||||||
|
<artifactId>rascal</artifactId>
|
||||||
|
<version>0.34.1</version>
|
||||||
|
</dependency>
|
||||||
|
</dependencies>
|
||||||
|
|
||||||
|
<build>
|
||||||
|
<plugins>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.apache.maven.plugins</groupId>
|
||||||
|
<artifactId>maven-compiler-plugin</artifactId>
|
||||||
|
<version>3.8.0</version>
|
||||||
|
<configuration>
|
||||||
|
<compilerArgument>-parameters</compilerArgument>
|
||||||
|
<release>11</release>
|
||||||
|
</configuration>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<groupId>org.rascalmpl</groupId>
|
||||||
|
<artifactId>rascal-maven-plugin</artifactId>
|
||||||
|
<version>0.8.2</version>
|
||||||
|
<configuration>
|
||||||
|
<errorsAsWarnings>true</errorsAsWarnings>
|
||||||
|
<bin>${project.build.outputDirectory}</bin>
|
||||||
|
<srcs>
|
||||||
|
<src>${project.basedir}/src/main/rascal</src>
|
||||||
|
</srcs>
|
||||||
|
</configuration>
|
||||||
|
</plugin>
|
||||||
|
</plugins>
|
||||||
|
</build>
|
||||||
|
</project>
|
||||||
|
|
@ -0,0 +1,55 @@
|
|||||||
|
module Syntax
|
||||||
|
|
||||||
|
extend lang::std::Layout;
|
||||||
|
extend lang::std::Id;
|
||||||
|
extend lang::std::ASCII;
|
||||||
|
|
||||||
|
start syntax Progarm = 'program' Id ";" ConstDecl* VarDecl* SubProgDecl* CompoundStatement;
|
||||||
|
syntax ConstDecl = 'const' Id "=" Number;
|
||||||
|
syntax IdList = Id {"," Id}*;
|
||||||
|
syntax TypeSpec = BasicType | 'array' "[" Number ".." Number "]" 'of' BasicType;
|
||||||
|
syntax BasicType = 'integer' | 'real';
|
||||||
|
syntax SubProgDecl = 'function' Id Parameters ":" BasicType ";" VarDecl* CompoundStatement ";" |
|
||||||
|
'procedure' Id Parameters? ";" VarDecl* CompoundStatement ";"
|
||||||
|
;
|
||||||
|
syntax Parameters = "(" ParameterList ")";
|
||||||
|
syntax ParameterList = 'var'? IdList ":" TypeSpec {";" ParameterList}*;
|
||||||
|
syntax CompoundStatement = 'begin' StatementList? 'end';
|
||||||
|
syntax StatementList = Statement {";" Statement}*;
|
||||||
|
syntax Statement = Lhs ":=" Expr |
|
||||||
|
ProcedureCall |
|
||||||
|
CompoundStatement |
|
||||||
|
'skip' |
|
||||||
|
'if' Guard 'then' Statement 'else' Statement |
|
||||||
|
'while' Guard 'do' Statement
|
||||||
|
;
|
||||||
|
|
||||||
|
syntax Guard = Expr Relop Expr |
|
||||||
|
'not' Guard |
|
||||||
|
Guard 'or' Guard |
|
||||||
|
Guard 'and' GUard |
|
||||||
|
"(" Guard ")"
|
||||||
|
;
|
||||||
|
|
||||||
|
syntax LhsList = Lhs {"," Lhs}*;
|
||||||
|
syntax Lhs = Id ("[" ExprList "]")?;
|
||||||
|
syntax ProcedureCall = Id ("(" ExprList ")")? |
|
||||||
|
'readln'"(" LhsList ")" |
|
||||||
|
'writeln'"(" ExprList ")"
|
||||||
|
;
|
||||||
|
syntax ExprList = Expr {"," Expr}*;
|
||||||
|
syntax Expr = Id ("[" Expr (".." Expr)?"]")? |
|
||||||
|
Num |
|
||||||
|
Id "(" ExprList ")" |
|
||||||
|
Expr "+" Expr |
|
||||||
|
Expr "-" Expr |
|
||||||
|
Expr "*" Expr |
|
||||||
|
Expr "/" Expr |
|
||||||
|
Expr 'div' Expr |
|
||||||
|
Expr 'mod' Expr |
|
||||||
|
"-" Expr |
|
||||||
|
"(" Expr ")"
|
||||||
|
;
|
||||||
|
|
||||||
|
lexical Relop = "\<"|"\<="|"\>"|"\>="|"=="|"!=";
|
||||||
|
lexical Number = Digit* ("." Digit+)?;
|
@ -0,0 +1,18 @@
|
|||||||
|
module MyTest
|
||||||
|
|
||||||
|
import ParseTree;
|
||||||
|
|
||||||
|
void main() {
|
||||||
|
[loc] files = getFilesIn(|project://test/input|);
|
||||||
|
for (loc file <- files) {
|
||||||
|
runTestOn(file);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void runTestOn(loc file) {
|
||||||
|
println(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
void getFilesIn(loc dir) {
|
||||||
|
return |project://test/input/arr.pas|;
|
||||||
|
}
|
@ -0,0 +1,24 @@
|
|||||||
|
{ This program does some work on arrays, passing them by value and by reference and such }
|
||||||
|
program arr;
|
||||||
|
|
||||||
|
const N = 5;
|
||||||
|
|
||||||
|
var arr : array [5 .. 6] of real;
|
||||||
|
|
||||||
|
function some (rra : array [1 .. 2] of real; y : real; z : real) : real;
|
||||||
|
begin
|
||||||
|
some := rra[1] + y + z
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure some2 (var rra : array [2 .. 3] of real);
|
||||||
|
begin
|
||||||
|
rra[3] := rra[3] + 20
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
readln(arr[5], arr[6]);
|
||||||
|
writeln(some(arr, arr[5], N));
|
||||||
|
writeln(some(arr, 5, 5.6));
|
||||||
|
some2(arr);
|
||||||
|
writeln(arr[5], arr[6])
|
||||||
|
end.
|
@ -0,0 +1,32 @@
|
|||||||
|
{ Example from the lab pdf }
|
||||||
|
PROGRAM arrparmechanism;
|
||||||
|
|
||||||
|
VAR a : ARRAY [0 .. 5] OF integer; {array with values a[0], a[1], a[2], a[3], a[4], a[5]}
|
||||||
|
VAR b : ARRAY [1 .. 6] OF integer; {array with values b[1], b[2], b[3], b[4], b[5], b[6]}
|
||||||
|
|
||||||
|
PROCEDURE arrcopy(VAR dest : ARRAY [0 .. 5] OF integer; src : ARRAY [5 .. 10] OF integer);
|
||||||
|
{dest is a var-paremeter, src is a value-parameter. Note the funny array bounds!}
|
||||||
|
VAR i : integer;
|
||||||
|
BEGIN
|
||||||
|
i := 0
|
||||||
|
; WHILE i <> 6 DO
|
||||||
|
BEGIN
|
||||||
|
dest[i] := src[i+5] { reflected to caller: dest is a var-parameter!}
|
||||||
|
; src[i+5] := 0 { not reflected to caller: src is a value-parameter!}
|
||||||
|
; i := i + 1
|
||||||
|
END
|
||||||
|
END;
|
||||||
|
|
||||||
|
FUNCTION sum(a : ARRAY [1 .. 3] OF integer) : integer;
|
||||||
|
BEGIN
|
||||||
|
sum := a[1] + a[2] + a[3]
|
||||||
|
END;
|
||||||
|
|
||||||
|
BEGIN
|
||||||
|
readln(b[1], b[2], b[3], b[4], b[5], b[6])
|
||||||
|
; arrcopy(a,b) {here index range translation takes place, the range sizes fit }
|
||||||
|
; writeln(a[0],a[1],a[2],a[3],a[4],a[5]) {this will print: 1 2 3 4 5 6 }
|
||||||
|
; writeln(b[1],b[2],b[3],b[4],b[5],b[6]) {this will also print: 1 2 3 4 5 6 }
|
||||||
|
; writeln(sum(a[0..2])) { note the section notation: this will print 6 (because 1+2+3=6) }
|
||||||
|
; writeln(sum(a[1..3])) { note the section notation: this will print 9 (because 2+3+4=9) }
|
||||||
|
END.
|
@ -0,0 +1,16 @@
|
|||||||
|
{ This program tries some logic statements }
|
||||||
|
program logic;
|
||||||
|
|
||||||
|
var x, z : integer;
|
||||||
|
var xs : array [1 .. 10] of integer;
|
||||||
|
var y : real;
|
||||||
|
var ys : array [1 .. 10] of real;
|
||||||
|
|
||||||
|
begin
|
||||||
|
readln(x, xs[1], y, ys[1]);
|
||||||
|
if x < 10 and xs[1] < 1 or not(y > 0 and ys[1] >= 3 and y < 2.3 and ys[1] < 3.3) then
|
||||||
|
z := 100
|
||||||
|
else
|
||||||
|
z := 999;
|
||||||
|
writeln(z)
|
||||||
|
end.
|
@ -0,0 +1,33 @@
|
|||||||
|
program sign;
|
||||||
|
|
||||||
|
const N = 4;
|
||||||
|
const M = 2.3;
|
||||||
|
|
||||||
|
var x, y, xy, xyz : integer;
|
||||||
|
var z : real;
|
||||||
|
var as, cs : array [2 .. 2] of real; { Array of size 1 }
|
||||||
|
var bs : array [2 .. 2] of integer;
|
||||||
|
|
||||||
|
begin
|
||||||
|
as[2] := 25.3; { assign real to *real* }
|
||||||
|
as[2] := 2; { assign int to *real* }
|
||||||
|
bs[2] := 1;
|
||||||
|
cs[2] := bs[2];
|
||||||
|
as[2] := cs[2];
|
||||||
|
x := N;
|
||||||
|
z := M;
|
||||||
|
z := 3 / 2;
|
||||||
|
z := 3.5 * 3 + 2 - 1;
|
||||||
|
z := 3.4 / 5;
|
||||||
|
z := 3.5 / 3.4 - 3.4;
|
||||||
|
y := 3 div 2;
|
||||||
|
z := bs[2];
|
||||||
|
x := 42;
|
||||||
|
y := -1;
|
||||||
|
xy := x*y;
|
||||||
|
xyz := -1*x + (-xy);
|
||||||
|
x := -x - x;
|
||||||
|
z := as[2];
|
||||||
|
writeln(z);
|
||||||
|
writeln(10 * 3 / 2 + 6 - 5 / 4 + (4 / 3 * 8 + 6 - 7) * 25 - 15 + 4)
|
||||||
|
end.
|
@ -0,0 +1,52 @@
|
|||||||
|
program fibonacci;
|
||||||
|
|
||||||
|
var n,i : integer;
|
||||||
|
var fibs : array [1 .. 35] of integer;
|
||||||
|
|
||||||
|
function fib(n : integer) : integer;
|
||||||
|
begin
|
||||||
|
if n <= 2 then
|
||||||
|
fib := 1
|
||||||
|
else
|
||||||
|
fib := fib(n-1) + fib(n-2)
|
||||||
|
end;
|
||||||
|
|
||||||
|
function fibMem(n : integer) : integer;
|
||||||
|
var fibCache : array [1 .. 100] of integer;
|
||||||
|
var i : integer;
|
||||||
|
begin
|
||||||
|
if n > 100 then
|
||||||
|
fibMem := 0
|
||||||
|
else
|
||||||
|
begin
|
||||||
|
fibCache[1] := 1;
|
||||||
|
fibCache[2] := 1;
|
||||||
|
i := 3;
|
||||||
|
while i <= n do
|
||||||
|
begin
|
||||||
|
fibCache[i] := fibCache[i - 1] + fibCache[i - 2];
|
||||||
|
i := i + 1
|
||||||
|
end;
|
||||||
|
fibMem := fibCache[i-1]
|
||||||
|
end
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
readln(n);
|
||||||
|
i := 1;
|
||||||
|
while i <= n do
|
||||||
|
begin
|
||||||
|
writeln(fib(i));
|
||||||
|
i := i + 1
|
||||||
|
end;
|
||||||
|
{ the dynamic }
|
||||||
|
writeln(fibMem(35));
|
||||||
|
{ now for the array }
|
||||||
|
i := 1;
|
||||||
|
while i <= 35 do
|
||||||
|
begin
|
||||||
|
fibs[i] := fib(i);
|
||||||
|
i := i + 1
|
||||||
|
end;
|
||||||
|
writeln(fibs[35])
|
||||||
|
end.
|
@ -0,0 +1,41 @@
|
|||||||
|
{ This program computes the greatest common divisor in three different ways }
|
||||||
|
PROGRAM euclid;
|
||||||
|
|
||||||
|
VAR a,b : integer;
|
||||||
|
|
||||||
|
function gcd_euclid(a, b : integer) : integer;
|
||||||
|
begin
|
||||||
|
while a <> b do
|
||||||
|
begin
|
||||||
|
while a > b do a := a - b;
|
||||||
|
while b > a do b := b - a
|
||||||
|
end;
|
||||||
|
gcd_euclid := a
|
||||||
|
end;
|
||||||
|
|
||||||
|
FUNCTION gcd_recursive(u, v : integer) : integer;
|
||||||
|
BEGIN
|
||||||
|
IF u mod v <> 0 THEN
|
||||||
|
gcd_recursive := gcd_recursive(v, u mod v)
|
||||||
|
ELSE
|
||||||
|
gcd_recursive := v
|
||||||
|
END;
|
||||||
|
|
||||||
|
function gcd_iterative(u, v : integer) : integer;
|
||||||
|
var t : integer;
|
||||||
|
begin
|
||||||
|
while v <> 0 do
|
||||||
|
begin
|
||||||
|
t := u;
|
||||||
|
u := v;
|
||||||
|
v := t mod v
|
||||||
|
end;
|
||||||
|
gcd_iterative := u
|
||||||
|
end;
|
||||||
|
|
||||||
|
BEGIN
|
||||||
|
readln(a,b);
|
||||||
|
writeln(gcd_recursive(a,b));
|
||||||
|
writeln(gcd_iterative(a,b));
|
||||||
|
writeln(gcd_euclid(a,b))
|
||||||
|
END.
|
@ -0,0 +1,12 @@
|
|||||||
|
{ Example program implementing some old IP assignment }
|
||||||
|
PROGRAM alt;
|
||||||
|
var shift : integer;
|
||||||
|
begin
|
||||||
|
readln(shift);
|
||||||
|
if shift < 0 then
|
||||||
|
shift := shift + shift
|
||||||
|
else
|
||||||
|
shift := shift - shift;
|
||||||
|
writeln(shift)
|
||||||
|
end
|
||||||
|
.
|
@ -0,0 +1,63 @@
|
|||||||
|
{ Example program implementing an old IP assignment that uses arrays by reference }
|
||||||
|
PROGRAM calc;
|
||||||
|
{
|
||||||
|
Small calculator with 4 registers
|
||||||
|
<register> : integer [1..4]
|
||||||
|
<value> : real
|
||||||
|
Options:
|
||||||
|
- 0 exit
|
||||||
|
- 1 <register> <value> : assign value to register
|
||||||
|
- 2 <ra> <rb> <rc> store (rb + rc) in ra (registers)
|
||||||
|
- 3 <ra> <rb> <rc> store (rb * rc) in ra (registers)
|
||||||
|
}
|
||||||
|
|
||||||
|
var rt : real;
|
||||||
|
var r : array [1 .. 4] of real;
|
||||||
|
var option, rid1, rid2, rid3 : integer;
|
||||||
|
|
||||||
|
function readRegister(var regs : array [1 .. 4] of real; regId : integer) : real;
|
||||||
|
begin
|
||||||
|
if regId >= 1 and regId <= 4 then
|
||||||
|
readRegister := regs[regId]
|
||||||
|
else
|
||||||
|
readRegister := 0
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure writeRegister(var regs : array [1 .. 4] of real; regId : integer; number : real);
|
||||||
|
begin
|
||||||
|
if regId >= 1 and regId <= 4 then
|
||||||
|
regs[regId] := number
|
||||||
|
else
|
||||||
|
skip
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
r[1] := 0;
|
||||||
|
r[2] := 0;
|
||||||
|
r[3] := 0;
|
||||||
|
r[4] := 0;
|
||||||
|
writeln(r[1], r[2], r[3], r[4]);
|
||||||
|
readln(option);
|
||||||
|
while option <> 0 do
|
||||||
|
begin
|
||||||
|
if option <= 1 then
|
||||||
|
begin
|
||||||
|
readln(rid1, rt);
|
||||||
|
writeRegister(r, rid1, rt)
|
||||||
|
end
|
||||||
|
else if option <= 2 then
|
||||||
|
begin
|
||||||
|
readln(rid1, rid2, rid3);
|
||||||
|
writeRegister(r, rid1, readRegister(r, rid2) + readRegister(r, rid3))
|
||||||
|
end
|
||||||
|
else if option <= 3 then
|
||||||
|
begin
|
||||||
|
readln(rid1, rid2, rid3);
|
||||||
|
writeRegister(r, rid1, readRegister(r, rid2) * readRegister(r, rid3))
|
||||||
|
end
|
||||||
|
else skip;
|
||||||
|
writeln(r[1], r[2], r[3], r[4]);
|
||||||
|
readln(option)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
.
|
@ -0,0 +1,75 @@
|
|||||||
|
{ Example program implementing an old IP assignment that uses arrays by reference }
|
||||||
|
PROGRAM calc;
|
||||||
|
{
|
||||||
|
Small calculator with 4 registers
|
||||||
|
<register> : integer [1..4]
|
||||||
|
<value> : real
|
||||||
|
Options:
|
||||||
|
- 0 exit
|
||||||
|
- 1 <register> <value> : assign value to register
|
||||||
|
- 2 <ra> <rb> <rc> store (rb + rc) in ra (registers)
|
||||||
|
- 3 <ra> <rb> <rc> store (rb * rc) in ra (registers)
|
||||||
|
}
|
||||||
|
|
||||||
|
var r1, r2, r3, r4, rt: real;
|
||||||
|
var option, rid1, rid2, rid3 : integer;
|
||||||
|
|
||||||
|
function readRegister(regId : integer) : real;
|
||||||
|
begin
|
||||||
|
if regId <= 1 then
|
||||||
|
readRegister := r1
|
||||||
|
else if regId <= 2 then
|
||||||
|
readRegister := r2
|
||||||
|
else if regId <= 3 then
|
||||||
|
readRegister := r3
|
||||||
|
else if regId <= 4 then
|
||||||
|
readRegister := r4
|
||||||
|
else
|
||||||
|
readRegister := 0.0
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure writeRegister(regId : integer; number : real);
|
||||||
|
begin
|
||||||
|
if regId < 1 then
|
||||||
|
skip
|
||||||
|
else if regId <= 1 then
|
||||||
|
r1 := number
|
||||||
|
else if regId <= 2 then
|
||||||
|
r2 := number
|
||||||
|
else if regId <= 3 then
|
||||||
|
r3 := number
|
||||||
|
else if regId <= 4 then
|
||||||
|
r4 := number
|
||||||
|
else skip
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
r1 := 0.0;
|
||||||
|
r2 := 0.0;
|
||||||
|
r3 := 0.0;
|
||||||
|
r4 := 0.0;
|
||||||
|
writeln(r1, r2, r3, r4);
|
||||||
|
readln(option);
|
||||||
|
while option <> 0 do
|
||||||
|
begin
|
||||||
|
if option <= 1 then
|
||||||
|
begin
|
||||||
|
readln(rid1, rt);
|
||||||
|
writeRegister(rid1, rt)
|
||||||
|
end
|
||||||
|
else if option <= 2 then
|
||||||
|
begin
|
||||||
|
readln(rid1, rid2, rid3);
|
||||||
|
writeRegister(rid1, readRegister(rid2) + readRegister(rid3))
|
||||||
|
end
|
||||||
|
else if option <= 3 then
|
||||||
|
begin
|
||||||
|
readln(rid1, rid2, rid3);
|
||||||
|
writeRegister(rid1, readRegister(rid2) * readRegister(rid3))
|
||||||
|
end
|
||||||
|
else skip;
|
||||||
|
writeln(r1, r2, r3, r4);
|
||||||
|
readln(option)
|
||||||
|
end
|
||||||
|
end
|
||||||
|
.
|
@ -0,0 +1,21 @@
|
|||||||
|
{ Example IP exam assignment with a basic while loop }
|
||||||
|
program missing;
|
||||||
|
{ Takes a number N, then N unique numbers <= N of which one is 0. Prints the missing number <= N }
|
||||||
|
|
||||||
|
var n, total, a, i : integer;
|
||||||
|
|
||||||
|
begin
|
||||||
|
readln(n);
|
||||||
|
total := n;
|
||||||
|
i := 0;
|
||||||
|
|
||||||
|
while i < n do
|
||||||
|
begin
|
||||||
|
readln(a);
|
||||||
|
total := total + i;
|
||||||
|
total := total - a;
|
||||||
|
i := i + 1
|
||||||
|
end;
|
||||||
|
|
||||||
|
writeln(total)
|
||||||
|
end.
|
@ -0,0 +1,63 @@
|
|||||||
|
program permutations;
|
||||||
|
|
||||||
|
var n, lcm, l, i : integer;
|
||||||
|
var p, loopLength : array [0 .. 100] of integer;
|
||||||
|
|
||||||
|
function gcd(a : integer; b : integer): integer;
|
||||||
|
begin
|
||||||
|
if a mod b <> 0 then
|
||||||
|
gcd := gcd(b, a mod b)
|
||||||
|
else
|
||||||
|
gcd := b
|
||||||
|
end;
|
||||||
|
|
||||||
|
function loopLengthAt(p : array [0 .. 100] of integer; length : integer; start : integer; current : integer; n : integer; lengths : array [0 .. 100] of integer) : integer;
|
||||||
|
var isSet, result : integer;
|
||||||
|
begin
|
||||||
|
isSet := 0;
|
||||||
|
if lengths[current] <> 0 then
|
||||||
|
begin
|
||||||
|
loopLengthAt := lengths[current];
|
||||||
|
isSet := 1
|
||||||
|
end
|
||||||
|
else if current = start then
|
||||||
|
if n > 0 then
|
||||||
|
begin
|
||||||
|
lengths[current] := n;
|
||||||
|
loopLengthAt := n;
|
||||||
|
isSet := 1
|
||||||
|
end
|
||||||
|
else skip
|
||||||
|
else skip;
|
||||||
|
|
||||||
|
if isSet = 0 then
|
||||||
|
begin
|
||||||
|
result := loopLengthAt(p, length, start, p[current], n + 1, lengths);
|
||||||
|
lengths[current] := result;
|
||||||
|
loopLengthAt := result
|
||||||
|
end
|
||||||
|
else skip
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
lcm := 1;
|
||||||
|
i := 0;
|
||||||
|
readln(n);
|
||||||
|
|
||||||
|
while i < n do
|
||||||
|
begin
|
||||||
|
readln(p[i]);
|
||||||
|
loopLength[i] := 0;
|
||||||
|
i := i + 1
|
||||||
|
end;
|
||||||
|
|
||||||
|
i := 0;
|
||||||
|
while i < n do
|
||||||
|
begin
|
||||||
|
l := loopLengthAt(p, n, i, i, 0, loopLength);
|
||||||
|
lcm := lcm * l div gcd(lcm, l);
|
||||||
|
i := i + 1
|
||||||
|
end;
|
||||||
|
|
||||||
|
writeln(lcm)
|
||||||
|
end.
|
@ -0,0 +1,14 @@
|
|||||||
|
{ Parameter passing mechanism from the lab pdf }
|
||||||
|
PROGRAM parmechanism;
|
||||||
|
VAR a, b : integer;
|
||||||
|
|
||||||
|
PROCEDURE proc(VAR a:integer; b, c : integer);
|
||||||
|
BEGIN b := b + 2
|
||||||
|
; a := c*a + b
|
||||||
|
END;
|
||||||
|
|
||||||
|
BEGIN readln(a)
|
||||||
|
; b := 0
|
||||||
|
; proc(a,b,2)
|
||||||
|
; writeln(a,b)
|
||||||
|
END.
|
@ -0,0 +1,27 @@
|
|||||||
|
{ This program determines whether a number is prime }
|
||||||
|
PROGRAM prime;
|
||||||
|
|
||||||
|
VAR p,c : integer;
|
||||||
|
|
||||||
|
BEGIN
|
||||||
|
readln(p);
|
||||||
|
c := 2;
|
||||||
|
while c * c <= p do
|
||||||
|
begin
|
||||||
|
if p mod c <> 0 then
|
||||||
|
begin
|
||||||
|
c := c + 1;
|
||||||
|
if c * c > p then
|
||||||
|
writeln(1)
|
||||||
|
else
|
||||||
|
begin
|
||||||
|
end
|
||||||
|
end
|
||||||
|
else
|
||||||
|
begin
|
||||||
|
writeln(0);
|
||||||
|
c := p + 100 { Exit condition that also works for p = 1 }
|
||||||
|
end
|
||||||
|
end
|
||||||
|
END
|
||||||
|
.
|
@ -0,0 +1,34 @@
|
|||||||
|
{ This is some puzzle thing from an old IP exam }
|
||||||
|
program puzzle;
|
||||||
|
|
||||||
|
var len, temp : integer;
|
||||||
|
var series : array [0 .. 20] of integer;
|
||||||
|
|
||||||
|
function canReachLast(i : integer; pos : integer; len : integer; series : array [0 .. 20] of integer) : integer;
|
||||||
|
begin
|
||||||
|
if pos < 0 or pos >= len or i >= len then
|
||||||
|
canReachLast := 0
|
||||||
|
else if len - 1 = pos + series[pos] or canReachLast(i + 1, pos + series[pos], len, series) = 1 then
|
||||||
|
canReachLast := 1
|
||||||
|
else
|
||||||
|
canReachLast := canReachLast(i + 1, pos - series[pos], len, series)
|
||||||
|
end;
|
||||||
|
|
||||||
|
function isSolvable(len : integer; series : array [0 .. 20] of integer) : integer;
|
||||||
|
begin
|
||||||
|
isSolvable := canReachLast(0, 0, len, series)
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
len := 0;
|
||||||
|
readln(temp);
|
||||||
|
series[len] := temp;
|
||||||
|
while series[len] <> 0 do
|
||||||
|
begin
|
||||||
|
len := len + 1;
|
||||||
|
readln(temp);
|
||||||
|
series[len] := temp
|
||||||
|
end;
|
||||||
|
len := len + 1;
|
||||||
|
writeln(isSolvable(len, series))
|
||||||
|
end.
|
@ -0,0 +1,41 @@
|
|||||||
|
{ Pythagoras program }
|
||||||
|
PROGRAM pyth;
|
||||||
|
{
|
||||||
|
Program that reads three numbers and tells bou
|
||||||
|
- 0 if they're not a triangle
|
||||||
|
- 1 if it's a right-angled triangle
|
||||||
|
- 2 if it's an obtuse triangle
|
||||||
|
- 3 if it's a sharp triangle
|
||||||
|
}
|
||||||
|
VAR a, b, c, t: integer;
|
||||||
|
|
||||||
|
BEGIN
|
||||||
|
readln(a, b, c);
|
||||||
|
while a > b do
|
||||||
|
begin
|
||||||
|
t := a;
|
||||||
|
a := b;
|
||||||
|
b := t
|
||||||
|
end; {a <= b}
|
||||||
|
while a > c do
|
||||||
|
begin
|
||||||
|
t := a;
|
||||||
|
a := c;
|
||||||
|
c := t
|
||||||
|
end; {a <= c && a <= b}
|
||||||
|
while b > c do
|
||||||
|
begin
|
||||||
|
t := b;
|
||||||
|
b := c;
|
||||||
|
c := t
|
||||||
|
end; {a <= b <= c}
|
||||||
|
if a + b <= c then
|
||||||
|
writeln(0)
|
||||||
|
else if a * a + b * b < c * c then
|
||||||
|
writeln(2)
|
||||||
|
else if a * a + b * b > c * c then
|
||||||
|
writeln(3)
|
||||||
|
else
|
||||||
|
writeln(1)
|
||||||
|
END
|
||||||
|
.
|
@ -0,0 +1,19 @@
|
|||||||
|
{ Return 42 example from lab pdf }
|
||||||
|
program return42;
|
||||||
|
|
||||||
|
var x : integer;
|
||||||
|
|
||||||
|
function return42(n : integer) : integer;
|
||||||
|
begin
|
||||||
|
if n > 42 then
|
||||||
|
return42 := return42(n-1)
|
||||||
|
else begin
|
||||||
|
return42 := n;
|
||||||
|
while return42 < 42 do return42 := return42 + 1
|
||||||
|
end
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
readln(x);
|
||||||
|
writeln(return42(x))
|
||||||
|
end.
|
@ -0,0 +1,18 @@
|
|||||||
|
{ This program does a lot of shadowing }
|
||||||
|
PROGRAM shadowing;
|
||||||
|
|
||||||
|
function x (a : integer) : integer;
|
||||||
|
begin
|
||||||
|
x := a
|
||||||
|
end;
|
||||||
|
|
||||||
|
function a (b : integer) : integer;
|
||||||
|
var x : integer;
|
||||||
|
begin
|
||||||
|
x := b;
|
||||||
|
a := x
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
writeln(a(x(4)))
|
||||||
|
end.
|
@ -0,0 +1,23 @@
|
|||||||
|
{ This program does more stuff with subarrays }
|
||||||
|
program arr;
|
||||||
|
|
||||||
|
var arr : array [1 .. 10] of real;
|
||||||
|
|
||||||
|
procedure some (rra : array [5 .. 10] of real);
|
||||||
|
begin
|
||||||
|
rra[6] := 4
|
||||||
|
end;
|
||||||
|
|
||||||
|
procedure some2 (var rra : array [5 .. 10] of real; var x : real);
|
||||||
|
begin
|
||||||
|
rra[6] := 4;
|
||||||
|
x := 3
|
||||||
|
end;
|
||||||
|
|
||||||
|
begin
|
||||||
|
arr[3] := 3;
|
||||||
|
some(arr[2 .. 7]);
|
||||||
|
writeln(arr[3]);
|
||||||
|
some2(arr[2 .. 7], arr[4]);
|
||||||
|
writeln(arr[3], arr[4])
|
||||||
|
end.
|
Loading…
Reference in New Issue