一铭段、面向過程與面向?qū)ο?/h3>
1.1 面向過程(POP)
- 面向過程就是分析出解決問題所需要的步驟畜份,然后用函數(shù)把這些步驟一步一步實現(xiàn)顿仇,使用的時候再一個一個的依次調(diào)用就可以了玄叠。
例子:1.打開冰箱??2.把大象裝進去??3.把冰箱門關(guān)上
1.2 面向?qū)ο螅∣OP)
- 面向?qū)ο笫前咽聞?wù)分解成為一個個對象古徒,然后由對象之間分工與合作。
以對象功能來劃分問題读恃。
例子:將大象裝進冰箱隧膘,面向?qū)ο笞龇ā?br>
先找出對象,并寫出這些對象的功能:
1. 大象對象:
- 進去
2. 冰箱對象:
- 打開
- 關(guān)閉
3. 使用大象和冰箱的功能
1.3 面向過程與面向?qū)ο髮Ρ?/h4>
面向過程 | 面向?qū)ο?/th> | |
---|---|---|
優(yōu)點 | 性能比面向?qū)ο蟾吆唬m合跟硬件聯(lián)系很緊密的東西舀寓,例如單片機就采用的面向過程編程。適合比較簡單的小型程序肌蜻。 | 易維護互墓、易復(fù)用、易擴展蒋搜,由于面向?qū)ο笥?strong>封裝性篡撵、繼承性、多態(tài)性的特性豆挽,可以設(shè)計出低耦合的系統(tǒng)育谬,使系統(tǒng) 更加靈活、更加易于維護帮哈。適合多人合作的大型項目膛檀。 |
缺點 | 不易維護、不易復(fù)用娘侍、不易擴展 | 性能比面向過程低 |
面向過程和面向?qū)ο笾皇菍τ诰幊趟季S的一種描述咖刃,面向過程的方法寫出來的程序就像蛋炒飯,如果里面某些食材不愛吃很難挑出來憾筏;而用面向?qū)ο髮懙某绦蚋裆w澆飯嚎杨,自己想要什么澆頭自己取用就可。
1.4 面向?qū)ο蟮乃季S特點
- 抽妊跹(抽象)對象共用的屬性和行為封裝成一個類(模版)
- 對類進行實例化枫浙,產(chǎn)生具體的一個個對象
二刨肃、對象與類
2.1 對象
對象是由屬性和方法組成的:是一個無序鍵值對(相關(guān)屬性與方法)的集合,指的是一個具體的事物。所有的事物都是對象箩帚,例如字符串真友、數(shù)值、數(shù)組膏潮、函數(shù)等锻狗。
- 屬性:事物的特征,在對象中用屬性來表示(常用名詞)
- 方法:事物的行為焕参,在對象中用方法來表示(常用動詞)
2.1.1 創(chuàng)建對象
//以下代碼是對對象的復(fù)習(xí)
//字面量創(chuàng)建對象
var ldh = {
name: '劉德華',
age: 18
}
console.log(ldh);
//構(gòu)造函數(shù)創(chuàng)建對象
function Star(name, age) {
this.name = name;
this.age = age;
}
var ldh = new Star('劉德華', 18)//實例化對象
console.log(ldh);
如上兩行代碼運行結(jié)果為:2.2 類
- 在 ES6 中新增加了類的概念,可以使用 class 關(guān)鍵字聲明一個類油额,之后以這個類來實例化對象叠纷。類抽象了對象的公共部分,它泛指某一大類(class)潦嘶。對象特指某一個涩嚣,通過類實例化一個具體的對象
2.2.1創(chuàng)建類
- 語法:
//步驟1 使用class關(guān)鍵字
class Name {
// class body
}
//步驟2使用定義的類創(chuàng)建實例 注意new關(guān)鍵字
var xx = new Name();
constructor構(gòu)造函數(shù)(構(gòu)造器)
constructor()方法是類的構(gòu)造函數(shù)(默認方法),用于傳遞參數(shù)掂僵,返回實例對象航厚,通過new命令生成對象實例時,自動調(diào)用該方法锰蓬。如果我門定義類的時候沒有寫幔睬,類內(nèi)部會自動給我們創(chuàng)建一個constructor()
- 示例
// 1. 創(chuàng)建類 class 創(chuàng)建一個 明星類
class Star {
// 類的共有屬性放到 constructor 里面
constructor(name, age) {
this.name = name;
this.age = age;
}
}
// 2. 利用類創(chuàng)建對象 new
var ldh = new Star('劉德華', 18);
console.log(ldh);
以上代碼運行結(jié)果:
通過結(jié)果我們可以看出,運行結(jié)果和使用構(gòu)造函數(shù)方式一樣
2.2.2 類創(chuàng)建添加屬性和方法
// 1. 創(chuàng)建類 class 創(chuàng)建一個類
class Star {
// 類的共有屬性放到 constructor 里面 constructor是 構(gòu)造器或者構(gòu)造函數(shù)
constructor(uname, age) {
this.uname = uname;
this.age = age;
}//------------------------------------------->注意,方法與方法之間不需要添加逗號
sing(song) {
console.log(this.uname + '唱' + song);
}
}
// 2. 利用類創(chuàng)建對象 new
var ldh = new Star('劉德華', 18);
console.log(ldh); // Star {uname: "劉德華", age: 18}
ldh.sing('冰雨'); // 劉德華唱冰雨
注意:
- 通過class 關(guān)鍵字創(chuàng)建類, 類名我們還是習(xí)慣性定義首字母大寫
- 類里面有個constructor 函數(shù),可以接受傳遞過來的參數(shù),同時返回實例對象
- constructor 函數(shù) 只要 new 生成實例時,就會自動調(diào)用這個函數(shù), 如果我們不寫這個函數(shù),類也會自動生成這個函數(shù)
- 多個函數(shù)方法之間不需要添加逗號分隔
- 生成實例 new 不能省略
- 語法規(guī)范, 創(chuàng)建類 類名后面不要加小括號,生成實例 類名后面加小括號, 構(gòu)造函數(shù)不需要加function
2.2.3 類的繼承
- 語法
// 父類
class Father{
}
// 子類繼承父類
class Son extends Father {
}
- 示例
class Father {
constructor(surname) {
this.surname= surname;
}
say() {
console.log('你的姓是' + this.surname);
}
}
class Son extends Father{ // 這樣子類就繼承了父類的屬性和方法
}
var damao= new Son('劉');
damao.say(); //結(jié)果為 你的姓是劉
以上代碼運行結(jié)果:
- 子類使用super關(guān)鍵字訪問父類的方法
//定義了父類
class Father {
constructor(x, y) {
this.x = x;
this.y = y;
}
sum() {
console.log(this.x + this.y);
}
}
//子元素繼承父類
class Son extends Father {
constructor(x, y) {
super(x, y); //使用super調(diào)用了父類中的構(gòu)造函數(shù)
}
}
var son = new Son(1, 2);
son.sum(); //結(jié)果為3
注意:
繼承中,如果實例化子類輸出一個方法,先看子類有沒有這個方法,如果有就先執(zhí)行子類的
繼承中,如果子類里面沒有,就去查找父類有沒有這個方法,如果有,就執(zhí)行父類的這個方法(就近原則)
如果子類想要繼承父類的方法,同時在自己內(nèi)部擴展自己的方法,利用super 調(diào)用父類的構(gòu)造函數(shù),super必須在子類this之前調(diào)用
// 父類有加法方法
class Father {
constructor(x, y) {
this.x = x;
this.y = y;
}
sum() {
console.log(this.x + this.y);
}
}
// 子類繼承父類加法方法 同時 擴展減法方法
class Son extends Father {
constructor(x, y) {
// 利用super 調(diào)用父類的構(gòu)造函數(shù) super 必須在子類this之前調(diào)用,放到this之后會報錯
super(x, y);
this.x = x;
this.y = y;
}
subtract() {
console.log(this.x - this.y);
}
}
var son = new Son(5, 3);
son.subtract(); //2
son.sum();//8
以上代碼運行結(jié)果為:
-
時刻注意this的指向問題,類里面的共有的屬性和方法一定要加this使用
- constructor中的this指向的是new出來的實例對象
- 自定義的方法,一般也指向的new出來的實例對象
- 綁定事件之后this指向的就是觸發(fā)事件的事件源
在 ES6 中類沒有變量提升芹扭,所以必須先定義類麻顶,才能通過類實例化對象
三、面向?qū)ο蟀鎡ab 欄切換
3.1 功能需求
- 點擊 tab欄,可以切換效果.
- 點擊 + 號, 可以添加 tab 項和內(nèi)容項.
- 點擊 x 號, 可以刪除當前的tab項和內(nèi)容項.
- 雙擊tab項文字或者內(nèi)容項文字可以修改里面的文字內(nèi)容
3.2 案例準備
- 獲取到標題元素
- 獲取到內(nèi)容元素
- 獲取到刪除的小按鈕 x號
- 新建js文件,定義類,添加需要的屬性方法(切換,刪除,增加,修改)
- 時刻注意this的指向問題
3.3 切換
-
為獲取到的標題綁定點擊事件,展示對應(yīng)的內(nèi)容區(qū)域,存儲對應(yīng)的索引
this.lis[i].index = i; this.lis[i].onclick = this.toggleTab;
-
使用排他,實現(xiàn)只有一個元素的顯示
toggleTab() { //將所有的標題與內(nèi)容類樣式全部移除 for (var i = 0; i < this.lis.length; i++) { this.lis[i].className = ''; this.sections[i].className = ''; } //為當前的標題添加激活樣式 this.className = 'liactive'; //為當前的內(nèi)容添加激活樣式 that.sections[this.index].className = 'conactive'; }
3.4 添加
-
為添加按鈕+ 綁定點擊事件
this.add.onclick = this.addTab;
-
實現(xiàn)標題與內(nèi)容的添加,做好排他處理
addTab() { that.clearClass(); // (1) 創(chuàng)建li元素和section元素 var random = Math.random(); var li = '<li class="liactive"><span>新選項卡</span><span class="iconfont icon-guanbi"> </span></li>'; var section = '<section class="conactive">測試 ' + random + '</section>'; // (2) 把這兩個元素追加到對應(yīng)的父元素里面 that.ul.insertAdjacentHTML('beforeend', li); that.fsection.insertAdjacentHTML('beforeend', section); that.init(); }
3.5 刪除
-
為元素的刪除按鈕x綁定點擊事件
this.remove[i].onclick = this.removeTab;
-
獲取到點擊的刪除按鈕的所在的父元素的所有,刪除對應(yīng)的標題與內(nèi)容
removeTab(e) { e.stopPropagation(); // 阻止冒泡 防止觸發(fā)li 的切換點擊事件 var index = this.parentNode.index; console.log(index); // 根據(jù)索引號刪除對應(yīng)的li 和section remove()方法可以直接刪除指定的元素 that.lis[index].remove(); that.sections[index].remove(); that.init(); // 當我們刪除的不是選中狀態(tài)的li 的時候,原來的選中狀態(tài)li保持不變 if (document.querySelector('.liactive')) return; // 當我們刪除了選中狀態(tài)的這個li 的時候, 讓它的前一個li 處于選定狀態(tài) index--; // 手動調(diào)用我們的點擊事件 不需要鼠標觸發(fā) that.lis[index] && that.lis[index].click(); }
3.6 編輯
-
為元素(標題與內(nèi)容)綁定雙擊事件
this.spans[i].ondblclick = this.editTab; this.sections[i].ondblclick = this.editTab;
-
在雙擊事件處理文本選中狀態(tài),修改內(nèi)部DOM節(jié)點,實現(xiàn)新舊value值的傳遞
editTab() { var str = this.innerHTML; // 雙擊禁止選定文字 window.getSelection ? window.getSelection().removeAllRanges() : document.selection.empty(); // alert(11); this.innerHTML = '<input type="text" />'; var input = this.children[0]; input.value = str; input.select(); // 文本框里面的文字處于選定狀態(tài) // 當我們離開文本框就把文本框里面的值給span input.onblur = function() { this.parentNode.innerHTML = this.value; }; // 按下回車也可以把文本框里面的值給span input.onkeyup = function(e) { if (e.keyCode === 13) { // 手動調(diào)用表單失去焦點事件 不需要鼠標離開操作 this.blur(); } } }
四舱卡、構(gòu)造函數(shù)和原型
4.1 對象的三種創(chuàng)建方式--復(fù)習(xí)
-
字面量方式
var obj = {};
-
new關(guān)鍵字
var obj = new Object();
-
構(gòu)造函數(shù)方式
function Person(name,age){ this.name = name; this.age = age; } var obj = new Person('zs',12);
4.2 靜態(tài)成員和實例成員
4.2.1 實例成員
實例成員就是構(gòu)造函數(shù)內(nèi)部通過this添加的成員 如下列代碼中uname age sing 就是實例成員辅肾,實例成員只能通過實例化的對象來訪問
function Star(uname, age) {
this.uname = uname;
this.age = age;
this.sing = function() {
console.log('我會唱歌');
}
}
var ldh = new Star('劉德華', 18);
console.log(ldh.uname);//實例成員只能通過實例化的對象來訪問
4.2.2 靜態(tài)成員
靜態(tài)成員 在構(gòu)造函數(shù)本身上添加的成員 如下列代碼中 sex 就是靜態(tài)成員,靜態(tài)成員只能通過構(gòu)造函數(shù)來訪問
function Star(uname, age) {
this.uname = uname;
this.age = age;
this.sing = function() {
console.log('我會唱歌');
}
}
Star.sex = '男';
var ldh = new Star('劉德華', 18);
console.log(Star.sex);//靜態(tài)成員只能通過構(gòu)造函數(shù)來訪問
4.3 構(gòu)造函數(shù)的問題
構(gòu)造函數(shù)方法很好用,但是存在浪費內(nèi)存的問題轮锥。
4.4 構(gòu)造函數(shù)原型prototype
構(gòu)造函數(shù)通過原型分配的函數(shù)是所有對象所共享的矫钓。
JavaScript 規(guī)定,每一個構(gòu)造函數(shù)都有一個prototype 屬性舍杜,指向另一個對象新娜。注意這個prototype就是一個對象,這個對象的所有屬性和方法蝴簇,都會被構(gòu)造函數(shù)所擁有杯活。
我們可以把那些不變的方法,直接定義在 prototype 對象上熬词,這樣所有對象的實例就可以共享這些方法旁钧。
function Star(uname, age) {
this.uname = uname;
this.age = age;
}
Star.prototype.sing = function() {
console.log('我會唱歌');
}
var ldh = new Star('劉德華', 18);
var zxy = new Star('張學(xué)友', 19);
ldh.sing();//我會唱歌
zxy.sing();//我會唱歌
4.5 對象原型
對象都會有一個屬性__proto__
指向構(gòu)造函數(shù)的 prototype
原型對象吸重,之所以我們對象可以使用構(gòu)造函數(shù) prototype
原型對象的屬性和方法,就是因為對象有__proto__
原型的存在歪今。
__proto__
對象原型和原型對象 prototype
是等價的
__proto__
對象原型的意義就在于為對象的查找機制提供一個方向嚎幸,或者說一條路線,但是它是一個非標準屬性寄猩,因此實際開發(fā)中嫉晶,不可以使用這個屬性,它只是內(nèi)部指向原型對象 prototype
4.6 constructor構(gòu)造函數(shù)
對象原型(__proto__
)和構(gòu)造函數(shù)(prototype
)原型對象里面都有一個屬性 constructor
屬性 田篇,constructor
我們稱為構(gòu)造函數(shù)替废,因為它指回構(gòu)造函數(shù)本身。
constructor
主要用于記錄該對象引用于哪個構(gòu)造函數(shù)泊柬,它可以讓原型對象重新指向原來的構(gòu)造函數(shù)椎镣。
一般情況下,對象的方法都在構(gòu)造函數(shù)的原型對象中設(shè)置兽赁。如果有多個對象的方法状答,我們可以給原型對象采取對象形式賦值,但是這樣就會覆蓋構(gòu)造函數(shù)原型對象原來的內(nèi)容刀崖,這樣修改后的原型對象 constructor
就不再指向當前構(gòu)造函數(shù)了惊科。此時,我們可以在修改后的原型對象中亮钦,添加一個 constructor
指向原來的構(gòu)造函數(shù)馆截。
如果我們修改了原來的原型對象,給原型對象賦值的是一個對象,則必須手動的利用constructor
指回原來的構(gòu)造函數(shù)如:
function Star(uname, age) {
this.uname = uname;
this.age = age;
}
// 很多情況下,我們需要手動的利用constructor 這個屬性指回 原來的構(gòu)造函數(shù)
Star.prototype = {
// 如果我們修改了原來的原型對象,給原型對象賦值的是一個對象,則必須手動的利用constructor指回原來的構(gòu)造函數(shù)
constructor: Star, // 手動設(shè)置指回原來的構(gòu)造函數(shù)
sing: function() {
console.log('我會唱歌');
},
movie: function() {
console.log('我會演電影');
}
}
var zxy = new Star('張學(xué)友', 19);
console.log(zxy)
以上代碼運行結(jié)果,設(shè)置constructor屬性如圖:
如果未設(shè)置constructor屬性,如圖:
4.7 原型鏈
? 每一個實例對象又有一個__proto__
屬性,指向的構(gòu)造函數(shù)的原型對象(prototype
)或悲,構(gòu)造函數(shù)的原型對象也是一個對象孙咪,也有__proto__
屬性,這樣一層一層往上找就形成了原型鏈巡语。
4.8 構(gòu)造函數(shù)實例和原型對象三角關(guān)系
- 構(gòu)造函數(shù)的
prototype
屬性指向了構(gòu)造函數(shù)原型對象 - 實例對象是由構(gòu)造函數(shù)創(chuàng)建的,實例對象的
__proto__
屬性指向了構(gòu)造函數(shù)的原型對象 - 構(gòu)造函數(shù)的原型對象的
constructor
屬性指向了構(gòu)造函數(shù)翎蹈,實例對象的原型的constructor
屬性也指向了構(gòu)造函數(shù)
4.9 原型鏈和成員的查找機制
任何對象都有原型對象,也就是prototype
屬性,任何原型對象也是一個對象,該對象就有__proto__
屬性,這樣一層一層往上找,就形成了一條鏈,我們稱此為原型鏈;
當訪問一個對象的屬性(包括方法)時,首先查找這個對象自身有沒有該屬性男公。
如果沒有就查找它的原型(也就是 __proto__
指向的 prototype
原型對象)荤堪。
如果還沒有就查找原型對象的原型(Object的原型對象)。
依此類推一直找到 Object 為止(null)枢赔。
__proto__
對象原型的意義就在于為對象成員查找機制提供一個方向澄阳,或者說一條路線。
4.10 原型對象中this指向
構(gòu)造函數(shù)中的this和原型對象的this踏拜,都指向我們new出來的實例對象
function Star(uname, age) {
this.uname = uname;
this.age = age;
}
var that;
Star.prototype.sing = function() {
console.log('我會唱歌');
that = this;
}
var ldh = new Star('劉德華', 18);
// 1. 在構(gòu)造函數(shù)中,里面this指向的是對象實例 ldh
console.log(that === ldh);//true
// 2.原型對象函數(shù)里面的this 指向的是 實例對象 ldh
4.11 通過原型為數(shù)組擴展內(nèi)置方法
Array.prototype.sum = function() {
var sum = 0;
for (var i = 0; i < this.length; i++) {
sum += this[i];
}
return sum;
};
//此時數(shù)組對象中已經(jīng)存在sum()方法了 可以始終 數(shù)組.sum()進行數(shù)據(jù)的求
五碎赢、組合繼承
5.1 call()
- call()可以調(diào)用函數(shù)
fn.call()
- call()可以修改this的指向,使用call()的時候 參數(shù)一是修改后的this指向,參數(shù)2,參數(shù)3..使用逗號隔開連接
function fn(x, y) {
console.log(this);
console.log(x + y);
}
var o = {
name: 'andy'
};
fn.call(o, 1, 2);//調(diào)用了函數(shù)此時的this指向了對象o,
5.2 子構(gòu)造函數(shù)繼承父構(gòu)造函數(shù)中的屬性
- 先定義一個父構(gòu)造函數(shù)
- 再定義一個子構(gòu)造函數(shù)
- 子構(gòu)造函數(shù)繼承父構(gòu)造函數(shù)的屬性(使用call方法)
// 1. 父構(gòu)造函數(shù)
function Father(uname, age) {
// this 指向父構(gòu)造函數(shù)的對象實例
this.uname = uname;
this.age = age;
}
// 2 .子構(gòu)造函數(shù)
function Son(uname, age, score) {
// this 指向子構(gòu)造函數(shù)的對象實例
3.使用call方式實現(xiàn)子繼承父的屬性
Father.call(this, uname, age);
this.score = score;
}
var son = new Son('劉德華', 18, 100);
console.log(son);
5.3 借用原型對象繼承方法
- 先定義一個父構(gòu)造函數(shù)
- 再定義一個子構(gòu)造函數(shù)
- 子構(gòu)造函數(shù)繼承父構(gòu)造函數(shù)的屬性(使用call方法)
// 1. 父構(gòu)造函數(shù)
function Father(uname, age) {
// this 指向父構(gòu)造函數(shù)的對象實例
this.uname = uname;
this.age = age;
}
Father.prototype.money = function() {
console.log(100000);
};
// 2 .子構(gòu)造函數(shù)
function Son(uname, age, score) {
// this 指向子構(gòu)造函數(shù)的對象實例
Father.call(this, uname, age);
this.score = score;
}
// Son.prototype = Father.prototype; 這樣直接賦值會有問題,因為是把父原型對象的地址給了子原型對象速梗;如果修改了子原型對象肮塞,父原型對象也會跟著一起變化
Son.prototype = new Father();
// 如果利用對象的形式修改了原型對象,別忘了利用constructor 指回原來的構(gòu)造函數(shù)
Son.prototype.constructor = Son;
// 這個是子構(gòu)造函數(shù)專門的方法
Son.prototype.exam = function() {
console.log('孩子要考試');
}
var son = new Son('劉德華', 18, 100);
console.log(son);
如上代碼結(jié)果如圖:
六襟齿、ES5新增方法
6.1 數(shù)組方法forEach遍歷數(shù)組
arr.forEach(function(value, index, array) {
//參數(shù)一是:數(shù)組元素
//參數(shù)二是:數(shù)組元素的索引
//參數(shù)三是:當前的數(shù)組
})
//相當于數(shù)組遍歷的 for循環(huán) 沒有返回值
6.2 數(shù)組方法filter過濾數(shù)組
var arr = [12, 66, 4, 88, 3, 7];
var newArr = arr.filter(function(value,index,array) {
//參數(shù)一是:數(shù)組元素
//參數(shù)二是:數(shù)組元素的索引
//參數(shù)三是:當前的數(shù)組
return value >= 20;
});
console.log(newArr);//[66,88] //返回值是一個新數(shù)組
6.3 數(shù)組方法map處理數(shù)組
通過指定函數(shù)處理數(shù)組的每個元素,并返回處理后的數(shù)組
var arr = [1,2,3,4,5,4,3,2,1];
var mapResult = arr.map(function(item, index, array){
return item * 2;
});
console.log(mapResult); // [2,4,6,8,10,8,6,4,2]
6.4 數(shù)組方法some和every
按順序查找數(shù)組中是否有滿足條件的元素枕赵,只要有1個符合條件就返回true猜欺,然后立即終止循環(huán),而every()
是執(zhí)行到最后一項拷窜,必須每一項都符合條件才會返回true
var arr = [10, 30, 4];
var flag = arr.some(function(value,index,array) {
//參數(shù)一是:數(shù)組元素
//參數(shù)二是:數(shù)組元素的索引
//參數(shù)三是:當前的數(shù)組
return value < 3;
});
console.log(flag);//false返回值是布爾值,只要查找到滿足條件的一個元素就立馬終止循環(huán)
6.5 篩選商品案例
-
定義數(shù)組對象數(shù)據(jù)
var data = [{ id: 1, pname: '小米', price: 3999 }, { id: 2, pname: 'oppo', price: 999 }, { id: 3, pname: '榮耀', price: 1299 }, { id: 4, pname: '華為', price: 1999 }, ];
-
使用forEach遍歷數(shù)據(jù)并渲染到頁面中
data.forEach(function(value) { var tr = document.createElement('tr'); tr.innerHTML = '<td>' + value.id + '</td><td>' + value.pname + '</td><td>' + value.price + '</td>'; tbody.appendChild(tr); });
-
根據(jù)價格篩選數(shù)據(jù)
-
獲取到搜索按鈕并為其綁定點擊事件
search_price.addEventListener('click', function() { });
-
使用filter將用戶輸入的價格信息篩選出來
search_price.addEventListener('click', function() { var newDate = data.filter(function(value) { //start.value是開始區(qū)間 //end.value是結(jié)束的區(qū)間 return value.price >= start.value && value.price <= end.value; }); console.log(newDate); });
-
將篩選出來的數(shù)據(jù)重新渲染到表格中
-
將渲染數(shù)據(jù)的邏輯封裝到一個函數(shù)中
function setDate(mydata) { // 先清空原來tbody 里面的數(shù)據(jù) tbody.innerHTML = ''; mydata.forEach(function(value) { var tr = document.createElement('tr'); tr.innerHTML = '<td>' + value.id + '</td><td>' + value.pname + '</td><td>' + value.price + '</td>'; tbody.appendChild(tr); }); }
-
將篩選之后的數(shù)據(jù)重新渲染
search_price.addEventListener('click', function() { var newDate = data.filter(function(value) { return value.price >= start.value && value.price <= end.value; }); console.log(newDate); // 把篩選完之后的對象渲染到頁面中 setDate(newDate); });
-
-
根據(jù)商品名稱篩選
獲取用戶輸入的商品名稱
-
為查詢按鈕綁定點擊事件,將輸入的商品名稱與這個數(shù)據(jù)進行篩選
search_pro.addEventListener('click', function() { var arr = []; data.some(function(value) { if (value.pname === product.value) { // console.log(value); arr.push(value); return true; // return 后面必須寫true } }); // 把拿到的數(shù)據(jù)渲染到頁面中 setDate(arr); })
-
6.6 some和forEach區(qū)別
- 如果查詢數(shù)組中唯一的元素, 用some方法更合適开皿,在some里面遇到
return true
就是終止遍歷,迭代效率更高 - 在forEach 里面 return 不會終止迭代
6.7 trim方法去除字符串兩端的空格
不影響原字符串篮昧,返回的是新字符串
var str = ' hello '
console.log(str.trim()) //hello 去除兩端空格
var str1 = ' he l l o '
console.log(str1.trim()) //he l l o 去除兩端空格
6.8 獲取對象的屬性名
Object.keys(對象) 獲取到當前對象中的屬性名 赋荆,返回值是一個數(shù)組
var obj = {
id: 1,
pname: '小米',
price: 1999,
num: 2000
};
var result = Object.keys(obj)
console.log(result)//[id,pname,price,num]
6.9 Object.defineProperty
Object.defineProperty設(shè)置或修改對象中的屬性
Object.defineProperty(對象obj懊昨,修改或新增的屬性名prop字符串糠睡,{
value:修改或新增的屬性的值,默認為undefined。
writable:true|false,//默認為false疚颊。即不允許修改這個屬性的值
enumerable: false,//enumerable 默認值為false,即不允許遍歷(枚舉)信认。Object.keys(obj)將沒有這個屬性名
configurable: false //configurable 默認值為false材义,即不允許刪除這個屬性 屬性是否可以被刪除或是否可以再次修改特性(即用Object.defineProperty再次設(shè)置這個屬性的第三個參數(shù))
})
var obj = {
id: 1,
pname: '小米',
price: 1999
};
// Object.defineProperty() 定義新屬性或修改原有的屬性
Object.defineProperty(obj, 'num', {
value: 1000,
enumerable: true
});