【面試必備】javascript操作DOM元素

呂大豹發表於2013-12-27

前言

  時間過的真快,不知不覺就到年底了。問問自己,這一年你對自己的工作滿意嗎? 評價標準是什麼呢?當然是馬雲的那兩條準則了:錢給到了嗎?乾的爽嗎?如果答案都是no,那麼,你準備好跳槽了嗎?

  為了應對年後跳槽高峰的到來,從現在開始我要把基礎過一遍了。從網上搜集的面試題入手,儘量全面的覆蓋到前端的基礎知識。為年後的面試提前熱身~雖然本人也不是什麼麵霸,沒有什麼面試經驗,但把基礎打紮實是永遠不會錯的,所以不嫌麻煩不嫌重複勞動,我會收集一些簡單基礎的面試題,從中提煉出相關的前端知識,然後分析加以記錄。大概算了算,只要勤快點,從現在開始一直積累到年後,應該也能小有收穫~

  另外還想說一下我對原生js的看法,也是最近產生的。隨著IE6、7、8的逐漸淘汰,ES5的普及,我們已經可以在ES5的標準上進行全面開發了。照這個潮流來看,jQuery似乎要被沒落了,因為它的主要工作就是做低版本IE的相容處理。我是jQuery的嚴重依賴者,如果哪天jQuery真的消失了,豈不連程式碼也不會寫了。真令人擔憂,所以今後要重視原生js了,能不用jq的地方就不用。隨著這次總結基礎知識,我也準備把原生js好好複習一遍,為未來早做打算。

正題

  說到面試題,你最怕什麼樣的呢?我最怕的是題目只有一句話的,越短越難,比如:如何用js操作DOM元素。

  這道題簡單嗎?,其實不然。DOM操作包括元素的建立、查詢、新增、移動、複製、刪除,每種操作又可以延伸出很多問題。如果你常年使用jq或其他框架,原生的寫法可能早就忘了。所以,我需要用一篇文章來描述清楚這個問題。

建立新元素

  document.createElement(elemengTagName)用來建立一個元素,返回該新建元素的引用。需要注意引數是標籤的名稱。在jq中我們可以這樣建立一個元素

var node = $('<div>');
var node2 = $('<span id="s"></span>');

  使用原生的我們必須傳入元素的標籤名稱,不能像jq中那麼靈活。如:

var node = document.createElement('div');

新增新元素

  有兩個方法可以向DOM樹中新增新元素,分別是appendChild(newElement)和insertBefore(newElement,beforeWhichElement)。

  appendChild向一個元素新增子節點,追加在尾部,如在body中追加一個元素:

var node = document.createElement('div');
node.innerHTML = '新新增的節點';
document.body.appendChild(node);

  insertBefore也是向一個元素新增子節點,不過可以指定新增在哪個子節點的前面,如果不指定第二個引數,會預設新增到最後,即與appendChild效果一樣。使用方法如下:

var node = document.createElement('div');
node.innerHTML = '新插入的節點';
var list = document.getElementById('list');
var item1 = document.getElementById('item1');
list.insertBefore(node,item1);

  會在list的子元素item1前面插入新建立的元素node。原生js沒有像jq的prepend那樣可以從頭部新增子節點的方法。

移動元素

  移動元素在DOM樹中的位置還是比較常見的需求。完成元素的移動不需要新的方法,還是使用上面的appendChild和insertBefore,只不過操作的元素不是新建立的,而是從已有節點中選擇你需要移動的。例如交換兩個元素的位置:

var item1 = document.getElementById('item1');
var item2 = document.getElementById('item2');
list.insertBefore(item2,item1);//把item2插入到item1前面

  使用appendChild也是同樣的道理。如:

var item3 = document.getElementById('item3');
var s = document.getElementById('some');
item3.appendChild(s);//把id為some的元素移動到item3下

複製元素

  元素的複製使用cloneNode(cloneChildNodes)方法,引數為boolean型別,表示是否克隆子元素。與jq的clone方法不同的時,原生的無法克隆元素上繫結的事件監聽器。使用方法如下:

var s = document.getElementById('some');
var sclone = s.cloneNode(true);

刪除元素

  使用removeChild(element)方法來刪除元素,需先找到父元素,然後刪除其子元素,如下:

var list = document.getElementById('list');
var item1 = document.getElementById('item1');
list.removeChild(item1);

查詢元素

  查詢元素的內容稍多一點。jq提供了強大的選擇器,這也是它的核心之一。離開了jq,我們還是要明白如何利用原生js來選擇到你所需的元素。getElementById(id)不多說了,getElementsByTagName(tagName)返回符合元素的陣列。除此之外,我們還需知道一個元素都有哪些指標可以訪問到其他元素。概括一下,主要包括以下指標:

  • parentNode:指向父節點
  • childNodes:指向所有子節點,是一個陣列
  • previousSibling:指向前一個兄弟節點
  • nextSibling:指向後一個兄弟節點
  • firstChild:指向第一個子節點
  • lastChild:指向最後一個子節點

  使用如下:

var item2 = document.getElementById('item2');
var parentNode = item2.parentNode;
var childNodes = item2.childNodes;
var previousSibling = item2.previousSibling;
var nextSibling = item2.nextSibling;
var firstChild = item2.firstChild;
var lastChild = item2.lastChild;

console.log(parentNode,childNodes,previousSibling,nextSibling,firstChild,lastChild);

  你可能覺得這比起jq的選擇器簡直差遠了。告訴你一個好訊息,現在可以有更強大的東西用了,那就是querySelector和querySelectorAll,這兩個方法是ES5中新增的,他們的作用就想jq的選擇器一樣,你可以使用像css風格那樣的描述來選擇所需的元素,是不是很爽!比如:

document.querySelector('#list');//選擇id為list的元素
document.querySelectorAll('.green');//選擇class為green的元素,返回元素的陣列

  兩者的區別你可看出來了,querySelector只會返回一個元素,如果匹配到多個就返回第一個。而querySelectorAll會返回所有匹配的元素陣列。有了這兩個原生的js方法,你是不是覺得jQuery的沒落不遠了呢?

結束

  本篇的記錄到此結束,當以後面試問到DOM操作時,就可以應付的過來了。不親手敲一下原生的程式碼真是忘了不少呢。不過有一點是本篇沒有涉及到的,那就是DOM操作的瀏覽器相容性。說實話這塊的知識我也沒有真實遇到過,都是在jq的關照下一路走來的。故本篇只記錄一些淺層次的東西了。

相關文章