執行個體講解避免javascript衝突的方法,執行個體講解javascript

來源:互聯網
上載者:User

執行個體講解避免javascript衝突的方法,執行個體講解javascript

本文執行個體講解了如何避免javascript中衝突的方法,需要的朋友可以瞭解一下

[1]工程師甲編寫功能A

var a = 1;var b = 2;alert(a+b);//3

[2]工程師乙添加新功能B

var a = 2;var b = 1;alert(a-b);//1

[3]上一步中,工程師乙在不知情的情況下,定義了同名變數a,產生衝突。於是使用匿名函數將指令碼包起來,讓變數範圍控制在匿名函數之內。

//功能A(function(){  var a = 1;  var b = 2;  alert(a+b);//3})();//功能B(function(){  var a = 2;  var b = 1;  alert(a-b);//1})();

[4]此時有了新需求,網頁中加入功能C,且需要用到功能A中的變數b。於是在window範圍下定義一個全域變數,把它作為一個橋樑,完成各匿名函數之間的通訊

//全域變數var str;//功能A(function(){  var a = 1;  //將b的值賦給str  var b = str = 2;  alert(a+b);//3})();//功能B(function(){  var a = 2;  var b = 1;  alert(a-b);//1})();//功能C(function(){  //將str的值賦給b  var b = str;  alert(b);//2})();

[5]但如果功能C還需要功能A中的變數a呢,這時就需要再定義一個全域變數

//全域變數var str,str1;//功能A(function(){  //將a的值賦給str1  var a = str1 = 1;  //將b的值賦給str  var b = str = 2;  alert(a+b);//3})();//功能B(function(){  var a = 2;  var b = 1;  alert(a-b);//1})();//功能C(function(){  //將str1的值賦給a  var a = str1;  //將str的值賦給b  var b = str;  alert(a*b);//2})(); 

[6]但隨著匿名函數之間需要通訊的變數越多,需要的全域變數也就越多。因此需要嚴格控制全域變數的數量,使用hash對象作為全域變數,可以將需要的變數都作為對象的屬性,可以保證全域變數的個數足夠少,同時拓展性非常好

//全域變數var GLOBAL = {};//功能A(function(){  //將a的值賦給GLOBAL.str1  var a = GLOBAL.str1 = 1;  //將b的值賦給GLOBAL.str  var b = GLOBAL.str = 2;  alert(a+b);//3})();//功能B(function(){  var a = 2;  var b = 1;  alert(a-b);//1})();//功能C(function(){  //將GLOBAL.str1的值賦給a  var a = GLOBAL.str1;  //將GLOBAL.str的值賦給b  var b = GLOBAL.str;  alert(a*b);//2})();

[7]但如果新增功能D,功能D需要和功能B通訊,並使用功能B指令碼中的變數a,開發功能D的是工程師丁

//全域變數var GLOBAL = {};//功能A(function(){  //將a的值賦給GLOBAL.str1  var a = GLOBAL.str1 = 1;  //將b的值賦給GLOBAL.str  var b = GLOBAL.str = 2;  alert(a+b);//3})();//功能B(function(){  //將a的值賦給GLOBAL.str1  var a = GLOBAL.str1 = 2;  var b = 1;  alert(a-b);//1})();//功能C(function(){  //將GLOBAL.str1的值賦給a  var a = GLOBAL.str1;  //將GLOBAL.str的值賦給b  var b = GLOBAL.str;  alert(a*b);//2})();//功能D(function(){  //將GLOBAL.str1的值賦給a  var a = GLOBAL.str1;  alert(a*2);//4})(); 

[8]由於工程師丁只關心自己的匿名函數和功能B的匿名函數,使用GLOBAL.str卻無意中覆蓋了功能A中設定的同名變數,導致功能C出錯。於是使用命名空間來解決這個問題,在不同的匿名函數下,根據功能聲明一個不同的命名空間,然後每個匿名函數中的GLOBAL對象的屬性都不要直接掛在GLOBAL對象上,而是掛在此匿名函數的命名空間下

//全域變數var GLOBAL = {};//功能A(function(){  GLOBAL.A = {};  //將a的值賦給GLOBAL.A.str1  var a = GLOBAL.A.str1 = 1;  //將b的值賦給GLOBAL.A.str  var b = GLOBAL.A.str = 2;  alert(a+b);//3})();//功能B(function(){  GLOBAL.B = {};  //將a的值賦給GLOBAL.B.str1  var a = GLOBAL.B.str1 = 2;  var b = 1;  alert(a-b);//1})();//功能C(function(){  //將GLOBAL.A.str1的值賦給a  var a = GLOBAL.A.str1;  //將GLOBAL.A.str的值賦給b  var b = GLOBAL.A.str;  alert(a*b);//2})();//功能D(function(){  //將GLOBAL.B.str1的值賦給a  var a = GLOBAL.B.str1;  alert(a*2);//4})(); 

