|
| 1 | +### 理解JavaScript的Object.defineProperty()函数 |
| 2 | + |
| 3 | +在进入今天的内容之前,我们可以先考虑这么一个场景,在你的项目中你有这么一个对象如下所示: |
| 4 | +```javascript |
| 5 | +var dreamapple = { |
| 6 | + firstName: 'dream', |
| 7 | + lastName: 'apple' |
| 8 | +}; |
| 9 | +``` |
| 10 | +我们的要求就是你要给`dreamapple`添加一个`fullName`属性,当`dreamapple`的`firstName`或者`lastName` |
| 11 | +发生变化的时候,`fullName`也要随之变化; |
| 12 | +而且当我们设置了`fullName`的值的时候,那么相应的它的`firstName`和`lastName`也随之发生变化; |
| 13 | +那么我们应该怎么做呢? |
| 14 | + |
| 15 | +如果你使用过`Vue.js`的话,那么你可以使用它的`计算属性`来达到这个目的,大概的代码应该是下面这个样子: |
| 16 | +```javascript |
| 17 | +// ... |
| 18 | +computed: { |
| 19 | + fullName: { |
| 20 | + // getter |
| 21 | + get: function () { |
| 22 | + return this.firstName + ' ' + this.lastName |
| 23 | + }, |
| 24 | + // setter |
| 25 | + set: function (newValue) { |
| 26 | + var names = newValue.split(' ') |
| 27 | + this.firstName = names[0] |
| 28 | + this.lastName = names[names.length - 1] |
| 29 | + } |
| 30 | + } |
| 31 | +} |
| 32 | +// ... |
| 33 | +``` |
| 34 | + |
| 35 | +如果你使用过`Angular 1.x`的话,那么你可能会使用`$watch`来达到这个目的,大概的代码应该是下面这个样子: |
| 36 | +```javascript |
| 37 | +// 在控制器中使用 var vm = this; |
| 38 | +$scope.$watch('vm.firstName', function() { |
| 39 | + vm.fullName = vm.firstName + ' ' + vm.lastName; |
| 40 | +}); |
| 41 | +$scope.$watch('vm.lastName', function() { |
| 42 | + vm.fullName = vm.firstName + ' ' + vm.lastName; |
| 43 | +}); |
| 44 | +$scope.$watch('vm.fullName', function() { |
| 45 | + var names = vm.fullName.trim().split(' '); |
| 46 | + if(2 === names.length) { |
| 47 | + vm.firstName = names[0]; |
| 48 | + vm.lastName = names[1]; |
| 49 | + } |
| 50 | + else { |
| 51 | + // TODO |
| 52 | + } |
| 53 | +}); |
| 54 | +``` |
| 55 | + |
| 56 | +那我们使用原生的`JavaScript`可不可以达到这个目的呢?当然可以了;那么我们需要怎么做呢?比较简单的做法就是给这个 |
| 57 | +对象的属性`fullName`设置一个`getter`和一个`setter`,因为这是`ES5`的特性所以较低版本的浏览器不支持这种特性,但是基本所有的 |
| 58 | +现代浏览器都已经支持.我们只需要写出下面的代码就可以了: |
| 59 | + |
| 60 | +```javascript |
| 61 | +var dreamapple = { |
| 62 | + firstName: 'dream', |
| 63 | + lastName: 'apple', |
| 64 | + get fullName() { |
| 65 | + return this.firstName + ' ' + this.lastName; |
| 66 | + }, |
| 67 | + set fullName(fullName) { |
| 68 | + var names = fullName.trim().split(' '); |
| 69 | + if(2 === names.length) { |
| 70 | + this.firstName = names[0]; |
| 71 | + this.lastName = names[1]; |
| 72 | + } |
| 73 | + } |
| 74 | +}; |
| 75 | + |
| 76 | +dreamapple.firstName = 'Dream'; |
| 77 | +dreamapple.lastName = 'Apple'; |
| 78 | +console.log(dreamapple.fullName); // Dream Apple |
| 79 | + |
| 80 | +dreamapple.fullName = 'Jams King'; |
| 81 | +console.log(dreamapple.firstName); // Jams |
| 82 | +console.log(dreamapple.lastName); // King |
| 83 | +``` |
| 84 | +是不是很方便呢?我们通过给`dreamapple`这个对象设置了属性`fullName`的`getter`和`setter`方法,就达到了我们想要的那种效果. |
| 85 | + |
| 86 | +当然更好的一种方法就是使用`Object.defineProperty()`这个函数了,下面我们就来好好的探讨一下这个函数. |
| 87 | + |
| 88 | + |
| 89 | + |
| 90 | + |
| 91 | + |
| 92 | + |
| 93 | + |
0 commit comments