:- module rational.
:- use_module builtin, integer, private_builtin, require.
:- type rational.rational
	--->	r(integer.integer, integer.integer).
:- func rational.rational_norm(integer.integer, integer.integer) = rational.rational.
:- mode rational.rational_norm((builtin.in), (builtin.in)) = (builtin.out) is det.
:- func rational.cmp(rational.rational, rational.rational) = builtin.comparison_result.
:- mode rational.cmp((builtin.in), (builtin.in)) = (builtin.out) is det.
rational.(R1_3 < R2_4) :-
    Cmp_5 = rational.cmp(R1_3, R2_4),
    Cmp_5 = builtin.(<) : builtin.comparison_result.
rational.(R1_3 > R2_4) :-
    Cmp_5 = rational.cmp(R1_3, R2_4),
    Cmp_5 = builtin.(>) : builtin.comparison_result.
rational.(R1_3 =< R2_4) :-
    Cmp_5 = rational.cmp(R1_3, R2_4),
    ( % disjunction
      Cmp_5 = builtin.(<) : builtin.comparison_result
    ;
      Cmp_5 = builtin.(=) : builtin.comparison_result
    ).
rational.(R1_3 >= R2_4) :-
    Cmp_5 = rational.cmp(R1_3, R2_4),
    ( % disjunction
      Cmp_5 = builtin.(>) : builtin.comparison_result
    ;
      Cmp_5 = builtin.(=) : builtin.comparison_result
    ).
rational.rational(Int_3) = HeadVar__2_2 :-
    HeadVar__2_2 = rational.rational_norm(V_4, V_5),
    V_4 = integer.integer(Int_3),
    V_5 = integer.one.
rational.rational(Num_4, Den_5) = HeadVar__3_3 :-
    HeadVar__3_3 = rational.rational_norm(V_6, V_7),
    V_6 = integer.integer(Num_4),
    V_7 = integer.integer(Den_5).
rational.from_integer(Integer_3) = HeadVar__2_2 :-
    HeadVar__2_2 = rational.rational_norm(Integer_3, V_4),
    V_4 = integer.one.
rational.from_integers(Num_4, Den_5) = HeadVar__3_3 :-
    HeadVar__3_3 = rational.rational_norm(Num_4, Den_5).
rational.(+ Rat_3) = Rat_3.
rational.(- rational.r(Num_3, Den_4)) = rational.r(V_5, Den_4) :-
    V_5 = integer.(- Num_3).
rational.(R1_4 - R2_5) = HeadVar__3_3 :-
    HeadVar__3_3 = rational.(R1_4 + V_6),
    V_6 = rational.(- R2_5).
rational.(R1_4 / R2_5) = HeadVar__3_3 :-
    HeadVar__3_3 = rational.(R1_4 * V_6),
    V_6 = rational.reciprocal(R2_5).
rational.numer(rational.r(Num_3, V_4)) = Num_3.
rational.denom(rational.r(V_3, Den_4)) = Den_4.
rational.abs(rational.r(Num_3, Den_4)) = rational.r(V_5, Den_4) :-
    V_5 = integer.abs(Num_3).
rational.one = rational.r(V_2, V_3) :-
    V_2 = integer.one,
    V_3 = integer.one.
rational.zero = rational.r(V_2, V_3) :-
    V_2 = integer.zero,
    V_3 = integer.one.
:- pragma exceptions(predicate, (rational.(<)), 2, 0, may_throw(user_exception)).
:- pragma exceptions(predicate, (rational.(>)), 2, 0, may_throw(user_exception)).
:- pragma exceptions(predicate, (rational.(=<)), 2, 0, may_throw(user_exception)).
:- pragma exceptions(predicate, (rational.(>=)), 2, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.rational), 2, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.rational), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.from_integer), 2, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.from_integers), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.(+)), 2, 0, will_not_throw).
:- pragma exceptions(function, (rational.(-)), 2, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.(+)), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.(-)), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.(*)), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.(/)), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.numer), 2, 0, will_not_throw).
:- pragma exceptions(function, (rational.denom), 2, 0, will_not_throw).
:- pragma exceptions(function, (rational.abs), 2, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.reciprocal), 2, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.one), 1, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.zero), 1, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.rational_norm), 3, 0, may_throw(user_exception)).
:- pragma exceptions(function, (rational.cmp), 3, 0, may_throw(user_exception)).
:- pragma termination_info(rational.'<'((builtin.in), (builtin.in)), finite(0, [no, no]), can_loop).
:- pragma termination_info(rational.'>'((builtin.in), (builtin.in)), finite(0, [no, no]), can_loop).
:- pragma termination_info(rational.'=<'((builtin.in), (builtin.in)), finite(0, [no, no]), can_loop).
:- pragma termination_info(rational.'>='((builtin.in), (builtin.in)), finite(0, [no, no]), can_loop).
:- pragma termination_info(rational.rational((builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.rational((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.from_integer((builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.from_integers((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.'+'((builtin.in)) = (builtin.out), finite(0, [yes, no]), cannot_loop).
:- pragma termination_info(rational.'-'((builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.'+'((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.'-'((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.'*'((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.'/'((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.numer((builtin.in)) = (builtin.out), finite(-2, [yes, no]), cannot_loop).
:- pragma termination_info(rational.denom((builtin.in)) = (builtin.out), finite(-2, [yes, no]), cannot_loop).
:- pragma termination_info(rational.abs((builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.reciprocal((builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info((rational.one) = (builtin.out), infinite, can_loop).
:- pragma termination_info((rational.zero) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.rational_norm((builtin.in), (builtin.in)) = (builtin.out), infinite, can_loop).
:- pragma termination_info(rational.cmp((builtin.in), (builtin.in)) = (builtin.out), finite(0, [no, no, no]), can_loop).
