3
\$\begingroup\$

I'm currently taking a JavaScript class. I'm fairly familiar with JavaScript and coding in general, so I decided to teach myself functional programming on the side. It's been great, my teacher's fine with it. However he doesn't really know much about functional programming, so it's difficult for him to critique my designs. I want to be developing good habits and practices, but so far it's been difficult.

Disclaimer: I am aware that JavaScript isn't the ideal language for functional programming for a variety of reasons, but it's what I have to use for now. Also, I can't use jQuery yet.

My current project is a simple program that just displays an investment and its total over x number of years. What I've written works, but if there's a better way to do things I'd like to learn it. I'd like to become the best programmer I can.

Anyways, here's my code:

function inputMask(source, mask = (x) => x) {
    const input = source();
    if (input === null) {
        return;
    };
    const match = mask(input);
    if (match === null) {
        return;
    };
    if (match === undefined) {
        return inputMask(source,mask);
    } else {
        return match;
    };
}

function investment() {
    const investmentAmount = inputMask(() => prompt("How much would you like to invest?"), function(x) {
        const value = parseInt(x);
        if (isNaN(value)) {
            return alert("[ "+x+" ] "+"is not a number.");
        }

        if (value <= 0) {
            return alert("Input must be greater than 0, [ "+value+" ] is not.");
        }

        return value.toFixed(2);
    })

    const investmentYears = inputMask(() => prompt("How many years would you like to invest?"), function(x) {
        const value = parseInt(x);
        if (isNaN(value)) {
            return alert("[ "+x+" ] "+"is not a number.");
        }

        if (value <= 0 || value != value.toFixed(0)) {
            return alert("Input must be an integer greater than 0, [ "+value+" ] is not.");
        }

        return value.toFixed(2);
    })

    const response = (function recur(amount = investmentAmount, accu = "", iterations = investmentYears, i = 0) {
        if (i > iterations) {
            return accu;
        }

        const string = "Year "+i+": $"+amount+"\n";

        return recur((amount*1.08).toFixed(2), accu+string, iterations, i+1);
    })()

    alert(response);

    if(confirm("Again?")) {
        return investment();
    }
}

investment();

\$\endgroup\$
  • 2
    \$\begingroup\$ I don't see any major red flags. I will say that its a bit weird to pass a function toinputMask just to call it immediately there. Why not just pass the return value toinputMask? Also, recur takes 4 arguments, which is a lot. Never make a method take more than 4 arguments. Instead, make it take a single object with 4 properties. Using ES6, the signature can be recur({ amount = investmentAmount, accu = "", iterations = investmentYears, i = 0 }) \$\endgroup\$ – Charlie Martin Oct 24 '16 at 22:52
  • \$\begingroup\$ @CharlieMartin Thanks! inputMask is meant to be to be an input verifier. I originally called it verifyInput but I'm making changes to it, so that name won't be as accurate. I want to be able to call it immediately if the return value from match is undefined. I've been shying away from using a while loop for this, but I will likely change my approach soon. I'll start using objects as parameters, thanks for the tip. \$\endgroup\$ – Ucenna Oct 24 '16 at 23:36
  • 1
    \$\begingroup\$ Have you seen the reactiveX functional programming in JS exercises? If not you might value it... \$\endgroup\$ – Sᴀᴍ Onᴇᴌᴀ Oct 25 '16 at 2:32
  • \$\begingroup\$ @Ucenna Kyle Simpson is authoring a fantastic book on Functional Javascript that is mostly complete. You can read it here: github.com/getify/Functional-Light-JS/blob/master/README.md \$\endgroup\$ – mhodges Oct 25 '16 at 17:08

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.