The following 2 methods are intended to calculate the length of loan(number of monthly payments that have to be paid and the interest due in the loan, respectively, given the parameters in which r is the monthly interest rate(APR), A is the loan amount(principal), P is the monthly payment and N is the number of payments that need to be made. However neither of the methods calculate correctly. How do I fix them so that they provide the number of months the payment must be made and the interest accrued?
public static double loanLength(double r, double A, double P){
double N = (Math.log(1 / (1 - ((r * A) / P)))) / Math.log(1 + r);
return N;
}
public static double loanInterest(double P, double N, double A){
double I = ((P * N) - A);
return I;
}
According to your example input it's just an arithmetic error.
The line double N = (Math.log(1 / (1 - ((r * A) / P)))) / Math.log(1 + r); has some calculations in it. The one that fails (or results in NaN) is Math.log(1 / (1 - ((r * A) / P))).
If we insert the example values: Math.log(1 / (1 - ((0.1 * 10000) / 500))) and we calculate that out:
1. Math.log(1 / (1 - ((0.1 * 10000) / 500)))
2. Math.log(1 / (1 - (1000 / 500)))
3. Math.log(1 / (1 - 2))
4. Math.log(1 / -1)
5. Math.log(-1) // <-- here happens the error
A logarithm of a number smaller/equals than 0 is not defined. So your equation is wrong
This site explains that the interest rate and payment have to be for the same period.
I guess in your case 10% is per year, while 500 is per month. So you need to divide 10 or multiply 500 by 12 to make them fit together. Otherwise, your calculation will give you the duration for a loan with 10%/500payment per month or per year (or any duration really), which can never be payed back: in every period there is 1000 interest, but only 500 payment.
Hence, log(-x) produces NaN, meaning you can never pay back.
Related
I am trying to calculate monthly loan payments the formula Loan Payment = Amount / Discount Factor on www.thebalance.com
According to the website discount factor is calculated with this formula (D) = {[(1 + i) ^n] - 1} / [i(1 + i)^n] I tried interpreting this into Java and came up with
double discountFactor = (Math.pow((1 + interest), numberOfPayments) - 1) / Math.pow(interest * (1 + interest), numberOfPayments);
But it outputs infinityam not so good with Math, can someone help point out the issue?
double discountFactor = (Math.pow((1 + interest), numberOfPayments) - 1) /
(interest * Math.pow((1 + interest), numberOfPayments));
interest is not part of the power, it should be outside power.
put the 'interest' outside the second power function not inside.
double discountFactor = (Math.pow((1 + interest),numberOfPayments)-1)/(interest*Math.pow((1+interest),numberOfPayments));
I am not very familiar with how to alter the range of both Math.random or a new Random() to generate a double like this. I need to be able to generate a double between -10 and 25 cents (my program is dealing with money; hence why I said cents). And a separate instance is generating a random double between 90 and -75 cents. I saw this when I was searching for my answer:
double result = Math.random() * (upper - lower) + lower;
But when I implemented the idea into my code, the range didn't seem to work when using a range between a positive and a negative number...
I tested it with the upper limit of 0.25 and lower of -0.10, but noticed it printed 0.3567587946356543 at one instance of the test I did. So by this I concluded that I obviously didn't adjust the range correctly..
Please help :(
This is my first time using stackoverflow so please go easy on me, I will elaborate if anything I said didn't make sense..
This is my existing method using this code:
public double variation(double price){
//formula: (Math.random() * range) + min; where range = max - min
//80% of the time returns amount between -10 & 25 cents
if(Math.random() > 0.19){
return (Math.random() * 0.35) - 0.10;
}
//20% of the time returns amount between -75 & 90 cents
return (Math.random() * 1.65) - 0.75;
}
I know the method takes in a double price that it doesn't use; it's part of the teacher's requirements to take in a double price but to disregard its value. So ignore that please.
Now you have included all your code in the question, so my answer is changed to:
When it printed 0.3567587946356543 then it comes from the 20% part with range -.75 to 0.90 when the first Math.random() call in if(Math.random() > 0.19){ becomes false.
Old answer:
I think you forgot the minus at the lower value:
double upper = 0.25;
double lower = -0.10;
double result = Math.random() * (upper - lower) + lower;
To generate between -10 and 25, try doing :-
Random r = new Random();
int d = r.nextInt(35)+1;
d = d - 10;
double result = d/100.0;
or a one liner
double result = ((r.nextInt(35)+1)-10)/100.0;
Looks like your formula is actually correct:
double result = Math.random() * (upper - lower) + lower;
You can test it by putting the min and max possible random (which is zero, 1)
Random Value | Result
---------------------------
0 | -0.1 (lower)
1 | 0.25
0.5 | 0.075
0.01 | -0.0965
Working back to get the Random value for the result to be 0.356758795, the Math.random() must return 1.305025128 which is not gonna be the case. :)
Having said that, Apache Commons3 has this nifty method RandomUtils.nextDouble(double startInclusive, double endInclusive); that does it for you.
To get an output with a long decimal:
it's a little bit rough, but it gets the job done.
Random rand = new Random();// creates 'Random' method
int number = rand.nextInt(35)+1;// gets a random integer out of 35
double randDouble = rand.nextDouble();//gets a random double
double finalNumber = ((number + randDouble)-10)/100;//adds the integer and the double,
//subtracts ten, and divides by 100
System.out.println(finalNumber);// prints the number
Here are some examples of the output (copied and pasted exactly).
0.22748959958842008
0.1963085030978741
0.17300671109908058
-0.002656673961685705
-0.08854411636457332
0.03578255664449403
To get an output with a two digit output:
Random rand = new Random(); // creates 'Random' method
float x = rand.nextInt(35)+1; // gets a random integer(0 through 35)
float y = x - 10; // subtracts that number by ten(making the new range -10 through 25)
float z = y/100; // puts number in decimal form
NOTICE this line int number = rand.nextInt(35)+1(in the long decimal version). The reason you have to do +1 at the end is because Java understands 1 as 0. see chart below
JAVA |0 1 2 3 4 5
-------|-----------
HUMANS |1 2 3 4 5 6
I took 400.0 and - 400.0 for example.
double min = 400.0;
double max = 2 * min;
System.out.println(Math.random() * max - min);
And the output is
138.0921773815627
212.7567891431654
9.063135840057157
-256.8594518458244
-99.84573995806142
116.53331370219462
33.29613621235126
The formula to compute the monthly payment is as follows:
monthlyPayment = (loanAmount x monthlyInterestRate) / (1 – (1 / (1 + monthlyInterestRate)numberOfYears x 12 ))
In the above formula, you have to compute (1 + monthlyInterestRate)numberOfYears x 12 ). The pow(a,b) method in the Java API Math class can be used to compute ab.
so how to put this in pow(a,b) method ?
The javadoc for the java.lang.Math class might help you here. Is there something specific you don't understand about that?
So the code to compute the b power of a should look something like this:
double result = Math.pow(a, b);
The formula you have does not look quite right. From Exact_formula_for_monthly_payment The formula should be
P= (L i)/(1- 1/(1+i)^n )
Where L is the loan amount, i is the monthly interest, and n number of periods. In your formula
monthlyPayment = (loanAmount x monthlyInterestRate) / (1 – (1 / (1 + monthlyInterestRate)numberOfYears x 12 ))
the exponential sign has been missed out. I think you want
monthlyPayment = (loanAmount x monthlyInterestRate) / (1 – (1 / (1 + monthlyInterestRate) ^ (numberOfYears x 12) ))
To calculate this in java you would want
monthlyPayment = (loanAmount * monthlyInterestRate) /
(1 – (1 / Math.pow(1 + monthlyInterestRate,numberOfYears * 12)));
Which could be simplified to
monthlyPayment = (loanAmount * monthlyInterestRate) /
(1 – Math.pow(1 + monthlyInterestRate,-numberOfYears * 12));
using a negative exponent.
I am supposed to make a monthly payment calculator in java with the given formula.
The formula for me to use is
M = P * i/ 1 - (1+i)^-n
where
P is the loan principal (i.e. the amount borrowed)
i is monthly interest rate (annual_interest_rate / 12; expressed as decimal)
N is time (number of monthly payments in total years of loan; i.e. years * 12)
The code below is my attempted function to get the monthly payment.
But if I put in 6 years with a loan amount of 200, I get 140 using the formula.
I am stumped as to why I get that number. Any help would be appreciated
public static int calMonthlyPay(double loanAmt, int y) {
double m = 0.0, interest = 0.0, annualIRate = 0.0;
double months = 0.0;
months = y * 12;
annualIRate = getAnnualIRate(y);
interest = annualIRate / 12;
System.out.println(interest);
System.out.println(months);
System.out.println(loanAmt);
System.out.println(y);
m = (loanAmt * (interest - Math.pow((1 + interest), -months))); // This is my formula calculation
System.out.println(m);
return 0;
}
private static double getAnnualIRate(int y) {
switch (y) {
case 2:
return 5.7;
case 3:
return 6.2;
case 4:
return 6.8;
case 5:
return 7.5;
case 6:
return 8.4;
default:
return 8.4;
}
}
If I understood your formula right, it should be:
m = loanAmt * interest - Math.pow(1 + interest, -months);
What you have now is :
m = (loanAmt * (interest / 1 - Math.pow((1 + interest), -months))) =
(loanAmt * (interest - Math.pow((1 + interest), -months)))
You should use the parentheses correctly :
m = loanAmt * (interest / (1 - Math.pow(1 + interest, -months)));
Your formula is incorrect, it need to be
loanAmt * (interest / (1 - Math.pow (1 + interest, -months)));
And there's a error in interest value formula, it need to be
interest = annualIRate / 100 / 12;
So your method calMonthlyPay(200, 6) gives 3 now, which is correct.
I'm trying to make a program that calculates the required score to level in a game and the equation works fine on my calculator but not when i try changing it to work with java.
the equation is 5,000 / 3 * (4n^3 - 3n^2 - n) + 1.25 * 1.8^(n - 60) for example level 49 you should need to have a total score of 772240000 points and the calculator gives this answer but my java program doesn't. here is the code i tried.
for (int i = 0; i <= 100; i++) {
double score = (double) ((5000 / 3) * (Math.pow(4 * i, 3) - Math.pow(3 * i, 2) - i) + (1.25 * Math.pow(1.8, i - 60)));
System.out.println("Level " + i + " requires " + (long) score);
}
This doesnt seem to work right and gives 12513130000 as the required points for lvl 49. If anyone can get it to work would you miind explaining what i did wrong.
You're messing up your Math.pow calls, but you can avoid some of them entirely:
double score = (double) ((5000 / 3) * (4 * i * i * i - 3 * i * i - i) + (1.25 * Math.pow(1.8, i - 60)));
Here's what's wrong: Math.pow(4 * i, 3) is actually (4i)^3 and not 4(i^3). To do the latter, you would need the following:
4 * Math.pow(i, 3)
I'm not entirely sure about the integer division part (you are casting it to double), but you may have to change 5000 / 3 to 5000.0 / 3.
Your problem is inside Math.pow - you're multiplying your index value by a scalar each time.
4 * Math.pow(i, 3)
And
3 * Math.pow(i, 2)
Should fix it.
Edit: And the integer division mentioned in other answers.