Для целых чисел все просто, как уже верно заметил
Stalker_RED достаточно взять остаток от деления на 10
n % 10
Но вот с дробными числами все намного интереснее. Потенциально, можно получить целое представление последовательно умножая число на 10 (сдвигая тем самым десятичную точку вправо), а после воспользоваться предыдущим приемом. Но проблема тут в том, что потенциально такая последовательность может оказаться бесконечной и такой алгоритм зациклится.
Если обратится к стандарту IEEE 754, то можно узнать, что в 64 битах можно точно представить не более 16 десятичных разрядов, а это уже можно использовать как ограничитель, так как при превышении 16 сдвигов десятичной точки значение все равно уже не будет точным
const lastDigit = n => {
// в n совсем не то
if (isNaN(n) || !isFinite(n)) return NaN;
// в n целое
if (n % 1 === 0) return n % 10;
// для дробных проще со строкой работать
const s = String(Math.abs(n));
// неточные значения
if (s.length > 16 || s.includes('e')) return NaN;
return +s.slice(-1);
}