Почему эти уравнения JavaScript выдают разные (но почти одинаковые) ответы? - PullRequest
0 голосов
/ 19 апреля 2019

Итак, я пытаюсь составить график доходов, полученных за определенный период времени, с включенным «повышением».

Пример.Я зарабатываю 100 долларов в год с 1% (без начисления процентов) каждый год.График будет отображать общий заработанный доход каждый год в течение следующих 50 лет или около того.Итак, 100, 201, 303 и т. Д.

Мой вопрос: почему все эти уравнения дают почти одинаковые, но не точные ответы.Я предполагаю, что моя логика, вероятно, неверна, но я застрял на ней около 2 недель и не вижу своей ошибки.


//This adds the income from 3 months at 1% to another 12 months at 1%

console.log(interestCalc(100.00 * (3.00/12), (1.00/365), ((365.00/12) * 3)) + interestCalc(100.00, (1.00/365), ((365.00/12) * 3) + 365));

//This adds the income from 4 months at 1% to another 11 months at 1%

console.log(interestCalc(100.00 * (4.00/12), (1.00/365), ((365.00/12) * 4)) + interestCalc(100.00 * (11.00/12), (1.00/365), ((365.00/12) * 4) + ((365.00/12) * 11)));

//This adds the income from 10 months at 1% to another 5 months at 1%   

console.log(interestCalc(100.00 * (10.00/12), (1.00/365), ((365.00/12) * 10)) + interestCalc(100.00 * (5.00/12), (1.00/365), ((365.00/12) * 10) + ((365.00/12) * 5)));

//This adds the income from 12 months at 1% to another 3 months at 1%

console.log(interestCalc(100.00, (1.00/365), 365) + interestCalc(100.00 * (3.00/12), (1.00/365), 365 + ((365.00/12) * 3)));


function interestCalc(principal, interestRate, time)
{
  interestRate = interestRate * 0.01;

  return principal + (principal * interestRate * time);
}

-------------------------------------------------------------------

Результаты:

126.3125

126.25694444444443

126.2152777777778

126.3125

Учитывая, что все уравнения должны давать доход за 15-месячный период, я не понимаю, почему они все126,3125Любая помощь будет принята с благодарностью.Я полагаю, что я просто как-то здесь глуп, так что давай, иди в меня, лол.

1 Ответ

2 голосов
/ 19 апреля 2019

Давайте сначала немного перестроим ваши входы и сделаем их "СУХИМ"

Поскольку целью time является количество дней (с использованием целых месяцев), передайте количество месяцев и дайте функции умножить это на 365 / 12 - в функции это 365 / 1200, потому что это также обрабатывает деление процентной ставки на 100

Принципал в ваших вычислениях также умножается на количество месяцев, поэтому давайте передадим это число, 3 и 12 для первого, 4 и 11 для второго и т. Д., И функция теперь будет обрабатывать это тоже - это последнее * m / 12.0 в функции, кстати

//This adds the income from 3 months at 1% to another 12 months at 1%

console.log(
    interestCalc(100.00, 3,  (1.00/365), 3) + 
    interestCalc(100.00, 12, (1.00/365), 15)
);

//This adds the income from 4 months at 1% to another 11 months at 1%

console.log(
    interestCalc(100.00, 4, (1.00/365), 4) + 
    interestCalc(100.00, 11, (1.00/365), 15)
);

//This adds the income from 10 months at 1% to another 5 months at 1%   

console.log(
    interestCalc(100.00, 10, (1.00/365), 10) + 
    interestCalc(100.00, 5, (1.00/365), 15)
);

//This adds the income from 12 months at 1% to another 3 months at 1%

console.log(
    interestCalc(100.00, 12, (1.00/365), 12) + 
    interestCalc(100.00,  3, (1.00/365), 15)
);


function interestCalc(principal, m, interestRate, time)
{
  return (principal + (principal * interestRate * time * 365 / 1200)) * m / 12.0;
}

