Skip to content

Commit

Permalink
Add tests for functions in input language
Browse files Browse the repository at this point in the history
  • Loading branch information
df7cb committed May 18, 2022
1 parent 92e69af commit 061a189
Show file tree
Hide file tree
Showing 5 changed files with 90 additions and 2 deletions.
2 changes: 1 addition & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ DATA_built = unit--2--3.sql unit--3.sql \
unit--4--5.sql unit--5.sql \
unit--5--6.sql unit--6.sql \
unit--6--7.sql unit--7.sql
REGRESS = extension tables unit binary unicode prefix units time temperature functions round derived compare aggregate iec custom
REGRESS = extension tables unit binary unicode prefix units time temperature functions language_functions round derived compare aggregate iec custom
# Jessie's and trusty's bison (3.0.2) is buggy, ship pregenerated .tab files
EXTRA_CLEAN = unitparse.yy.* powers powers.o unit-*.dump # unitparse.tab.*

Expand Down
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -249,10 +249,11 @@ Unit values allow a fairly complex expression syntax on input.
* operators + - * /
* exponentiation: `expr^integer` or Unicode superscripts: `expr⁺⁻⁰¹²³⁴⁵⁶⁷⁸⁹`
* parentheses ()
* multiplication binds tighter than division such that `kg/s^2*A`
* multiplication binds tighter than division such that `kg/s^2*A` and `kg/s^2 A`
can be written without parentheses
* `N|M` denotes a numeric fraction, e.g. `3|4`
* use `hh:mm:ss[.sss]` for time values, e.g. `10:05:30 s`
* functions: `sqrt(unit)`, `exp(x)`, `ln(x)`, `log2(x)`, `asin(x)`, `tan(x)`

*Note: This covers the unit input parser for expressions like
`'1|2 m / h'::unit`. PostgreSQL operators on type unit values are a separate
Expand Down
62 changes: 62 additions & 0 deletions expected/language_functions.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,62 @@
select 'sqrt(4 m^2)'::unit;
unit
------
2 m
(1 row)

select 'sqrt(-4 m^2)'::unit;
ERROR: cannot take square root of a negative-valued unit
LINE 1: select 'sqrt(-4 m^2)'::unit;
^
select 'sqrt(4 m^3)'::unit;
ERROR: cannot take square root of a unit with odd "m" exponent
LINE 1: select 'sqrt(4 m^3)'::unit;
^
select 'exp(1)'::unit;
unit
------------------
2.71828182845905
(1 row)

select 'exp(1 A)'::unit;
ERROR: cannot take base-e exponent of value that is not dimension-less
LINE 1: select 'exp(1 A)'::unit;
^
select 'ln(2.7)'::unit;
unit
-------------------
0.993251773010283
(1 row)

select 'ln(-2.7)'::unit;
ERROR: cannot take ln of a negative-valued unit
LINE 1: select 'ln(-2.7)'::unit;
^
select 'ln(2.7 s)'::unit;
ERROR: cannot take ln of value that is not dimension-less
LINE 1: select 'ln(2.7 s)'::unit;
^
select 'asin(1)'::unit;
unit
-----------------
1.5707963267949
(1 row)

select 'asin(2)'::unit;
ERROR: cannot asin of values outside the range -1 to 1
LINE 1: select 'asin(2)'::unit;
^
select 'asin(1 kg)'::unit;
ERROR: cannot take asin of value that is not dimension-less
LINE 1: select 'asin(1 kg)'::unit;
^
select 'tan(1)'::unit;
unit
-----------------
1.5574077246549
(1 row)

select 'tan(1 mol)'::unit;
ERROR: cannot take tan of value that is not dimension-less
LINE 1: select 'tan(1 mol)'::unit;
^
17 changes: 17 additions & 0 deletions sql/language_functions.sql
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
select 'sqrt(4 m^2)'::unit;
select 'sqrt(-4 m^2)'::unit;
select 'sqrt(4 m^3)'::unit;

select 'exp(1)'::unit;
select 'exp(1 A)'::unit;

select 'ln(2.7)'::unit;
select 'ln(-2.7)'::unit;
select 'ln(2.7 s)'::unit;

select 'asin(1)'::unit;
select 'asin(2)'::unit;
select 'asin(1 kg)'::unit;

select 'tan(1)'::unit;
select 'tan(1 mol)'::unit;
8 changes: 8 additions & 0 deletions unit.c
Original file line number Diff line number Diff line change
Expand Up @@ -995,6 +995,10 @@ unit_ln_internal(Unit *a, Unit *result)
int i;

/* compute ln of value */
if (a->value < 0)
ereport(ERROR,
(errcode(ERRCODE_INVALID_ARGUMENT_FOR_POWER_FUNCTION),
errmsg("cannot take ln of a negative-valued unit")));
result->value = log(a->value);

/* check dimension */
Expand All @@ -1014,6 +1018,10 @@ unit_log2_internal(Unit *a, Unit *result)
int i;

/* compute log2 of value */
if (a->value < 0)
ereport(ERROR,
(errcode(ERRCODE_INVALID_ARGUMENT_FOR_POWER_FUNCTION),
errmsg("cannot take log2 of a negative-valued unit")));
result->value = log2(a->value);

/* check dimension */
Expand Down

0 comments on commit 061a189

Please sign in to comment.