first commit

This commit is contained in:
duboissim 2024-03-01 13:22:27 +01:00
commit de2fc4afe0
4 changed files with 367 additions and 0 deletions

Binary file not shown.

33
input.pl Normal file
View File

@ -0,0 +1,33 @@
:- dynamic tabl/2.
tabl(persons, [id, first, last, age, city]).
tabl(cities, [name, state, temp]).
:- dynamic persons/5.
persons( 0, "Jeffrey", "Bowman", 30, "Daytona Beach").
persons( 1, "Lorena", "Michaels", 50, "Boardman").
persons( 2, "Joseph", "Mixson", 37, "Washington").
persons( 3, "Stewart", "Sullivan", 83, "Grand Island").
persons( 4, "Thomas", "Marshall", 75, "Houston").
persons( 5, "Tameka", "Escobedo", 25, "Orlando").
persons( 6, "Annette", "Marcy", 40, "Pittsburgh").
persons( 7, "David", "Smith", 36, "Orlando").
persons( 8, "Anthony", "Garcia", 20, "Daytona Beach").
persons( 9, "Lindsay", "Faught", 70, "Boardman").
persons(10, "Claudette", "Neil", 32, "Washington").
persons(11, "Betty", "Strickland", 47, "Atlanta").
persons(12, "Richard", "Gordon", 47, "Dallas").
persons(13, "Robert", "Evans", 69, "Atlanta").
persons(14, "Candace", "Griffin", 61, "Pittsburgh").
persons(15, "Sandra", "Smith", 67, "Dallas").
:- dynamic cities/3.
cities("Daytona Beach", "Florida", 22).
cities("Boardman", "Oregon", 12).
cities("Washington", "District of Columbia", 11).
cities("Grand Island", "New York", 10).
cities("Houston", "Texas", 20).
cities("Orlando", "Florida", 23).
cities("Dallas", "Texas", 17).
cities("Pittsburgh", "Pennsylvania", 11).
cities("Atlanta", "Georgia", 16).

236
tests.pl Normal file
View File