[9]如果同一個匿名函數中的程式非常複雜,變數名很多,命名空間還可以進一步拓展,產生二級命名空間

//以功能A為例(function(){  var a = 1, b = 2;  GLOBAL.A = {};  GLOBAL.A.CAT = {};  GLOBAL.A.DOG = {};  GLOBAL.A.CAT.name = 'mimi';  GLOBAL.A.DOG.name = 'xiaobai';  GLOBAL.A.CAT.move = function(){};  GLOBAL.A.str1 = a;  GLOBAL.B.str = b;  })();

[10]因為產生命名空間是個非常常用的功能,進一步將產生命名空間的功能定義成一個函數,方便調用,完整版本改寫後的代碼如下

var GLOBAL = {};GLOBAL.namespace = function(str){  var arr = str.split('.');  var o = GLOBAL;  var start = 0;  if(arr[0] == 'GLOBAL'){    start = 1;  }else{    start = 0;  }  for(var i = start; i < arr.length; i++){    o[arr[i]] = o[arr[i]] || {};    o = o[arr[i]];  }};//功能A(function(){  var a = 1;  var b = 2;  GLOBAL.namespace('A.CAT');  GLOBAL.namespace('A.DOG');  GLOBAL.A.CAT.name = 'mimi';  GLOBAL.A.DOG.name = 'xiaobai';  GLOBAL.A.CAT.move = function(){};  GLOBAL.A.str1 = a;  GLOBAL.A.str = b;    alert(a+b);//3})();//功能B(function(){  var a = 2;  var b = 1;  GLOBAL.namespace('B');  GLOBAL.B.str1 = a;  alert(a-b);//1})();//功能C(function(){  var a = GLOBAL.A.str1;  var b = GLOBAL.A.str;  alert(a*b);//2})();//功能D(function(){  var a = GLOBAL.B.str1;  alert(a*2);//4})();

[11]代碼的衝突問題已經解決了,但可維護性並不強。比如,現在需要讓工程師甲去修改功能B。因為工程師甲寫的指令碼是關於功能A的,他並不知道功能B的指令碼情況。為了改善這種局面,需要給代碼添加適當的注釋。

var GLOBAL = {};GLOBAL.namespace = function(str){  var arr = str.split('.');  var o = GLOBAL;  var start = 0;  if(arr[0] == 'GLOBAL'){    start = 1;  }else{    start = 0;  }  for(var i = start; i < arr.length; i++){    o[arr[i]] = o[arr[i]] || {};    o = o[arr[i]];  }};/** @method 功能A:實現加法運算* @author 工程師甲* @connect 1234567* @time 2015-01-01*/(function(){  var a = 1;  var b = 2;  GLOBAL.namespace('A.CAT');  GLOBAL.namespace('A.DOG');  GLOBAL.A.CAT.name = 'mimi';  GLOBAL.A.DOG.name = 'xiaobai';  GLOBAL.A.CAT.move = function(){};  GLOBAL.A.str1 = a;  GLOBAL.A.str = b;    alert(a+b);//3})();/** @method 功能B:實現減法運算* @author 工程師乙* @connect 1234567* @time 2015-01-01*/(function(){  var a = 2;  var b = 1;  GLOBAL.namespace('B');  GLOBAL.B.str1 = a;  alert(a-b);//1})();/** @method 功能C:實現乘法運算* @author 工程師丙* @connect 1234567* @time 2015-01-01*/(function(){  var a = GLOBAL.A.str1;  var b = GLOBAL.A.str;  alert(a*b);//2})();/** @method 功能D:實現乘2運算* @author 工程師丁* @connect 1234567* @time 2015-01-01*/(function(){  var a = GLOBAL.B.str1;  alert(a*2);//4})();

讓javascript不再衝突,需要

  •   [1]避免全域變數的泛濫
  •   [2]合理使用命名空間
  •   [3]為代碼添加必要的注釋

以上就是本文的詳細內容,希望對大家的學習有所協助。

您可能感興趣的文章:
  • JS 學習筆記 防止發生命名衝突
  • jQuery庫與其他JS庫衝突的解決辦法
  • js不完美解決click和dblclick事件衝突問題
  • jquery與js函數衝突的兩種解決方案
  • 解決css和js的{}與smarty定界符衝突問題的兩種方法
  • js中單引號與雙引號衝突問題解決方案
  • 匯入extjs、jquery 檔案時$使用衝突問題解決方案
  • JQuery的$和其它JS發生衝突的快速解決方案
  • jQuery避免$符和其他JS庫衝突的方法對比
  • js函數名與form表單元素同名衝突的問題

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.