[英]Do JavaScript classes have a method equivalent to Python classes' __call__?
在Python中,您可以为类实现__call__()
,以便调用类本身的实例来执行__call__()
方法。
class Example:
def __call__(self):
print("the __call__ method")
e = Example()
e() # "the __call__ method"
JavaScript类有一个等效的方法吗?
编辑
结合讨论的摘要答案:
self
,与this
相比) bind
? 执行此操作的唯一方法是构造函数显式返回可以调用的函数。 (在Javascript中,如果没有在构造函数中显式return
,则会return
新创建的实例 - 但是这样的实例将是普通对象,而不是函数。)
class Example { constructor() { return function() { console.log('function running'); } } } const e = new Example(); e();
但这样做真的很奇怪 ,并且不允许你引用原型上的任何属性,或类似的东西。 最好避免它,或者创建一个返回函数的普通函数:
const example = () => () => console.log('function running'); const e = example(); e();
我基本同意@CertainPerformace,这不是你在普通的JS代码中会做的事情。 话虽如此,代理提供了很多可能性,你可以创建一些令人惊讶的接近(表面上)Python的__call__()
。
例如:
class F extends Function{ constructor(someID, arr, n){ super() this.id = someID this.arr = arr this.n = n return new Proxy(this, { apply(target, thisArg, argumentsList) { return target.__call__(...argumentsList); } }) } __call__(a){ // simple mult functions return a * this.n } *[Symbol.iterator](){ // make it iterable for demo purposes yield *this.arr.map(this) // call itself in a map! } } let f = new F("FrankenFunction", [1, 2, 3, 4], 5) // access instance variable console.log("id:", f.id) // call it console.log("calling with 100: ", f(100)) // use the iterator // get multiples of calling this on arr console.log([...f]) // change the __call__ function to power instead F.prototype.__call__ = function(a){ return a ** this.n } // change n to get squares: fn = 2 // call it again with new __call__ console.log("calling with 10:", f(10)) // 10**2 console.log([...f]) // or iterate
我真的不确定这是否是一个好主意,但这是一个有趣的实验。
你可以完成这件事,但是以一种相当奇怪的方式。
JavaScript中没有像__call__()
, __add__()
或__sub__()
的东西--JavaScript不支持运算符重载。
但是,如果您真的想让对象可调用,可以通过为函数提供不同的原型来实现:
function createCallableObject(cls, fn) { // wrap the original function to avoid modifying it const wrapper = (...args) => fn(...args) // set the prototype of the wrapped function so we can call class methods Object.setPrototypeOf(wrapper, cls.prototype) return wrapper } class Example { method() { console.log('This is an instance of class Example') } } function example() { console.log('This is a function') } const obj = createCallableObject(Example, example) obj() // 'This is a function' obj.method() // 'This is an instance of class Example' console.log(obj.constructor) // 'class Example { ... }'
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.