ScalerByLeo/Src/Scaler/MinMax/MinMax.mqh

162 lines
5.1 KiB
MQL5

2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
//| MinMax.mqh |
2026-09-16 09:57:52 -05:00
//| Copyright 2026, Leo. |
2026-09-16 08:06:10 -05:00
//| https://www.mql5.com |
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
#property copyright "Copyright 2026, Leo."
#property link "https://www.mql5.com/en/users/nique_372"
#property strict
2026-09-16 10:10:34 -05:00
#ifndef SCALERBYLEO_SRC_SCALER_MINMAX_MINMAX_MQH
#define SCALERBYLEO_SRC_SCALER_MINMAX_MINMAX_MQH
2026-09-16 09:57:52 -05:00
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
//| |
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
#include "MinMaxBase.mqh"
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
//| |
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
namespace TSN
{
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
//| MaxMin Scaler (CPU) |
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+
2026-09-16 09:57:52 -05:00
template<typename TFlt>
class MaxMinScaler : public MaxMinScalerBase<TFlt>
{
public:
2026-09-16 10:10:34 -05:00
MaxMinScaler(void) { m_type = SCALERBYLEO_SCALER_TYPE_MINMAX; }
2026-09-16 09:57:52 -05:00
~MaxMinScaler(void) {}
//---
__forceinline bool FitTransform(const matrix<TFlt> &X, matrix<TFlt> &out);
bool Transform(const matrix<TFlt> &X, matrix<TFlt> &out);
bool InverseTransform(const matrix<TFlt> &X_scaled, matrix<TFlt> &out);
};
//+------------------------------------------------------------------+
//| |
//+------------------------------------------------------------------+
template<typename TFlt>
__forceinline bool MaxMinScaler::FitTransform(const matrix<TFlt> &X, matrix<TFlt> &out)
{
//---
if(!Fit(X))
return false;
if(!Transform(X, out))
return false;
//---
return true;
}
//+------------------------------------------------------------------+
//| Transform |
//+------------------------------------------------------------------+
template<typename TFlt>
bool MaxMinScaler::Transform(const matrix<TFlt> &X, matrix<TFlt> &out)
{
//---
if(!m_loaded_scaler)
{
m_last_err = SCALERBYLEO_ERR_NOT_TRAINED;
return false;
}
//--- chekeo de rows
const ulong rows = X.Rows();
if(rows == 0)
{
m_last_err = SCALERBYLEO_ERR_EMPTY_INPUT;
return false;
}
//--- chekeo de cols
const ulong total_cols = X.Cols();
const ulong fs = m_min_vals.Size();
if(m_i_start + fs > total_cols)
{
m_last_err = SCALERBYLEO_ERR_SIZE_MISMATCH;
return false;
}
2026-09-16 18:20:12 -05:00
//---
// En caso nos obligen a reoncutr y no coinciden entonces
if(m_reconstruir && fs != total_cols)
2026-09-16 09:57:52 -05:00
{
2026-09-16 18:20:12 -05:00
out = X; // copia optimizada (ya probado, conpensa el overwrite)
// modificamos inplace
for(ulong c = 0; c < fs; c++)
for(ulong r = 0; r < rows; r++)
out[r][m_i_start + c] = TFlt((double(X[r][m_i_start + c]) - m_min_vals[c]) * m_diff_inv[c]);
2026-09-16 09:57:52 -05:00
}
else
{
2026-09-16 18:20:12 -05:00
// De lo contrario exacto asi que inplace
2026-09-16 09:57:52 -05:00
out.Resize(rows, fs);
2026-09-16 18:20:12 -05:00
for(ulong c = 0; c < fs; c++)
for(ulong r = 0; r < rows; r++)
out[r][c] = TFlt((double(X[r][m_i_start + c]) - m_min_vals[c]) * m_diff_inv[c]);
2026-09-16 09:57:52 -05:00
}
//---
return true;
}
//+------------------------------------------------------------------+
//| InverseTransform |
//+------------------------------------------------------------------+
template<typename TFlt>
bool MaxMinScaler::InverseTransform(const matrix<TFlt> &X_scaled, matrix<TFlt> &out)
{
//---
if(!m_loaded_scaler)
{
m_last_err = SCALERBYLEO_ERR_NOT_TRAINED;
return false;
}
//--- chekeo de rows
const ulong rows = X_scaled.Rows();
if(rows == 0)
{
m_last_err = SCALERBYLEO_ERR_EMPTY_INPUT;
return false;
}
//--- chekeo de cols
const ulong total_cols = X_scaled.Cols();
const ulong fs = m_min_vals.Size();
if(m_i_start + fs > total_cols)
{
m_last_err = SCALERBYLEO_ERR_SIZE_MISMATCH;
return false;
}
2026-09-16 18:51:57 -05:00
//---
// En caso nos obligen a reoncutr y no coinciden entonces
if(m_reconstruir && fs != total_cols)
2026-09-16 09:57:52 -05:00
{
2026-09-16 18:51:57 -05:00
out = X_scaled; // copia optimizada (ya probado, conpensa el overwrite)
// modificamos inplace
for(ulong c = 0; c < fs; c++)
for(ulong r = 0; r < rows; r++)
out[r][m_i_start + c] = TFlt((double(X_scaled[r][m_i_start + c]) * m_diff[c]) + m_min_vals[c]);
2026-09-16 09:57:52 -05:00
}
else
{
2026-09-16 18:51:57 -05:00
// De lo contrario exacto asi que inplace
2026-09-16 09:57:52 -05:00
out.Resize(rows, fs);
2026-09-16 18:51:57 -05:00
for(ulong c = 0; c < fs; c++)
for(ulong r = 0; r < rows; r++)
out[r][c] = TFlt((double(X_scaled[r][m_i_start + c]) * m_diff[c]) + m_min_vals[c]);
2026-09-16 09:57:52 -05:00
}
//---
return true;
}
}
2026-09-16 10:10:34 -05:00
#endif // SCALERBYLEO_SRC_SCALER_MINMAX_MINMAX_MQH
2026-09-16 08:06:10 -05:00
//+------------------------------------------------------------------+