改进功能性javascript示例

时间:2017-12-02 18:32:25

标签: javascript functional-programming

所以我有一个使用类的例子,并以面向对象的方式增加员工工资。然后以功能的方式做同样的事情。

class Employee {
    constructor(name, salary) {
        this.name = name;
        this.salary = salary;
    }

    changeSalary(amt) {
        this.salary = this.salary + amt;
    }

    description() {
        console.log(this.name + " makes "+this.salary);
    }
}

var emps = [
    new Employee("Bob", 100000),
    new Employee("Jane", 150000)
];


emps.map(emp => emp.changeSalary(10000));
emps.map(emp => emp.description());


// vs functional

var emps2 = [
    {name:"Bob", salary:100000},
    {name: 'Jane', salary: 150000}
];

const changeSalary = amount => emp => {
    var newEmp = Object.assign({}, emp);
    newEmp.salary = emp.salary + amount;
    return newEmp;
};

const describe = employee => console.log(employee.name+" makes "+employee.salary);

var happyEmployees = emps2.map(changeSalary(10000));

happyEmployees.map(describe);
emps2.map(describe);

这里有2个问题:

  1. 我想知道是否有人可以帮助我进一步重构changeSalary功能。我不能把我的想法包围在任何更多的改进,但似乎我错过了一些东西。

  2. 我尝试使用Object.assign来保持2个数组之间的不变性。除了不变性之外,这里的功能方法与面向对象方法相比有哪些优势?我知道我的函数是纯粹的,但是新的changeSalary函数似乎比简单的ES6类更难理解。此外,它似乎并不真正可重用,因为它期望一个具有工资属性的对象。

2 个答案:

答案 0 :(得分:2)

const changeSalary = amount => emp => Object.assign({}, emp, {salary: emp.salary + amount});

一如既往:为正确的工作选择合适的工具。在这种情况下,我会使用OOP变体,但这是一种意见。

答案 1 :(得分:0)

使用spread in object literals(查看Browser compatibility),可以缩短Object.assign

var emps = [ { name: "Bob" , salary: 100000 }, { name: 'Jane', salary: 150000 }] 

const changeSalary = amount => emp => ({ ...emp, salary: emp.salary + amount })

console.log( JSON.stringify( emps = emps.map( changeSalary(42) ) ) )