狭義の抽象化、つまりコードにおける抽象化とは、関連するビジネスロジックを属性とメソッド(動作)に分離することであり、これらの属性とメソッドはオブジェクトを形成することができます。
この抽象化は、理解しにくいコードを、子犬のようなオブジェクトなどの現実世界に関連する概念に要約することです。属性は、「毛色」、「品種」、「年齢」として要約できます。など; 方法(行動)は、「吠える」、「走る」、「骨をかじる」などに要約できます。
注: ここでの抽象は抽象クラスを指すものではなく、カプセル化セクションで抽象クラスについて説明する方が適切だと思います。
JavaScriptでオブジェクトを作成する方法はたくさんあります、例として子犬オブジェクトを取り上げます:
1 var dog = { 2 hairColor: '白色', 3 breed: '贵宾', 4 age: 2, 5 shout: function() { 6 console.log('汪!汪!汪!'); //这里是你的业务逻辑代码,这里我就简单用这个来代替 7 }, 8 run: function() { 9 console.log('吃我灰吧,哈哈!');10 },11 gnawBone: function() {12 console.log('这是本狗最幸福的时候');13 }14 };
とても便利です。しかし現時点では、次のような質問があります。たくさんの dog を作成したい場合はどうすればよいですか? dogを作成するたびにvarをしますか?
そこで今回、クラス(クラス)の概念を導入しました。クラスは、同じ特性を持つ類似したオブジェクトのプロトタイプであり、クラス自体は存在しません。クラスのコードを実行すると、オブジェクト (instance/instance) がメモリ内に作成されます。クラスは、オブジェクトを作成するためのファクトリーとして単純に理解できます。 javascript(
es5)にはクラスはありません。茶色のテディベアを作りたいのですが、どうすればいいですか?この問題は、クラスの作成時にクラスのコンストラクターにパラメーターを渡すことで解決できます。 先ほどの例でも述べたように、クラスで作成した各オブジェクト(インスタンス)のメソッドは共有され、属性は独自のものになりますが、共有属性だけを作成したい場合はどうすればよいでしょうか?たとえば、instanceNumber 属性を作成して、プログラム内の犬のオブジェクト (インスタンス) の数を記録したいとします。 このとき、Dog クラスの static 属性を作成できます。 static 属性はクラスに属するため、オブジェクト (インスタンス) の変更によって変更されず、グローバル変数の設定に使用できます。クラス待機のグローバルパラメータ設定。 以下は新しいコードです: 1 /*类的创建*/ 2 function Dog() { 3 //构造函数:人们一致协定把构造函数的名字(即类名),首字母大写,以便区分 4 this.hairColor = '白色'; 5 /*this指向被创造的对象(实例),如果不明白可以简单的理解为给对象(this)赋予hairColor这个属性 6 */ 7 this.breed = '贵宾'; 8 this.age = 2; 9 this.runSpeed = null; //string10 /*属性的声明一定要放在构造函数的最顶部;11 有的属性可能一开始没有初始值,会在方法里才赋值,但你一定要在构造函数里声明一下12 有必要的话再声明一下属性的类型13 */14 }15 Dog.prototype.shout = function() {16 /*我们把方法追加到构造函数的prototype属性,而不是直接在构造函数里用this.shout = function(){};17 这样的好处是会让Dog创造的所有对象都共享一个方法,从而节约内存;18 一般来说属性在构造函数里赋予,方法在prototype里赋予;19 更多prototype的知识就看书去吧,这里不会深讲,作者要保持本章知识的封装性;20 */21 console.log('汪!汪!汪!我是一只' + this.age + '岁的' + this.hairColor + this.breed);22 //方法里通过this可以访问属性23 }24 Dog.prototype.run = function() {25 this.runSpeed = '10m/s';26 console.log('吃我灰吧,哈哈!本狗的速度可是有' + this.runSpeed);27 }28 Dog.prototype.gnawBone = function() {29 console.log('这是本狗最幸福的时候');30 }31 /*对象(实例)的创建与使用*/32 var dog1 = new Dog(); //33 console.log(dog1.breed); //log: '贵宾'34 dog1.shout(); //log: '汪!汪!汪!我是一只2岁的白色贵宾'35 var dog2 = new Dog(); //创建多只dog(对象/实例)36 var dog3 = new Dog();37 /*dog1、dog2、dog3这些对象的属性是各自的,但方法是共享的*/38 dog1.hairColor = '黑色'; //修改dog1的属性39 console.log(dog1.hairColor); //log: '黑色';dog1属性已被修改;40 console.log(dog2.hairColor); //'白色';其它对象不受影响;41 console.log(dog3.hairColor); //log: '白色'42 console.log(dog1.shout === dog2.shout); //log: true;dog1的shout方法和dog2的是同一个方法;
1 function Dog(hairColor, breed, age) { 2 this.hairColor = hairColor; //string,这种依赖参数的属性最好声明下类型或接口; 3 this.breed = breed; //string 4 this.age = age; //number 5 this.runSpeed = null; //string 6 Dog.instanceNumber++; 7 } 8 Dog.instanceNumber = 0; //创建静态属性 9 Dog.prototype.shout = function() {10 console.log('汪!汪!汪!我是一只' + this.age + '岁的' + this.hairColor + this.breed);11 }12 Dog.prototype.run = function() {13 this.runSpeed = '10m/s';14 console.log('吃我灰吧,哈哈!本狗的速度可是有' + this.runSpeed);15 }16 Dog.prototype.gnawBone = function() {17 console.log('这是本狗最幸福的时候');18 }19 Dog.prototype.getInstanceNumber = function() { //为访问静态属性封装方法20 return Dog.instanceNumber;21 }22 var dog1 = new Dog('白色', '贵宾', 2);23 console.log(Dog.instanceNumber); //log: 1;虽然可以这样访问静态属性,并且还可以修改它,但坚决不推荐这样做24 console.log(dog1.getInstanceNumber()); //log: 1;正确的做法!为什么要这样做,在封装一节会详细讲25 var dog2 = new Dog('棕色', '泰迪', 1);26 console.log(dog1.getInstanceNumber()); //log: 2;27 var dog3 = new Dog('黑色', '土狗', 3);28 console.log(dog1.getInstanceNumber()); //log: 3;29 dog1.shout(); //log: '汪!汪!汪!我是一只2岁的白色贵宾'30 dog2.shout(); //log: '汪!汪!汪!我是一只1岁的棕色泰迪'31 dog3.shout(); //log: '汪!汪!汪!我是一只3岁的黑色土狗'
りー
上面的例子是我们明确知道要创建一个对象(实例)dog,但实际开发当中是没有人告诉我们需要创建哪些对象的,领导给我们的只有需求,所以我们要分析需求的业务逻辑,把需求分解成一个个对象。
比如说现在领导给我们一个需求:做一个超市收银系统,分为两种角色:收银员和管理员,收银员可以查询物品信息、统计价格、录入账单信息、打印小票,管理员可以查看账单信息、统计账单信息。
注意需求中的名词:收银员、管理员、物品信息、账单、小票,这些就是天然的对象,这是最初步的抽象。
让我们再注意动词:查询、统计、录入、打印,我们是不是也可以抽象成对象?查询器?统计器?
然后我们开始coding吧,不要纠结自己的抽象是否完美,作者很赞同Facebook的一句标语:Done is better than perfect(比完美更重要的是完成).
当某个对象的代码不断膨胀,慢慢超出控制的时候(作者自己的的标准是一个对象尽量不超过300行代码),这时候你就得考虑更深层次的抽象了,查找这个对象里代码比较多的属性、方法、然后抽象成另一个对象,把新对象作为原先对象的成员(属性)。
function Dog(){ this._tail = new Tail();//把尾巴tail抽象成另一个对象,作为dog的一个属性; }
当然,你成了老司机后可以一开始就把一个对象再抽象出许多成员对象,随你喜欢。
如果你喜欢作者的文章,记得收藏,你的点赞是对作者最大的鼓励;
作者会尽量每周更新一章,下一章是讲继承;
大家有什么疑问可以留言或私信作者,作者尽量第一时间回复大家;
如果老司机们觉得那里可以有不恰当的,或可以表达的更好的,欢迎指出来,作者会尽快修正、完善。
以上がJavaScriptにおける抽象化の詳細説明(ES5、ES6、TypeScriptによるデモ)の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。