Одна функция в роли сеттера (геттера) для разных свойств
Можно ли сделать одну функцию геттером либо сеттером для разных элементов так, чтобы в момент вызова знать, для какого свойства объекта она была вызвана?
Поясню, в чём суть: имеется несколько разных свойств у одного объекта, геттер которых должен просто возвращать значение, и больше ничего (а вот сеттер уже делает разные интересные вещи). Хочется не писать для каждого из этих свойств свою функцию-геттер, а сделать одну общую и вызывать каждый раз её. obj= { get a() { return this._a }, set a(v) { // do smth interesting }, get b() { return this._b; }, set b(v) { // do smth else }, get c() { return this._c }, set c(v) { // i don't know what to do :-) } } Хочется это сократить. |
Мб забиндить? Не знаю правда как в этом случае с оптимизацией... Вся надежда на браузер.)
var obj = {}, props = { "a": 1, "b": 1, "c": 1, }; function setGet(isSet, prop, val){ if(isSet){ console.log('set ' + prop + ' = ' + val); return props[prop] = val; }else{ console.log('get ' + prop + ' = ' + props[prop]); return props[prop] } }; for(var prop in props) if(props.hasOwnProperty(prop)){ Object.defineProperty(obj, prop, { set: setGet.bind(obj, true, prop), get: setGet.bind(obj, false, prop), enumerable : true, configurable : true }); } var x = obj.b; obj.b = x + 10; В ES6 есть какраз подходящая для этого няшная штука, Proxy: var props = { "a": 1, "b": 1, "c": 1, }; function setGet(obj, prop, val, proxy){ var isSet = !!proxy; //при get приходит только три аргумента, где третий proxy if(isSet){ console.log('set ' + prop + ' = ' + val); return obj[prop] = val; }else{ console.log('get ' + prop + ' = ' + obj[prop]); return obj[prop] } }; var obj = new Proxy(props, { get: setGet, set: setGet }); var x = obj.b; obj.b = x + 10;Но увы без дополнительной настройки пока работать будет только в FF. Вообще прокси крутая штука, которая может гораздо больше чем я привёл в пример.) |
Не совсем понятное объяснение ((
т.е. у объекта есть свойства у которых есть функции и проблема в том что для каждого свойства есть приходится писать однотипную функцию? тогда почему не использовать наследование? <!Doctype html> <html><head><style></style></head><body> <a id="fr"></a> <script type='text/javascript'> obj_A ={ set:function set (){ return "seter val = " + this.val }, get:function get (){ return "seter val = " + this.val }, } obj_B = function ff (){ this.val = "ничегошеньки в val нетути" } obj_B.prototype = obj_A; var obj = {}; obj.a = new obj_B; obj.b = new obj_B; obj.c = new obj_B; obj.d = new obj_B; obj.a.val = "im A"; obj.b.val = "im B"; obj.c.val = "im C"; document.all["fr"].innerHTML = ""+ obj.a.get() +"<br>"+ obj.b.get() +"<br>"+ obj.c.get() +"<br>"+ obj.d.get(); </script></body></html> |
Aetae, круто, про вот не знал про bind, позор на мою голову. Proxy -- и правда красивое решение, но у меня сразу даже пример ваш не получилось запустить:haha:
По-хорошему, надо попробовать оба варианта и проверить на производительность, ибо у меня она как раз важна, так как рисуется графика. MallSerg, суть именно в геттерах и сеттерах. В том, что потом функция будет вызываться, когда ты просто делаешь obj.a=0 Вот, почитай. http://habrahabr.ru/post/66242/ |
Имхо если производительность сильно критична, то стоит забыть о вызовах функций на каждый чих, и вообще смотреть в сторону всяких TypedArray. (Посоветовал бы asm.js, но в текущем его виде человеку им пользоваться невозможно:) )
|
Aetae, ещё не понял, насколько критична. Сначала допишу, затормозит -- буду оптимизировать) Преждевременно этим заниматься, как известно, грех.
|
Часовой пояс GMT +3, время: 03:57. |