简而言之:我想要一个类似于PHP的getter,但是在JavaScript中实现。
我的JavaScript仅在Firefox中运行,因此仅使用Mozilla特定的JS也可以。
我找到的制作JS getter的唯一方法需要指定其名称,但我想为所有可能的名称定义getter。我不确定这是否可行,但我非常想知道。
简而言之:我想要一个类似于PHP的getter,但是在JavaScript中实现。
我的JavaScript仅在Firefox中运行,因此仅使用Mozilla特定的JS也可以。
我找到的制作JS getter的唯一方法需要指定其名称,但我想为所有可能的名称定义getter。我不确定这是否可行,但我非常想知道。
代理对象
可以做到这一点!我很高兴它存在!!这里有一个答案:是否有 JavaScript 等效于 Python 的 __getattr__ 方法? 用我的话来说:
var x = new Proxy({}, {
get(target, name) {
return "Its hilarious you think I have " + name
}
})
console.log(x.hair) // logs: "Its hilarious you think I have hair"
代理万岁!查看 MDN 文档:https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Proxy
可在 Chrome、Firefox 和 Node.js 中使用。缺点:不支持 IE - 可恶的 IE。不过很快就会支持。
myProxy.foo('bar')
。 - B T您可以将代理和类组合在一起,使代码看起来像PHP一样美观:
class Magic {
constructor () {
return new Proxy(this, this);
}
get (target, prop) {
return this[prop] || 'MAGIC';
}
}
这个绑定到处理程序,所以你可以使用this代替目标。
注意:与PHP不同,代理处理所有属性访问。
let magic = new Magic();
magic.foo = 'NOT MAGIC';
console.log(magic.foo); // NOT MAGIC
console.log(magic.bar); // MAGIC
您可以查看哪些浏览器支持代理 http://caniuse.com/#feat=proxy。
你能找到的最接近的是__noSuchMethod__(__noSuchMethod__已被弃用),它是JavaScript中与PHP的__call()相当的方法。
遗憾的是,没有__get/__set的等效方法,这是令人遗憾的,因为如果有它们,我们就可以实现__noSuchMethod__,但我还没有看到一种使用__noSuchMethod__来实现属性(如C#中所示)的方法。
var foo = {
__noSuchMethod__ : function(id, args) {
alert(id);
alert(args);
}
};
foo.bar(1, 2);
__noSuchMethod__
等效的东西。 - Ionuț G. Stanundefined
来“欺骗”自己,这也意味着你可以使用get来实际设置参数。var foo = {
args: {},
__noSuchMethod__ : function(id, args) {
if(args === undefined) {
return this.args[id] === undefined ? this[id] : this.args[id]
}
if(this[id] === undefined) {
this.args[id] = args;
} else {
this[id] = args;
}
}
};
Javascript 1.5有getter/settersyntactic sugar。这在John Resig的这里中解释得非常清楚。
它不够通用以用于Web,但Firefox肯定有它们(如果您想在服务器端使用,也可以使用Rhino)。
__get()
函数的东西,我认为Javascript没有提供任何这样的结构。for (o in this) {
if (this.hasOwnProperty(o)) {
this['get_' + o] = function() {
// return this.o -- but you'll need to create a closure to
// keep the correct reference to "o"
};
}
}
我最终使用nickfs的答案构建了自己的解决方案。我的解决方案将为所有属性自动创建get_{propname}和set_{propname}函数。它会在添加函数之前检查函数是否已经存在。这使您可以覆盖默认的get或set方法,并使用自己的实现,而不必担心被覆盖。
for (o in this) {
if (this.hasOwnProperty(o)) {
var creategetter = (typeof this['get_' + o] !== 'function');
var createsetter = (typeof this['set_' + o] !== 'function');
(function () {
var propname = o;
if (creategetter) {
self['get_' + propname] = function () {
return self[propname];
};
}
if (createsetter) {
self['set_' + propname] = function (val) {
self[propname] = val;
};
}
})();
}
}
通过将对象包装在getter函数中,可以轻松地获得类似的结果:
const getProp = (key) => {
const dictionary = {
firstName: 'John',
lastName: 'Doe',
age: 42,
DEFAULT: 'there is no prop like this'
}
return (typeof dictionary[key] === 'undefined' ? dictionary.DEFAULT : dictionary[key]);
}
console.log(getProp('age')) // 42
console.log(getProp('Hello World')) // 'there is no prop like this'