JavaScript前端面試題

  • 介紹js的基本數據類型。

      Undefined、Null、Boolean、Number、String、
      ECMAScript 2015 新增:Symbol(創建後獨一無二且不可變的數據類型 )
    
  • 介紹js有哪些內置對象?

     Object 是 JavaScript 中所有對象的父對象
    
     數據封裝類對象:Object、Array、Boolean、Number 和 String
     其他對象:Function、Arguments、Math、Date、RegExp、Error
    
     參考:http://www.ibm.com/developerworks/cn/web/wa-objectsinjs-v1b/index.html
    
  • 說幾條寫JavaScript的基本規範?

     1.不要在同一行聲明多個變量。
     2.請使用 ===/!==來比較true/false或者數值
     3.使用對象字面量替代new Array這種形式
     4.不要使用全局函數。
     5.Switch語句必須帶有default分支
     6.函數不應該有時候有返回值,有時候沒有返回值。
     7.For循環必須使用大括號
     8.If語句必須使用大括號
     9.for-in循環中的變量 應該使用var關鍵字明確限定作用域,從而避免作用域污染。
    
  • JavaScript原型,原型鏈 ? 有什麼特點?

     每個對象都會在其內部初始化一個屬性,就是prototype(原型),當我們訪問一個對象的屬性時,
     如果這個對象內部不存在這個屬性,那麼他就會去prototype裏找這個屬性,這個prototype又會有自己的prototype,
     於是就這樣一直找下去,也就是我們平時所說的原型鏈的概念。
     關係:instance.constructor.prototype = instance.__proto__
    
     特點:
     JavaScript對象是通過引用來傳遞的,我們創建的每個新對象實體中並沒有一份屬於自己的原型副本。當我們修改原型時,與之相關的對象也會繼承這一改變。
    
    
      當我們需要一個屬性的時,Javascript引擎會先看當前對象中是否有這個屬性, 如果沒有的話,
      就會查找他的Prototype對象是否有這個屬性,如此遞推下去,一直檢索到 Object 內建對象。
     	function Func(){}
     	Func.prototype.name = "Sean";
     	Func.prototype.getInfo = function() {
     	  return this.name;
     	}
     	var person = new Func();//現在可以參考var person = Object.create(oldObject);
     	console.log(person.getInfo());//它擁有了Func的屬性和方法
     	//"Sean"
     	console.log(Func.prototype);
     	// Func { name="Sean", getInfo=function()}
    
  • JavaScript有幾種類型的值?,你能畫一下他們的內存圖嗎?

     棧:原始數據類型(Undefined,Null,Boolean,Number、String)
     堆:引用數據類型(對象、數組和函數)
    
     兩種類型的區別是:存儲位置不同;
     原始數據類型直接存儲在棧(stack)中的簡單數據段,佔據空間小、大小固定,屬於被頻繁使用數據,所以放入棧中存儲;
     引用數據類型存儲在堆(heap)中的對象,佔據空間大、大小不固定。如果存儲在棧中,將會影響程序運行的性能;引用數據類型在棧中存儲了指針,該指針指向堆中該實體的起始地址。當解釋器尋找引用值時,會首先檢索其在棧中的地址,取得地址後從堆中獲得實體
    

    Stated Clearly Image

  • 如何將字符串轉化爲數字,例如'12.3b'?

      * parseFloat('12.3b');
      * 正則表達式,'12.3b'.match(/(\d)+(\.)?(\d)+/g)[0] * 1, 但是這個不太靠譜,提供一種思路而已。
    
  • 如何將浮點數點左邊的數每三位添加一個逗號,如12000000.11轉化爲『12,000,000.11』?

      function commafy(num){
      	return num && num
      		.toString()
      		.replace(/(\d)(?=(\d{3})+\.)/g, function($1, $2){
      			return $2 + ',';
      		});
      }
    
  • 如何實現數組的隨機排序?

      方法一:
      	var arr = [1,2,3,4,5,6,7,8,9,10];
      	function randSort1(arr){
      		for(var i = 0,len = arr.length;i < len; i++ ){
      			var rand = parseInt(Math.random()*len);
      			var temp = arr[rand];
      			arr[rand] = arr[i];
      			arr[i] = temp;
      		}
      		return arr;
      	}
      	console.log(randSort1(arr));
      	
      方法二:
      	var arr = [1,2,3,4,5,6,7,8,9,10];
      	function randSort2(arr){
      		var mixedArray = [];
      		while(arr.length > 0){
      			var randomIndex = parseInt(Math.random()*arr.length);
      			mixedArray.push(arr[randomIndex]);
      			arr.splice(randomIndex, 1);
      		}
      		return mixedArray;
      	}
      	console.log(randSort2(arr));
    
      方法三:
      	var arr = [1,2,3,4,5,6,7,8,9,10];
      	arr.sort(function(){
      		return Math.random() - 0.5;
      	})
      	console.log(arr);
    
  • Javascript如何實現繼承?

     1、構造繼承
     2、原型繼承
     3、實例繼承
     4、拷貝繼承
    
     原型prototype機制或apply和call方法去實現較簡單,建議使用構造函數與原型混合方式。
     
     	function Parent(){
     		this.name = 'wang';
     	}
    
     	function Child(){
     		this.age = 28;
     	}
     	Child.prototype = new Parent();//繼承了Parent,通過原型
    
     	var demo = new Child();
     	alert(demo.age);
     	alert(demo.name);//得到被繼承的屬性
    
  • JavaScript繼承的幾種實現方式?

  • javascript創建對象的幾種方式?

     javascript創建對象簡單的說,無非就是使用內置對象或各種自定義對象,當然還可以用JSON;但寫法有很多種,也能混合使用。
    
    
     1、對象字面量的方式
    
     	person={firstname:"Mark",lastname:"Yun",age:25,eyecolor:"black"};
    
     2、用function來模擬無參的構造函數
    
     	function Person(){}
     	var person=new Person();//定義一個function,如果使用new"實例化",該function可以看作是一個Class
     	person.name="Mark";
     	person.age="25";
     	person.work=function(){
     	alert(person.name+" hello...");
     	}
     	person.work();
    
     3、用function來模擬參構造函數來實現(用this關鍵字定義構造的上下文屬性)
    
     	function Pet(name,age,hobby){
     	   this.name=name;//this作用域:當前對象
     	   this.age=age;
     	   this.hobby=hobby;
     	   this.eat=function(){
     	      alert("我叫"+this.name+",我喜歡"+this.hobby+",是個程序員");
     	   }
     	}
     	var maidou =new Pet("麥兜",25,"coding");//實例化、創建對象
     	maidou.eat();//調用eat方法
    
    
     4、用工廠方式來創建(內置對象)
    
     	 var wcDog =new Object();
     	 wcDog.name="旺財";
     	 wcDog.age=3;
     	 wcDog.work=function(){
     	   alert("我是"+wcDog.name+",汪汪汪......");
     	 }
     	 wcDog.work();
    
    
     5、用原型方式來創建
    
     	function Dog(){
    
     	 }
     	 Dog.prototype.name="旺財";
     	 Dog.prototype.eat=function(){
     	 alert(this.name+"是個吃貨");
     	 }
     	 var wangcai =new Dog();
     	 wangcai.eat();
    
    
     5、用混合方式來創建
    
     	function Car(name,price){
     	  this.name=name;
     	  this.price=price;
     	}
     	 Car.prototype.sell=function(){
     	   alert("我是"+this.name+",我現在賣"+this.price+"萬元");
     	  }
     	var camry =new Car("凱美瑞",27);
     	camry.sell();
    
  • Javascript作用鏈域?

     全局函數無法查看局部函數的內部細節,但局部函數可以查看其上層的函數細節,直至全局細節。
     當需要從局部函數查找某一屬性或方法時,如果當前作用域沒有找到,就會上溯到上層作用域查找,
     直至全局函數,這種組織形式就是作用域鏈。
    
  • 談談This對象的理解。

  • this總是指向函數的直接調用者(而非間接調用者);

  • 如果有new關鍵字,this指向new出來的那個對象;

  • 在事件中,this指向觸發這個事件的對象,特殊的是,IE中的attachEvent中的this總是指向全局對象Window;

  • eval是做什麼的?

     它的功能是把對應的字符串解析成JS代碼並運行;
     應該避免使用eval,不安全,非常耗性能(2次,一次解析成js語句,一次執行)。
     由JSON字符串轉換爲JSON對象的時候可以用eval,var obj =eval('('+ str +')');
    
  • 什麼是window對象? 什麼是document對象?

     window對象是指瀏覽器打開的窗口。
     document對象是Documentd對象(HTML 文檔對象)的一個只讀引用,window對象的一個屬性。
    
  • null,undefined 的區別?

     null 		表示一個對象是“沒有值”的值,也就是值爲“空”;
     undefined 	表示一個變量聲明瞭沒有初始化(賦值);
    
     undefined不是一個有效的JSON,而null是;
     undefined的類型(typeof)是undefined;
     null的類型(typeof)是object;
    
    
     Javascript將未賦值的變量默認值設爲undefined;
     Javascript從來不會將變量設爲null。它是用來讓程序員表明某個用var聲明的變量時沒有值的。
    
     typeof undefined
     	//"undefined"
     	undefined :是一個表示"無"的原始值或者說表示"缺少值",就是此處應該有一個值,但是還沒有定義。當嘗試讀取時會返回 undefined;
     	例如變量被聲明瞭,但沒有賦值時,就等於undefined
    
     typeof null
     	//"object"
     	null : 是一個對象(空對象, 沒有任何屬性和方法);
     	例如作爲函數的參數,表示該函數的參數不是對象;
    
     注意:
     	在驗證null時,一定要使用 === ,因爲 == 無法分別 null 和 undefined
     	null == undefined // true
     	null === undefined // false
    
     再來一個例子:
    
     	null
     	Q:有張三這個人麼?
     	A:有!
     	Q:張三有房子麼?
     	A:沒有!
    
     	undefined
     	Q:有張三這個人麼?
     	A:有!
     	Q: 張三有多少歲?
     	A: 不知道(沒有被告訴)
    

    參考閱讀:undefined與null的區別

  • 寫一個通用的事件偵聽器函數。

     	// event(事件)工具集,來源:github.com/markyun
     	markyun.Event = {
     		// 頁面加載完成後
     		readyEvent : function(fn) {
     			if (fn==null) {
     				fn=document;
     			}
     			var oldonload = window.onload;
     			if (typeof window.onload != 'function') {
     				window.onload = fn;
     			} else {
     				window.onload = function() {
     					oldonload();
     					fn();
     				};
     			}
     		},
     		// 視能力分別使用dom0||dom2||IE方式 來綁定事件
     		// 參數: 操作的元素,事件名稱 ,事件處理程序
     		addEvent : function(element, type, handler) {
     			if (element.addEventListener) {
     				//事件類型、需要執行的函數、是否捕捉
     				element.addEventListener(type, handler, false);
     			} else if (element.attachEvent) {
     				element.attachEvent('on' + type, function() {
     					handler.call(element);
     				});
     			} else {
     				element['on' + type] = handler;
     			}
     		},
     		// 移除事件
     		removeEvent : function(element, type, handler) {
     			if (element.removeEventListener) {
     				element.removeEventListener(type, handler, false);
     			} else if (element.datachEvent) {
     				element.detachEvent('on' + type, handler);
     			} else {
     				element['on' + type] = null;
     			}
     		},
     		// 阻止事件 (主要是事件冒泡,因爲IE不支持事件捕獲)
     		stopPropagation : function(ev) {
     			if (ev.stopPropagation) {
     				ev.stopPropagation();
     			} else {
     				ev.cancelBubble = true;
     			}
     		},
     		// 取消事件的默認行爲
     		preventDefault : function(event) {
     			if (event.preventDefault) {
     				event.preventDefault();
     			} else {
     				event.returnValue = false;
     			}
     		},
     		// 獲取事件目標
     		getTarget : function(event) {
     			return event.target || event.srcElement;
     		},
     		// 獲取event對象的引用,取到事件的所有信息,確保隨時能使用event;
     		getEvent : function(e) {
     			var ev = e || window.event;
     			if (!ev) {
     				var c = this.getEvent.caller;
     				while (c) {
     					ev = c.arguments[0];
     					if (ev && Event == ev.constructor) {
     						break;
     					}
     					c = c.caller;
     				}
     			}
     			return ev;
     		}
     	};
    
  • ["1", "2", "3"].map(parseInt) 答案是多少?

     parseInt() 函數能解析一個字符串,並返回一個整數,需要兩個參數 (val, radix),
     其中 radix 表示要解析的數字的基數。【該值介於 2 ~ 36 之間,並且字符串中的數字不能大於radix才能正確返回數字結果值】;
     但此處 map 傳了 3 個 (element, index, array),我們重寫parseInt函數測試一下是否符合上面的規則。
    
     function parseInt(str, radix) {
         return str+'-'+radix;
     };
     var a=["1", "2", "3"];
     a.map(parseInt);  // ["1-0", "2-1", "3-2"] 不能大於radix
    
     因爲二進制裏面,沒有數字3,導致出現超範圍的radix賦值和不合法的進制解析,纔會返回NaN
     所以["1", "2", "3"].map(parseInt) 答案也就是:[1, NaN, NaN]
    
     詳細解析:http://blog.csdn.net/justjavac/article/details/19473199
    
  • 事件是?IE與火狐的事件機制有什麼區別? 如何阻止冒泡?

      1. 我們在網頁中的某個操作(有的操作對應多個事件)。例如:當我們點擊一個按鈕就會產生一個事件。是可以被 JavaScript 偵測到的行爲。
      2. 事件處理機制:IE是事件冒泡、Firefox同時支持兩種事件模型,也就是:捕獲型事件和冒泡型事件;
      3. ev.stopPropagation();(舊ie的方法 ev.cancelBubble = true;)
    
  • 什麼是閉包(closure),爲什麼要用它?

     閉包是指有權訪問另一個函數作用域中變量的函數,創建閉包的最常見的方式就是在一個函數內創建另一個函數,通過另一個函數訪問這個函數的局部變量,利用閉包可以突破作用鏈域,將函數內部的變量和方法傳遞到外部。
    
     閉包的特性:
    
     1.函數內再嵌套函數
     2.內部函數可以引用外層的參數和變量
     3.參數和變量不會被垃圾回收機制回收
    
     //li節點的onclick事件都能正確的彈出當前被點擊的li索引
      <ul id="testUL">
         <li> index = 0</li>
         <li> index = 1</li>
         <li> index = 2</li>
         <li> index = 3</li>
     </ul>
     <script type="text/javascript">
       	var nodes = document.getElementsByTagName("li");
     	for(i = 0;i<nodes.length;i+= 1){
     	    nodes[i].onclick = (function(i){
     	              return function() {
     	                 console.log(i);
     	              } //不用閉包的話,值每次都是4
     	            })(i);
     	}
     </script>
    
    
    
     執行say667()後,say667()閉包內部變量會存在,而閉包內部函數的內部變量不會存在
     使得Javascript的垃圾回收機制GC不會收回say667()所佔用的資源
     因爲say667()的內部函數的執行需要依賴say667()中的變量
     這是對閉包作用的非常直白的描述
    
       function say667() {
     	// Local variable that ends up within closure
     	var num = 666;
     	var sayAlert = function() {
     		alert(num);
     	}
     	num++;
     	return sayAlert;
     }
    
      var sayAlert = say667();
      sayAlert()//執行結果應該彈出的667
    
  • javascript 代碼中的"use strict";是什麼意思 ? 使用它區別是什麼?

     use strict是一種ECMAscript 5 添加的(嚴格)運行模式,這種模式使得 Javascript 在更嚴格的條件下運行,
    
     使JS編碼更加規範化的模式,消除Javascript語法的一些不合理、不嚴謹之處,減少一些怪異行爲。
     默認支持的糟糕特性都會被禁用,比如不能用with,也不能在意外的情況下給全局變量賦值;
     全局變量的顯示聲明,函數必須聲明在頂層,不允許在非函數代碼塊內聲明函數,arguments.callee也不允許使用;
     消除代碼運行的一些不安全之處,保證代碼運行的安全,限制函數中的arguments修改,嚴格模式下的eval函數的行爲和非嚴格模式的也不相同;
    
     提高編譯器效率,增加運行速度;
     爲未來新版本的Javascript標準化做鋪墊。
    
  • 如何判斷一個對象是否屬於某個類?

       使用instanceof (待完善)
        if(a instanceof Person){
            alert('yes');
        }
    
  • new操作符具體幹了什麼呢?

     	 1、創建一個空對象,並且 this 變量引用該對象,同時還繼承了該函數的原型。
       	 2、屬性和方法被加入到 this 引用的對象中。
     	 3、新創建的對象由 this 所引用,並且最後隱式的返回 this 。
    
     var obj  = {};
     obj.__proto__ = Base.prototype;
     Base.call(obj);
    
  • 用原生JavaScript的實現過什麼功能嗎?

  • Javascript中,有一個函數,執行時對象查找時,永遠不會去查找原型,這個函數是?

     hasOwnProperty
    
     javaScript中hasOwnProperty函數方法是返回一個布爾值,指出一個對象是否具有指定名稱的屬性。此方法無法檢查該對象的原型鏈中是否具有該屬性;該屬性必須是對象本身的一個成員。
     使用方法:
     object.hasOwnProperty(proName)
     其中參數object是必選項。一個對象的實例。
     proName是必選項。一個屬性名稱的字符串值。
    
     如果 object 具有指定名稱的屬性,那麼JavaScript中hasOwnProperty函數方法返回 true,反之則返回 false。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章