Problem overview
A box of candy costs price dollars and you have balance dollars. The method buyCandy must return how many more dollars you would need to buy one more box than you can buy now.
Take price = 4 and balance = 9. You can buy two boxes, which cost 8 dollars. To afford a third box you would need 12 dollars in total, and you have 9, so you are 3 dollars short. The answer is 3.
Approach
The question has three parts, and each becomes one small calculation:
- How many whole boxes can you buy now?
- What is the total cost of one more box than that?
- How much of that total do you not have?
Splitting the work this way keeps each line simple and gives every value a name that says what it means.
Step by step
Step 1: the number of boxes
You can buy balance / price boxes, but only whole ones. In TypeScript, / always does decimal division, so 9 / 4 is 2.25, not 2. There is no separate integer division. To keep the whole part, wrap the quotient in Math.floor, which rounds down. That gives boxes.
For positive numbers, Math.trunc would give the same result. The two differ only for negative values: Math.floor(-9 / 4) is -3, while Math.trunc(-9 / 4) is -2. Here both inputs are positive, so either works.
Step 2: the cost of one more box
One more than boxes is boxes + 1, and each box costs price, so the total is (boxes + 1) * price. The parentheses matter: without them, only the 1 would be multiplied by price. Store the total in balanceNeeded.
Step 3: the missing money
The gap between what you need and what you have is balanceNeeded - balance. Store it in extraBalance.
Step 4: return it
Return extraBalance. The method is meant to give the answer back, not to print it.
The solution in TypeScript
class Solution {
buyCandy(price: number, balance: number): number {
const boxes: number = Math.floor(balance / price);
const balanceNeeded: number = (boxes + 1) * price;
const extraBalance: number = balanceNeeded - balance;
return extraBalance;
}
}
Tracing the example with price = 4 and balance = 9: boxes is Math.floor(2.25), which is 2. Then balanceNeeded is 3 * 4 = 12, and extraBalance is 12 - 9 = 3.
Language details
- Division does not truncate. Without
Math.floor,boxeswould be2.25, and the final result would be wrong. The typenumbercovers both integers and decimals, so the compiler can't warn you. - Annotations are optional here. TypeScript infers
numberfor all three constants. They are written out to make the types explicit, and they are erased when the code is compiled. - Use
const. None of the three values changes after it is set.
You can see the effect of skipping the rounding with the example. Without it, boxes would be 2.25, the total would be (2.25 + 1) * 4 = 13, and the result would be 4 instead of 3. A fractional number of boxes gives a price that nobody can actually pay.
Complexity
The method does a fixed number of arithmetic operations whatever the input values are, so it runs in O(1) time and uses O(1) extra space.
Edge cases and common mistakes
- An exact multiple. With
price = 4andbalance = 8, you can buy 2 boxes with nothing left over, and the answer is4, a full price, not0. The formula gives this correctly:(2 + 1) * 4 - 8 = 4. - Not enough for any box. With
price = 5andbalance = 3,boxesis0, so the answer is5 - 3 = 2. - Zero balance. With
balance = 0, the answer is exactlyprice. - Forgetting to round down. Using
balance / pricedirectly gives a fraction and a wrong total. - Missing parentheses.
boxes + 1 * pricemultiplies first, giving the wrong amount. - Returning the cost instead of the gap. The answer is how much more you need, not the total
balanceNeeded.
Testing
| price | balance | result |
|---|---|---|
| 4 | 9 | 3 |
| 4 | 8 | 4 |
| 4 | 0 | 4 |
| 5 | 3 | 2 |
| 4 | 3 | 1 |