refactor: Standardize TensorFlowNET.Keras/Losses/*tags/v0.110.0-LSTM-Model
@@ -1,8 +1,9 @@ | |||||
namespace Tensorflow.Keras.Losses; | namespace Tensorflow.Keras.Losses; | ||||
public class BinaryCrossentropy : LossFunctionWrapper, ILossFunc | |||||
public class BinaryCrossentropy : LossFunctionWrapper | |||||
{ | { | ||||
float label_smoothing; | float label_smoothing; | ||||
public BinaryCrossentropy( | public BinaryCrossentropy( | ||||
bool from_logits = false, | bool from_logits = false, | ||||
float label_smoothing = 0, | float label_smoothing = 0, | ||||
@@ -15,7 +16,6 @@ public class BinaryCrossentropy : LossFunctionWrapper, ILossFunc | |||||
this.label_smoothing = label_smoothing; | this.label_smoothing = label_smoothing; | ||||
} | } | ||||
public override Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | public override Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | ||||
{ | { | ||||
var sum = keras.backend.binary_crossentropy(y_true, y_pred, from_logits: from_logits); | var sum = keras.backend.binary_crossentropy(y_true, y_pred, from_logits: from_logits); | ||||
@@ -1,8 +1,9 @@ | |||||
namespace Tensorflow.Keras.Losses; | namespace Tensorflow.Keras.Losses; | ||||
public class CategoricalCrossentropy : LossFunctionWrapper, ILossFunc | |||||
public class CategoricalCrossentropy : LossFunctionWrapper | |||||
{ | { | ||||
float label_smoothing; | float label_smoothing; | ||||
public CategoricalCrossentropy( | public CategoricalCrossentropy( | ||||
bool from_logits = false, | bool from_logits = false, | ||||
float label_smoothing = 0, | float label_smoothing = 0, | ||||
@@ -15,7 +16,6 @@ public class CategoricalCrossentropy : LossFunctionWrapper, ILossFunc | |||||
this.label_smoothing = label_smoothing; | this.label_smoothing = label_smoothing; | ||||
} | } | ||||
public override Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | public override Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | ||||
{ | { | ||||
// Try to adjust the shape so that rank of labels = rank of logits - 1. | // Try to adjust the shape so that rank of labels = rank of logits - 1. | ||||
@@ -1,28 +1,22 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class CosineSimilarity : LossFunctionWrapper | |||||
{ | { | ||||
public class CosineSimilarity : LossFunctionWrapper, ILossFunc | |||||
protected int axis = -1; | |||||
public CosineSimilarity( | |||||
string reduction = null, | |||||
int axis = -1, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "cosine_similarity" : name) | |||||
{ | { | ||||
protected int axis=-1; | |||||
public CosineSimilarity( | |||||
string reduction = null, | |||||
int axis=-1, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "cosine_similarity" : name) | |||||
{ | |||||
this.axis = axis; | |||||
} | |||||
this.axis = axis; | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_true_normalize = nn_impl.l2_normalize(y_true, axis : this.axis); | |||||
Tensor y_pred_normalize = nn_impl.l2_normalize(y_pred, axis: this.axis); | |||||
return -math_ops.reduce_sum(y_true_normalize * y_pred_normalize, axis : constant_op.constant(this.axis)); | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred = null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_true_normalize = nn_impl.l2_normalize(y_true, axis: this.axis); | |||||
Tensor y_pred_normalize = nn_impl.l2_normalize(y_pred, axis: this.axis); | |||||
return -math_ops.reduce_sum(y_true_normalize * y_pred_normalize, axis: constant_op.constant(this.axis)); | |||||
} | } | ||||
} | |||||
} |
@@ -1,36 +1,29 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class Huber : LossFunctionWrapper | |||||
{ | { | ||||
public class Huber : LossFunctionWrapper, ILossFunc | |||||
protected Tensor delta = tf.Variable(1.0); | |||||
public Huber( | |||||
string reduction = null, | |||||
Tensor delta = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "huber" : name) | |||||
{ | { | ||||
protected Tensor delta = tf.Variable(1.0) ; | |||||
public Huber ( | |||||
string reduction = null, | |||||
Tensor delta = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "huber" : name) | |||||
{ | |||||
this.delta = delta==null? this.delta: delta; | |||||
} | |||||
this.delta = delta == null ? this.delta : delta; | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_cast = math_ops.cast(y_pred, dtype: TF_DataType.TF_FLOAT); | |||||
Tensor y_true_cast = math_ops.cast(y_true, dtype: TF_DataType.TF_FLOAT); | |||||
Tensor delta = math_ops.cast(this.delta, dtype: TF_DataType.TF_FLOAT); | |||||
Tensor error = math_ops.subtract(y_pred_cast, y_true_cast); | |||||
Tensor abs_error = math_ops.abs(error); | |||||
Tensor half = ops.convert_to_tensor(0.5, dtype: abs_error.dtype); | |||||
return gen_math_ops.mean(array_ops.where_v2(abs_error <= delta, | |||||
half * math_ops.pow(error, 2), | |||||
half * math_ops.pow(delta, 2) + delta * (abs_error - delta)), | |||||
ops.convert_to_tensor(-1)); | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred = null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_cast = math_ops.cast(y_pred, dtype: TF_DataType.TF_FLOAT); | |||||
Tensor y_true_cast = math_ops.cast(y_true, dtype: TF_DataType.TF_FLOAT); | |||||
Tensor delta = math_ops.cast(this.delta, dtype: TF_DataType.TF_FLOAT); | |||||
Tensor error = math_ops.subtract(y_pred_cast, y_true_cast); | |||||
Tensor abs_error = math_ops.abs(error); | |||||
Tensor half = ops.convert_to_tensor(0.5, dtype: abs_error.dtype); | |||||
return gen_math_ops.mean(array_ops.where_v2(abs_error <= delta, | |||||
half * math_ops.pow(error, 2), | |||||
half * math_ops.pow(delta, 2) + delta * (abs_error - delta)), | |||||
ops.convert_to_tensor(-1)); | |||||
} | } | ||||
} | } |
@@ -1,27 +1,20 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using Tensorflow.Operations; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class LogCosh : LossFunctionWrapper | |||||
{ | { | ||||
public class LogCosh : LossFunctionWrapper, ILossFunc | |||||
{ | |||||
public LogCosh( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "log_cosh" : name){ } | |||||
public LogCosh( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "log_cosh" : name) | |||||
{ } | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
Tensor x = y_pred_dispatch - y_true_cast; | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred = null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
Tensor x = y_pred_dispatch - y_true_cast; | |||||
return gen_math_ops.mean(x + gen_nn_ops.softplus(-2.0 * x) - math_ops.cast(math_ops.log(tf.Variable(2.0)), x.dtype), | |||||
ops.convert_to_tensor(-1)); | |||||
} | |||||
return gen_math_ops.mean(x + gen_nn_ops.softplus(-2.0 * x) - math_ops.cast(math_ops.log(tf.Variable(2.0)), x.dtype), | |||||
ops.convert_to_tensor(-1)); | |||||
} | } | ||||
} | |||||
} |
@@ -1,55 +1,51 @@ | |||||
using System; | |||||
using Tensorflow.Keras.Utils; | |||||
using Tensorflow.Keras.Utils; | |||||
namespace Tensorflow.Keras.Losses | |||||
namespace Tensorflow.Keras.Losses; | |||||
/// <summary> | |||||
/// Loss base class. | |||||
/// </summary> | |||||
public abstract class Loss : ILossFunc | |||||
{ | { | ||||
/// <summary> | |||||
/// Loss base class. | |||||
/// </summary> | |||||
public abstract class Loss | |||||
protected string reduction; | |||||
protected string name; | |||||
bool _allow_sum_over_batch_size; | |||||
protected bool from_logits = false; | |||||
string _name_scope; | |||||
public string Reduction => reduction; | |||||
public string Name => name; | |||||
public Loss(string reduction = ReductionV2.AUTO, | |||||
string name = null, | |||||
bool from_logits = false) | |||||
{ | { | ||||
protected string reduction; | |||||
protected string name; | |||||
bool _allow_sum_over_batch_size; | |||||
protected bool from_logits = false; | |||||
string _name_scope; | |||||
public string Reduction => reduction; | |||||
public string Name => name; | |||||
public Loss(string reduction = ReductionV2.AUTO, | |||||
string name = null, | |||||
bool from_logits = false) | |||||
{ | |||||
this.reduction = reduction == null ? ReductionV2.SUM_OVER_BATCH_SIZE : reduction; | |||||
this.name = name; | |||||
this.from_logits = from_logits; | |||||
_allow_sum_over_batch_size = false; | |||||
} | |||||
this.reduction = reduction == null ? ReductionV2.SUM_OVER_BATCH_SIZE : reduction; | |||||
this.name = name; | |||||
this.from_logits = from_logits; | |||||
_allow_sum_over_batch_size = false; | |||||
} | |||||
public virtual Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | |||||
{ | |||||
throw new NotImplementedException(""); | |||||
} | |||||
public abstract Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1); | |||||
public Tensor Call(Tensor y_true, Tensor y_pred, Tensor sample_weight = null) | |||||
{ | |||||
var losses = Apply(y_true, y_pred, from_logits: from_logits); | |||||
var reduction = GetReduction(); | |||||
return losses_utils.compute_weighted_loss(losses, reduction: reduction, sample_weight: sample_weight); | |||||
} | |||||
public Tensor Call(Tensor y_true, Tensor y_pred, Tensor sample_weight = null) | |||||
{ | |||||
var losses = Apply(y_true, y_pred, from_logits: from_logits); | |||||
var reduction = GetReduction(); | |||||
return losses_utils.compute_weighted_loss(losses, reduction: reduction, sample_weight: sample_weight); | |||||
} | |||||
string GetReduction() | |||||
{ | |||||
return reduction switch | |||||
{ | |||||
ReductionV2.AUTO => ReductionV2.SUM_OVER_BATCH_SIZE, | |||||
_ => reduction | |||||
}; | |||||
} | |||||
void _set_name_scope() | |||||
string GetReduction() | |||||
{ | |||||
return reduction switch | |||||
{ | { | ||||
_name_scope = name; | |||||
} | |||||
ReductionV2.AUTO => ReductionV2.SUM_OVER_BATCH_SIZE, | |||||
_ => reduction | |||||
}; | |||||
} | |||||
void _set_name_scope() | |||||
{ | |||||
_name_scope = name; | |||||
} | } | ||||
} | |||||
} |
@@ -1,16 +1,14 @@ | |||||
using Tensorflow.Keras.Utils; | using Tensorflow.Keras.Utils; | ||||
namespace Tensorflow.Keras.Losses | |||||
namespace Tensorflow.Keras.Losses; | |||||
public abstract class LossFunctionWrapper : Loss | |||||
{ | { | ||||
public class LossFunctionWrapper : Loss | |||||
{ | |||||
public LossFunctionWrapper(string reduction = ReductionV2.AUTO, | |||||
string name = null, | |||||
bool from_logits = false) | |||||
: base(reduction: reduction, | |||||
name: name, | |||||
from_logits: from_logits) | |||||
{ | |||||
} | |||||
} | |||||
public LossFunctionWrapper(string reduction = ReductionV2.AUTO, | |||||
string name = null, | |||||
bool from_logits = false) | |||||
: base(reduction: reduction, | |||||
name: name, | |||||
from_logits: from_logits) | |||||
{ } | |||||
} | } |
@@ -1,23 +1,16 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class MeanAbsoluteError : LossFunctionWrapper | |||||
{ | { | ||||
public class MeanAbsoluteError : LossFunctionWrapper, ILossFunc | |||||
{ | |||||
public MeanAbsoluteError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "mean_absolute_error" : name){ } | |||||
public MeanAbsoluteError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "mean_absolute_error" : name){ } | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
return gen_math_ops.mean(math_ops.abs(y_pred_dispatch - y_true_cast), ops.convert_to_tensor(-1)); | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
return gen_math_ops.mean(math_ops.abs(y_pred_dispatch - y_true_cast), ops.convert_to_tensor(-1)); | |||||
} | } | ||||
} | } |
@@ -1,24 +1,17 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class MeanAbsolutePercentageError : LossFunctionWrapper | |||||
{ | { | ||||
public class MeanAbsolutePercentageError : LossFunctionWrapper, ILossFunc | |||||
{ | |||||
public MeanAbsolutePercentageError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "mean_absolute_percentage_error" : name){ } | |||||
public MeanAbsolutePercentageError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "mean_absolute_percentage_error" : name){ } | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
Tensor diff = math_ops.abs(y_true_cast - y_pred_dispatch) / gen_math_ops.maximum(math_ops.abs(y_true_cast), gen_math_ops.cast(tf.constant(1e-7), y_pred_dispatch.dtype)); | |||||
return gen_math_ops.cast(tf.constant(100), y_pred_dispatch.dtype) * gen_math_ops.mean(diff, ops.convert_to_tensor(-1)); | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
Tensor diff = math_ops.abs(y_true_cast - y_pred_dispatch) / gen_math_ops.maximum(math_ops.abs(y_true_cast), gen_math_ops.cast(tf.constant(1e-7), y_pred_dispatch.dtype)); | |||||
return gen_math_ops.cast(tf.constant(100), y_pred_dispatch.dtype) * gen_math_ops.mean(diff, ops.convert_to_tensor(-1)); | |||||
} | } | ||||
} | } |
@@ -1,23 +1,16 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class MeanSquaredError : LossFunctionWrapper | |||||
{ | { | ||||
public class MeanSquaredError : LossFunctionWrapper, ILossFunc | |||||
{ | |||||
public MeanSquaredError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name==null? "mean_squared_error" : name){ } | |||||
public MeanSquaredError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name==null? "mean_squared_error" : name){ } | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
return gen_math_ops.mean(gen_math_ops.squared_difference(y_pred_dispatch, y_true_cast), ops.convert_to_tensor(-1)); | |||||
} | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
return gen_math_ops.mean(gen_math_ops.squared_difference(y_pred_dispatch, y_true_cast), ops.convert_to_tensor(-1)); | |||||
} | } | ||||
} | } |
@@ -1,33 +1,28 @@ | |||||
using System; | |||||
using System.Collections.Generic; | |||||
using System.Text; | |||||
using static Tensorflow.Binding; | |||||
using static Tensorflow.KerasApi; | |||||
namespace Tensorflow.Keras.Losses; | |||||
namespace Tensorflow.Keras.Losses | |||||
public class MeanSquaredLogarithmicError : LossFunctionWrapper | |||||
{ | { | ||||
public class MeanSquaredLogarithmicError : LossFunctionWrapper, ILossFunc | |||||
{ | |||||
public MeanSquaredLogarithmicError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "mean_squared_logarithmic_error" : name){ } | |||||
public MeanSquaredLogarithmicError( | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "mean_squared_logarithmic_error" : name) | |||||
{ } | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred =null, bool from_logits = false, int axis = -1) | |||||
public override Tensor Apply(Tensor y_true = null, Tensor y_pred = null, bool from_logits = false, int axis = -1) | |||||
{ | |||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
Tensor first_log = null, second_log = null; | |||||
if (y_pred_dispatch.dtype == TF_DataType.TF_DOUBLE) | |||||
{ | |||||
first_log = math_ops.log(math_ops.maximum(y_pred_dispatch, 1e-7) + 1.0); | |||||
second_log = math_ops.log(math_ops.maximum(y_true_cast, 1e-7) + 1.0); | |||||
} | |||||
else | |||||
{ | { | ||||
Tensor y_pred_dispatch = ops.convert_to_tensor(y_pred); | |||||
Tensor y_true_cast = gen_math_ops.cast(y_true, y_pred_dispatch.dtype); | |||||
Tensor first_log=null, second_log=null; | |||||
if (y_pred_dispatch.dtype == TF_DataType.TF_DOUBLE) { | |||||
first_log = math_ops.log(math_ops.maximum(y_pred_dispatch, 1e-7) + 1.0); | |||||
second_log = math_ops.log(math_ops.maximum(y_true_cast, 1e-7) + 1.0); | |||||
} | |||||
else { | |||||
first_log = math_ops.log(math_ops.maximum(y_pred_dispatch, 1e-7f) + 1.0f); | |||||
second_log = math_ops.log(math_ops.maximum(y_true_cast, 1e-7f) + 1.0f); | |||||
} | |||||
return gen_math_ops.mean(gen_math_ops.squared_difference(first_log, second_log), ops.convert_to_tensor(-1)); | |||||
first_log = math_ops.log(math_ops.maximum(y_pred_dispatch, 1e-7f) + 1.0f); | |||||
second_log = math_ops.log(math_ops.maximum(y_true_cast, 1e-7f) + 1.0f); | |||||
} | } | ||||
return gen_math_ops.mean(gen_math_ops.squared_difference(first_log, second_log), ops.convert_to_tensor(-1)); | |||||
} | } | ||||
} | |||||
} |
@@ -2,7 +2,7 @@ | |||||
namespace Tensorflow.Keras.Losses; | namespace Tensorflow.Keras.Losses; | ||||
public class SigmoidFocalCrossEntropy : LossFunctionWrapper, ILossFunc | |||||
public class SigmoidFocalCrossEntropy : LossFunctionWrapper | |||||
{ | { | ||||
float _alpha; | float _alpha; | ||||
float _gamma; | float _gamma; | ||||
@@ -20,7 +20,6 @@ public class SigmoidFocalCrossEntropy : LossFunctionWrapper, ILossFunc | |||||
_gamma = gamma; | _gamma = gamma; | ||||
} | } | ||||
public override Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | public override Tensor Apply(Tensor y_true, Tensor y_pred, bool from_logits = false, int axis = -1) | ||||
{ | { | ||||
y_true = tf.cast(y_true, dtype: y_pred.dtype); | y_true = tf.cast(y_true, dtype: y_pred.dtype); | ||||
@@ -1,41 +1,41 @@ | |||||
using static Tensorflow.Binding; | using static Tensorflow.Binding; | ||||
namespace Tensorflow.Keras.Losses | |||||
namespace Tensorflow.Keras.Losses; | |||||
public class SparseCategoricalCrossentropy : LossFunctionWrapper | |||||
{ | { | ||||
public class SparseCategoricalCrossentropy : LossFunctionWrapper, ILossFunc | |||||
private bool _from_logits = false; | |||||
public SparseCategoricalCrossentropy( | |||||
bool from_logits = false, | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "sparse_categorical_crossentropy" : name) | |||||
{ | |||||
_from_logits = from_logits; | |||||
} | |||||
public override Tensor Apply(Tensor target, Tensor output, bool from_logits = false, int axis = -1) | |||||
{ | { | ||||
private bool _from_logits = false; | |||||
public SparseCategoricalCrossentropy( | |||||
bool from_logits = false, | |||||
string reduction = null, | |||||
string name = null) : | |||||
base(reduction: reduction, name: name == null ? "sparse_categorical_crossentropy" : name) | |||||
target = tf.cast(target, dtype: TF_DataType.TF_INT64); | |||||
if (!_from_logits) | |||||
{ | { | ||||
_from_logits = from_logits; | |||||
var epsilon = tf.constant(KerasApi.keras.backend.epsilon(), output.dtype); | |||||
output = tf.clip_by_value(output, epsilon, 1 - epsilon); | |||||
output = tf.log(output); | |||||
} | } | ||||
public override Tensor Apply(Tensor target, Tensor output, bool from_logits = false, int axis = -1) | |||||
// Try to adjust the shape so that rank of labels = rank of logits - 1. | |||||
var output_shape = array_ops.shape_v2(output); | |||||
var output_rank = output.shape.ndim; | |||||
var target_rank = target.shape.ndim; | |||||
var update_shape = target_rank != output_rank - 1; | |||||
if (update_shape) | |||||
{ | { | ||||
target = tf.cast(target, dtype: TF_DataType.TF_INT64); | |||||
if (!_from_logits) | |||||
{ | |||||
var epsilon = tf.constant(KerasApi.keras.backend.epsilon(), output.dtype); | |||||
output = tf.clip_by_value(output, epsilon, 1 - epsilon); | |||||
output = tf.log(output); | |||||
} | |||||
// Try to adjust the shape so that rank of labels = rank of logits - 1. | |||||
var output_shape = array_ops.shape_v2(output); | |||||
var output_rank = output.shape.ndim; | |||||
var target_rank = target.shape.ndim; | |||||
var update_shape = target_rank != output_rank - 1; | |||||
if (update_shape) | |||||
{ | |||||
target = array_ops.reshape(target, new int[] { -1 }); | |||||
output = array_ops.reshape(output, new int[] { -1, output_shape[-1].numpy() }); | |||||
} | |||||
return tf.nn.sparse_softmax_cross_entropy_with_logits(target, output); | |||||
target = array_ops.reshape(target, new int[] { -1 }); | |||||
output = array_ops.reshape(output, new int[] { -1, output_shape[-1].numpy() }); | |||||
} | } | ||||
return tf.nn.sparse_softmax_cross_entropy_with_logits(target, output); | |||||
} | } | ||||
} | |||||
} |