Выводит то же самое, что и ваш код (за исключением младшей цифры, из-за порядка операций и того факта, что с плавающей запятой в javascript, как любая другая с плавающей запятой - но это не имеет значения для проблемы)

Теперь давайте упростим

Удалить константы, так как они ... константы

function interestCalc(principal, m, interestRate, time)
{
  return (principal + (principal * interestRate * time)) * m;
}

, поскольку interestRate и способ, которым я это написал, principal, всегда одинаковы, удалите их

function interestCalc(principal, m, interestRate, time)
{
  return time * m;
}

Итак, теперь результаты

 3 *  3 + 12 * 15 === 189
 4 *  4 + 11 * 15 === 181
10 * 10 +  5 * 15 === 175
12 * 12 +  3 * 15 === 189

Вы можете увидеть, что ваши вычисления ошибочны, если вы думаете, что все 4 будут иметь одинаковый результат

Также очевидно, что два вычисления, которые совпадают, на самом деле также неверны

Сказав это, я не пытался найти правильную формулу, потому что я не совсем уверен, чего вы пытаетесь достичь

Прочитав вопрос еще раз, я не могу понять, как ваш код даже связан с тем, чего вы пытаетесь достичь

Я предполагаю, что это именно то, что вы хотели сделать - вы хотите рассчитать заработную плату, когда повышение произойдет через 3, 4, 10 или 12 месяцев - т.е. повышение заработной платы может быть частью пути в год

без увеличения, 100 в год в течение 15 месяцев будет 100 * 15/12 = 125

Таким образом, каждый сплит должен давать значение выше 125 (из-за увеличения), но, поскольку у вас будет больше времени на более низком уровне, значения станут ближе к 125

Вы ожидаете, что максимум за 15 месяцев составит 25 в течение первых 3 месяцев плюс 101 в течение следующих 12 месяцев

Минимум будет 100 за 12 месяцев + 101/4 за 3 месяца 25,25 в общей сложности 125,25

Итак, все расчеты ДОЛЖНЫ находиться в диапазоне от 125,25 до 126,00

используя мой код выше и меняя interestCalc функцию:

console.log(
    interestCalc(100.00,  3, 0) + 
    interestCalc(100.00, 12, 1)
);

console.log(
    interestCalc(100.00,  4, 0) + 
    interestCalc(100.00, 11, 1)
);

console.log(
    interestCalc(100.00, 10, 0) + 
    interestCalc(100.00,  5, 1)
);

console.log(
    interestCalc(100.00, 12, 0) + 
    interestCalc(100.00,  3, 1)
);


function interestCalc(principal, time, interestRate) {
    return (principal + principal * interestRate / 100) * time / 12;
}

Как видите, все они попадают в этот диапазон

Теперь давайте сделаем это немного умнее

console.log(calc(100,  3, 1, 15));
console.log(calc(100,  4, 1, 15));
console.log(calc(100, 10, 1, 15));
console.log(calc(100, 12, 1, 15));

function calc(base, firstYearMonths, increase, totalMonths) {
    return (base * firstYearMonths / 12) + (base * (increase + 100) / 100 * (totalMonths - firstYearMonths) / 12);
}

Но это позволяет от 12 до 23 месяцев

Итак, давайте сделаем его еще умнее, потому что теперь мы можем даже справиться с двумя или более повышениями (т. Е. С увеличением зарплаты на 2 или более)

console.log(calc(100,  3, 1, 15));
console.log(calc(100,  4, 1, 15));
console.log(calc(100, 10, 1, 15));
console.log(calc(100, 12, 1, 15));

function calc(base, firstYearMonths, increase, totalMonths) {
    let ret = base * firstYearMonths / 12;
    totalMonths -= firstYearMonths;
    let year = 1;
    while(totalMonths > 0) {
        ret += base * (1 + (increase * year) / 100) * Math.min(totalMonths, 12) / 12;
        totalMonths -= 12;
        year += 1;
    }
    return ret;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...