@ -0,0 +1,236 @@
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% HELPERS
% plunit is a Prolog unit-test framework initially developed for SWI-Prolog
:- use_module(library(plunit)).
:- discontiguous test/2.
% Run the tests.
test :-
run_tests(sql).
% 'clean' drop: call drop/1 and swallow any thrown exceptions
cdrop(Table) :-
catch(drop(Table), _, true).
% Checks that two lists have the same content.
same_content(L1, L2) :-
msort(L1, S),
msort(L2, S).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% TESTS
:- begin_tests(sql).
% Test if create/1 works.
test(create_table, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
tables(Tables),
member(foo, Tables), !.
% Test if create/1 throws an error on dup table name.
test(create_redundant, [throws(_), cleanup(cdrop(foo))]) :-
create_table(foo, [bar, baz]),
create_table(foo, [bab, bac]).
% Test if the columns are properly recorded.
test(cols, cleanup(cdrop(foo))) :-
create_table(foo, [baru, bazu]),
cols(foo, Cols),
assertion(Cols == [baru, bazu]).
% Test if drop/1 works.
test(drop) :-
create_table(foo, [bar, baz]),
drop(foo), !,
tables(Tables),
\+ member(foo, Tables).
% Test if drop/1 throws an error on unknown table name.
test(drop_inexistant, throws(_)) :-
drop(foobar).
% Test if row/2 returns the different rows of a given table.
test(rows, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
rows(foo, Rows),
assertion(length(Rows,2)).
% Test if row/2 fails on an unknown table name.
test(row_inexistant, throws(_)) :-
rows(foo, _Row).
% Test if rows/1 works when called for a given table name.
test(rows, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
rows(foo).
% Test if rows/1 throws an error on unknown table name.
test(rows_inexistant, throws(_)) :-
rows(foo).
% Simple insert/2 & selec/4 test.
test(insert2, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
%selec(foo, *, [], X/Y), !,
selec(foo, *, X/Y), !,
assertion(X == [+bar, +baz]),
assertion(Y == [1, 2]),
insert(foo, [3, 4]),
findall(Z, selec(foo, *, [], _/Z), Zs), !,
assertion(Zs == [[1,2],[3,4]]).
% Test if insert/2 throws an error on unknown table name.
test(insert_inexistant, throws(_)) :-
insert(foo, [1, 2]).
% Simple delete/1 test.
test(delete1, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
delete(foo),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == []),
tables(Tables),
member(foo, Tables).
% Simple delete/2 test.
test(delete2, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
delete(foo, [+bar = 1]),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == [[3, 4]]).
% Another simple delete/2 test.
test(delete2bis, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
delete(foo, [+bar >= 1]),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == []).
% Test delete/2 using multiple conditions.
test(delete2_mult, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
delete(foo, [+bar = 1, +baz = 2]),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == [[3, 4]]).
% Another test of delete/2 using multiple conditions.
test(delete2_mult_bis, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
delete(foo, [+bar > 1, +baz < 2]),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == [[1, 2],[3,4]]).
% Test selec/4 with a single condition +col condition.
test(selec_cond1) :-
selec(persons, *, [+id = 0], _/Row1), !,
assertion(Row1 == [0, "Jeffrey", "Bowman", 30, "Daytona Beach"]),
selec(persons, *, [+first = "Lorena"], _/Row2), !,
assertion(Row2 == [1, "Lorena", "Michaels", 50, "Boardman"]).
% Test selec/4 with two +col conditions.
test(selec_cond_mult1) :-
selec(persons, *, [+age = 47, +city = "Atlanta"], _/Row), !,
assertion(Row == [11, "Betty", "Strickland", 47, "Atlanta"]).
% Test selec/4 with a single projection and no conditions.
test(selec_proj) :-
findall(Row, selec(persons, [+first], [], _/Row), Rows0),
flatten(Rows0, Rows),
assertion(Rows == ["Jeffrey", "Lorena", "Joseph", "Stewart", "Thomas",
"Tameka", "Annette", "David", "Anthony", "Lindsay", "Claudette", "Betty",
"Richard", "Robert", "Candace", "Sandra"]).
% Test selec/4 with projections and a condition.
test(selec_mult_proj) :-
findall(Row, selec(persons, [+first, +last], [+age >= 70], _/Row), Rows),
same_content(Rows, [
["Stewart", "Sullivan"],
["Thomas", "Marshall"],
["Lindsay", "Faught"]]).
% Test that drop/1 correctly removes rows.
test(drop_implem, cleanup(cdrop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
drop(foo),
create_table(foo, [bar, baz]),
findall(Z, selec(foo, *, [], _/Z), Zs), !,
assertion(Zs == []).
% Test that tables/1 works.
test(tables, cleanup((cdrop(foo), cdrop(bar), cdrop(baz)))) :-
create_table(foo, []),
create_table(bar, []),
create_table(baz, []),
drop(bar),
tables(Tables),
member(foo, Tables), !,
member(baz, Tables), !,
\+ member(bar, Tables), !.
% Test that insert/2 throws an error on unknown table name.
test(insert_inexistant, throws(_)) :-
insert(foobar, [1, 2]).
% Test that insert/2 throws an error if it is supplied too few values.
test(insert_count1, [throws(_), cleanup(drop(foo))]) :-
create_table(foo, [bar, baz]),
insert(foo, [1]).
% Test that insert/2 throws an error if it is supplied too many values.
test(insert_count2, [throws(_), cleanup(drop(foo))]) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2, 3]).
% Tests that delete/1 throws an error on unknown table name.
test(delete_inexistant1, throws(_)) :-
delete(foobar).
% Tests that delete/2 throws an error on unknown table name.
test(delete_inexistant2, throws(_)) :-
delete(foobar, []).
% Simple delete/2 test using the +<column>.
test(delete2_1, cleanup(drop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
delete(foo, [+baz = 4]),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == [[1, 2]]).
% delete/2 test using mixed notations.
test(delete2_2, cleanup(drop(foo))) :-
create_table(foo, [bar, baz]),
insert(foo, [1, 2]),
insert(foo, [3, 4]),
insert(foo, [3, 5]),
delete(foo, [+bar = 3, +baz = 4]),
findall(Z, selec(foo, *, [], _/Z), Zs),
assertion(Zs == [[1, 2], [3, 5]]).
% Test selec/4 with a projection and multiple conditions.
test(selec_mult_cond) :-
findall(Row, selec(persons, [+first, +last],
[+age >= 60, +city = "Atlanta"], _/Row), Rows),
same_content(Rows, [["Robert", "Evans"]]).
% ==============================================================================

98
tests_dcg.pl Normal file
View File

@ -0,0 +1,98 @@
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% HELPERS
% plunit is a Prolog unit-test framework initially developed for SWI-Prolog
:- use_module(library(plunit)).
:- discontiguous test/2.
% Run the tests.
test_dcg :-
run_tests(dcg).
% 'clean' drop: call drop/1 and swallow any thrown exceptions
cdrop(Table) :-
catch(drop(Table), _, true).
% Checks that two lists have the same content.
same_content(L1, L2) :-
msort(L1, S),
msort(L2, S).
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
:- begin_tests(dcg).
%%not tested because not specified.
%%test(query3) :-
%% query("SELECT +id FROM cities;", _/Z), !,
%% assertion(Z == []).
test(selec_with_selectors) :-
findall(Z,
query("SELECT +first, +age FROM persons;",
_/Z), Zs),
same_content(Zs, [
["Jeffrey",30],
["Lorena",50],
["Joseph",37],
["Stewart",83],
["Thomas",75],
["Tameka",25],
["Annette",40],
["David",36],
["Anthony",20],
["Lindsay",70],
["Claudette",32],
["Betty",47],
["Richard",47],
["Robert",69],
["Candace",61],
["Sandra",67]]).
test(selec_selectors_conditions) :-
findall(Z,
query("SELECT +state, +name FROM cities WHERE +temp>=20;",
_/Z), Zs),
same_content(Zs, [
["Florida", "Daytona Beach"],
["Texas", "Houston"],
["Florida", "Orlando"]]).
test(selec_multi_conditions) :-
findall(Z,
query(`SELECT +last FROM persons WHERE +city="Orlando", +age>30;`,
_/Z), Zs),
same_content(Zs, [["Smith"]]).
test(selec_all) :-
findall(Z,
query("SELECT * FROM cities;"
, _/Z), Zs),
same_content(Zs, [["Daytona Beach", "Florida", 22],
["Boardman", "Oregon", 12],
["Washington", "District of Columbia", 11],
["Grand Island", "New York", 10],
["Houston", "Texas", 20],
["Orlando", "Florida", 23],
["Dallas", "Texas", 17],
["Pittsburgh", "Pennsylvania", 11],
["Atlanta", "Georgia", 16]]).
test(selec_after_insert, cleanup(delete(cities, [+name="Tempa"]))) :-
query(`INSERT INTO cities (+name, +state) VALUES ("Tempa", "Florida");`),
findall(Z,
query("SELECT * FROM cities;"
, _/Z), Zs),
same_content(Zs, [["Daytona Beach", "Florida", 22],
["Boardman", "Oregon", 12],
["Washington", "District of Columbia", 11],
["Grand Island", "New York", 10],
["Houston", "Texas", 20],
["Orlando", "Florida", 23],
["Dallas", "Texas", 17],
["Pittsburgh", "Pennsylvania", 11],
["Atlanta", "Georgia", 16],
["Tempa", "Florida", _]]).
:- end_tests(dcg).