Packages
Tensor library for Gleam/BEAM with a pure Gleam API, zero-copy views, and optional native acceleration
Current section
Files
Jump to
Current section
Files
src/viva_tensor@metrics@regression.erl
-module(viva_tensor@metrics@regression).
-compile([no_auto_import, nowarn_unused_vars, nowarn_unused_function, nowarn_nomatch, inline]).
-define(FILEPATH, "src/viva_tensor/metrics/regression.gleam").
-export([mean_absolute_error/2, mean_squared_error/2, root_mean_squared_error/2, r_squared/2, mean_absolute_percentage_error/2]).
-if(?OTP_RELEASE >= 27).
-define(MODULEDOC(Str), -moduledoc(Str)).
-define(DOC(Str), -doc(Str)).
-else.
-define(MODULEDOC(Str), -compile([])).
-define(DOC(Str), -compile([])).
-endif.
?MODULEDOC(false).
-file("src/viva_tensor/metrics/regression.gleam", 154).
?DOC(false).
-spec materialize_pairs(
viva_tensor@tensor:tensor(),
viva_tensor@tensor:tensor()
) -> {ok, list({float(), float()})} |
{error, viva_tensor@core@error:tensor_error()}.
materialize_pairs(Predictions, Targets) ->
Pred_shape = viva_tensor@tensor:shape(Predictions),
Target_shape = viva_tensor@tensor:shape(Targets),
_pipe = case Pred_shape =:= Target_shape of
true ->
{ok, nil};
false ->
{error, {shape_mismatch, Target_shape, Pred_shape}}
end,
gleam@result:'try'(
_pipe,
fun(_) ->
gleam@result:'try'(
viva_tensor@tensor:try_to_list(Predictions),
fun(Pred_data) ->
gleam@result:'try'(
viva_tensor@tensor:try_to_list(Targets),
fun(Target_data) ->
{ok, gleam@list:zip(Pred_data, Target_data)}
end
)
end
)
end
).
-file("src/viva_tensor/metrics/regression.gleam", 19).
?DOC(false).
-spec mean_absolute_error(
viva_tensor@tensor:tensor(),
viva_tensor@tensor:tensor()
) -> {ok, float()} | {error, viva_tensor@core@error:tensor_error()}.
mean_absolute_error(Predictions, Targets) ->
gleam@result:'try'(
materialize_pairs(Predictions, Targets),
fun(Pairs) -> case Pairs of
[] ->
{error,
{invalid_shape,
<<"mean_absolute_error: empty inputs"/utf8>>}};
_ ->
Total = gleam@list:fold(
Pairs,
+0.0,
fun(Acc, Pair) ->
{P, T} = Pair,
Acc + gleam@float:absolute_value(P - T)
end
),
{ok, case erlang:float(erlang:length(Pairs)) of
+0.0 -> +0.0;
-0.0 -> -0.0;
Gleam@denominator -> Total / Gleam@denominator
end}
end end
).
-file("src/viva_tensor/metrics/regression.gleam", 40).
?DOC(false).
-spec mean_squared_error(
viva_tensor@tensor:tensor(),
viva_tensor@tensor:tensor()
) -> {ok, float()} | {error, viva_tensor@core@error:tensor_error()}.
mean_squared_error(Predictions, Targets) ->
gleam@result:'try'(
materialize_pairs(Predictions, Targets),
fun(Pairs) -> case Pairs of
[] ->
{error,
{invalid_shape,
<<"mean_squared_error: empty inputs"/utf8>>}};
_ ->
Total = gleam@list:fold(
Pairs,
+0.0,
fun(Acc, Pair) ->
{P, T} = Pair,
D = P - T,
Acc + (D * D)
end
),
{ok, case erlang:float(erlang:length(Pairs)) of
+0.0 -> +0.0;
-0.0 -> -0.0;
Gleam@denominator -> Total / Gleam@denominator
end}
end end
).
-file("src/viva_tensor/metrics/regression.gleam", 62).
?DOC(false).
-spec root_mean_squared_error(
viva_tensor@tensor:tensor(),
viva_tensor@tensor:tensor()
) -> {ok, float()} | {error, viva_tensor@core@error:tensor_error()}.
root_mean_squared_error(Predictions, Targets) ->
gleam@result:'try'(
mean_squared_error(Predictions, Targets),
fun(Mse_value) -> case gleam@float:square_root(Mse_value) of
{ok, Value} ->
{ok, Value};
{error, _} ->
{error,
{dimension_error,
<<"root_mean_squared_error: negative MSE"/utf8>>}}
end end
).
-file("src/viva_tensor/metrics/regression.gleam", 83).
?DOC(false).
-spec r_squared(viva_tensor@tensor:tensor(), viva_tensor@tensor:tensor()) -> {ok,
float()} |
{error, viva_tensor@core@error:tensor_error()}.
r_squared(Predictions, Targets) ->
gleam@result:'try'(
materialize_pairs(Predictions, Targets),
fun(Pairs) -> case Pairs of
[] ->
{error, {invalid_shape, <<"r_squared: empty inputs"/utf8>>}};
_ ->
Targets_only = gleam@list:map(
Pairs,
fun(Pair) -> erlang:element(2, Pair) end
),
Mean_t = case erlang:float(erlang:length(Targets_only)) of
+0.0 -> +0.0;
-0.0 -> -0.0;
Gleam@denominator -> gleam@list:fold(
Targets_only,
+0.0,
fun(Acc, V) -> Acc + V end
)
/ Gleam@denominator
end,
Ss_res = gleam@list:fold(
Pairs,
+0.0,
fun(Acc@1, Pair@1) ->
{P, T} = Pair@1,
D = T - P,
Acc@1 + (D * D)
end
),
Ss_tot = gleam@list:fold(
Targets_only,
+0.0,
fun(Acc@2, T@1) ->
D@1 = T@1 - Mean_t,
Acc@2 + (D@1 * D@1)
end
),
case Ss_tot > +0.0 of
true ->
{ok, 1.0 - (case Ss_tot of
+0.0 -> +0.0;
-0.0 -> -0.0;
Gleam@denominator@1 -> Ss_res / Gleam@denominator@1
end)};
false ->
case Ss_res > +0.0 of
true ->
{ok, +0.0};
false ->
{ok, 1.0}
end
end
end end
).
-file("src/viva_tensor/metrics/regression.gleam", 124).
?DOC(false).
-spec mean_absolute_percentage_error(
viva_tensor@tensor:tensor(),
viva_tensor@tensor:tensor()
) -> {ok, float()} | {error, viva_tensor@core@error:tensor_error()}.
mean_absolute_percentage_error(Predictions, Targets) ->
gleam@result:'try'(
materialize_pairs(Predictions, Targets),
fun(Pairs) -> case Pairs of
[] ->
{error,
{invalid_shape,
<<"mean_absolute_percentage_error: empty inputs"/utf8>>}};
_ ->
Has_zero = gleam@list:any(
Pairs,
fun(Pair) ->
{_, T} = Pair,
T =:= +0.0
end
),
case Has_zero of
true ->
{error,
{invalid_shape,
<<"MAPE: target contains zero values"/utf8>>}};
false ->
Total = gleam@list:fold(
Pairs,
+0.0,
fun(Acc, Pair@1) ->
{P, T@1} = Pair@1,
Acc + (case gleam@float:absolute_value(T@1) of
+0.0 -> +0.0;
-0.0 -> -0.0;
Gleam@denominator -> gleam@float:absolute_value(
P - T@1
)
/ Gleam@denominator
end)
end
),
{ok, case erlang:float(erlang:length(Pairs)) of
+0.0 -> +0.0;
-0.0 -> -0.0;
Gleam@denominator@1 -> 100.0 * Total / Gleam@denominator@1
end}
end
end end
).