你能在不使用它的情况下改变工厂函数的属性吗?
Can you mutate the properties of a factory function without using this?
我一直在阅读关于使用工厂函数优于 classes 的好处,但是,我无法让它们以类似的方式工作。
例如,classes:
class NumberManager {
constructor(numbers){
this.numbers = numbers;
}
removeNumber(input){
this.numbers = this.numbers.filter( number => number != input )
}
}
n = new NumberManager([1, 2])
n.numbers // --> [1, 2]
n.removeNumber(2)
n.numbers // --> [1]
但是,使用工厂函数:
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
numbers = numbers.filter( number => number != input )
}
return {
numbers,
removeNumber
}
}
n = NumberFactory([1, 2])
n.numbers // --> [1, 2]
n.removeNumber(2)
n.numbers // --> [1, 2]
是否有可能拥有与 classes 相似的自由度(例如,轻松改变属性),而不必使用像 this
这样的东西(它可以打破执行上下文)和new
(如果必须将 class 转换为工厂,这可能会中断)?
在 return 之前将您想要从工厂 return 的对象放入变量中,然后您可以引用该变量并改变对象:
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
instance.numbers = instance.numbers.filter( number => number != input );
};
const instance = { numbers, removeNumber };
return instance;
}
const n = NumberFactory([1, 2]);
console.log(n.numbers); // --> [1, 2]
n.removeNumber(2);
console.log(n.numbers); // --> [1]
除了 @CertainPerformance's ,您还可以为数字变量公开一个 getter(也许还有一个 setter):
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
numbers = numbers.filter( number => number != input );
};
return {
get numbers(){ return numbers },
// And if you want to allow external replacement of numbers:
// set numbers(value){ numbers = value },
removeNumber
};
}
const n = NumberFactory([1, 2]);
console.log(n.numbers); // --> [1, 2]
n.removeNumber(2);
console.log(n.numbers); // --> [1]
或者只是改变数组(使用突变方法而不是 filter
):
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
for(let i = 0; i < numbers.length; ){ // <-- Note that we don't increment i here
if(numbers[i] != input) // <-- Condition goes here
i++
else
numbers.splice(i, 1)
}
};
return {
numbers,
removeNumber
};
}
const n = NumberFactory([1, 2]);
console.log(n.numbers); // --> [1, 2]
n.removeNumber(2);
console.log(n.numbers); // --> [1]
我一直在阅读关于使用工厂函数优于 classes 的好处,但是,我无法让它们以类似的方式工作。
例如,classes:
class NumberManager {
constructor(numbers){
this.numbers = numbers;
}
removeNumber(input){
this.numbers = this.numbers.filter( number => number != input )
}
}
n = new NumberManager([1, 2])
n.numbers // --> [1, 2]
n.removeNumber(2)
n.numbers // --> [1]
但是,使用工厂函数:
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
numbers = numbers.filter( number => number != input )
}
return {
numbers,
removeNumber
}
}
n = NumberFactory([1, 2])
n.numbers // --> [1, 2]
n.removeNumber(2)
n.numbers // --> [1, 2]
是否有可能拥有与 classes 相似的自由度(例如,轻松改变属性),而不必使用像 this
这样的东西(它可以打破执行上下文)和new
(如果必须将 class 转换为工厂,这可能会中断)?
在 return 之前将您想要从工厂 return 的对象放入变量中,然后您可以引用该变量并改变对象:
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
instance.numbers = instance.numbers.filter( number => number != input );
};
const instance = { numbers, removeNumber };
return instance;
}
const n = NumberFactory([1, 2]);
console.log(n.numbers); // --> [1, 2]
n.removeNumber(2);
console.log(n.numbers); // --> [1]
除了 @CertainPerformance's
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
numbers = numbers.filter( number => number != input );
};
return {
get numbers(){ return numbers },
// And if you want to allow external replacement of numbers:
// set numbers(value){ numbers = value },
removeNumber
};
}
const n = NumberFactory([1, 2]);
console.log(n.numbers); // --> [1, 2]
n.removeNumber(2);
console.log(n.numbers); // --> [1]
或者只是改变数组(使用突变方法而不是 filter
):
const NumberFactory = (numbers) => {
const removeNumber = (input) => {
for(let i = 0; i < numbers.length; ){ // <-- Note that we don't increment i here
if(numbers[i] != input) // <-- Condition goes here
i++
else
numbers.splice(i, 1)
}
};
return {
numbers,
removeNumber
};
}
const n = NumberFactory([1, 2]);
console.log(n.numbers); // --> [1, 2]
n.removeNumber(2);
console.log(n.numbers); // --> [1]