Для этой игрушечной задачи задача заключалась в том, чтобы при вводе римской цифры вернуть ее значение в виде числа. С римскими цифрами каждый символ добавляет свое значение к сумме, но когда меньшая цифра стоит перед большей, она вычитается из суммы.
Самой сложной частью определения того, как переводить римские цифры в числа, было выяснить этот шаблон и то, как его реализовать. Я решил, что использование обратного цикла наиболее эффективно для суммирования суммы, поэтому при выполнении цикла я сравнивал каждый элемент с элементом справа (I + 1) и, если он был меньше, вычитал из суммы, в противном случае добавлено к итогу.
Эта игрушечная задача предоставляла вспомогательный объект с именем DIGIT_VALUES, который содержал пары «ключ-значение» римских цифр.
var DIGIT_VALUES = {
I: 1,
V: 5,
X: 10,
L: 50,
C: 100,
D: 500,
M: 1000
};
Итак, с помощью этого вспомогательного объекта я готов настроить свою функцию. Я начну с числа, равного 0, которое я верну в конце функции. Основной частью этой функции будет обратный цикл по входной строке «romanNumeral»:
function translateRomanNumeral (romanNumeral) { var number = 0; for (var i = romanNumeral.length - 1; i > -1; i--) { } return number; }
Внутри цикла я буду сравнивать значение каждого элемента с элементом справа от него. Если элемент слева меньше, его нужно вычесть из «числа». В противном случае он добавляется.
for (var i = romanNumeral.length - 1; i > -1; i--) { if (DIGIT_VALUES[romanNumeral[i]] < DIGIT_VALUES[romanNumeral[i + 1]]) { number -= DIGIT_VALUES[romanNumeral[i]]; } else { number += DIGIT_VALUES[romanNumeral[i]]; } }
Итак, это решает суть переводчика римских цифр, но, конечно, есть крайний случай. Что, если входная строка не является римской цифрой? Что, если это что-то глупое, например, «лошадь»? Тесты в этом случае ожидают, что будет возвращено значение null, если введен недопустимый ввод. В приведенной выше функции NaN возвращается, когда дается недопустимый ввод, поэтому я просто добавил оператор if перед возвратом, который указывает, что если число равно NaN, вместо этого должен быть возвращен null.
if (isNaN(parseFloat(number))) { return "null"; } else { return number; }
Вот и все! Эта функция теперь правильно переводит римские цифры в числа и обрабатывает крайние случаи!
function translateRomanNumeral (romanNumeral) { var number = 0; for (var i = romanNumeral.length - 1; i > -1; i--) { if (DIGIT_VALUES[romanNumeral[i]] < DIGIT_VALUES[romanNumeral[i + 1]]) { number -= DIGIT_VALUES[romanNumeral[i]]; } else { number += DIGIT_VALUES[romanNumeral[i]]; } } if (isNaN(parseFloat(number))) { return "null"; } else { return number; } }