javascript进阶(三)

javascript进阶(三)

javascript进阶(三)


小草的主博客:http://xiaocaoblog.diandian.com

最近在看《编写高质量代码-web前端修炼之道》,写了3篇博客,记下看的东西。


第一篇写了关于javascript封装以及模块化插件设计。

第二篇写了关于javascript面向对象思想以及原型和构造器。

第三篇主要写关于javascript的编写风格以及细节设计问题。


一、全局变量、全局函数     如果是很多人一起开发一个项目,那么就会造成很多的重命名的事件。这个时候就要一个局部函数,替换全局函数。

    假设,程序员A写了段代码:

1
2
3
4
function a(){
         var a= "a is in function a(), writed by B" ;
         alert( "It's writed by A!!" );
     }

    然后程序员B写了端代码:

1
2
3
4
function a(){
         var a= "a is in function a(), writed by B" ;
         alert( "It's writed by B!!" );
     }

    如果我想要在一个页面同时包含这个两个函数,那么很简单,我们要用到匿名函数。

1
2
3
4
5
6
7
8
9
10
11
/*=========下面是A写的==========*/
( function a(){
     var a= "a is in function a(), writed by B" ;
     alert( "It's writed by A!!" );
})();
/*=========下面是B写的==========*/
( function a(){
     var a= "a is in function a(), writed by B" ;
     alert( "It's writed by B!!" );
})();
//它们不会互相影响

    但是,如果我想要在A写的函数和B写的函数间传值,那么要怎么办?全局变量?可是一般最尽量不要用全局变量。

    那就建个数组,造个对象,存放数据。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var global={ };
 
/*=========下面是A写的==========*/
( function a(){
     global.A.a= "a is in function a(), writed by B" ;
     global.A.b= function (){alert( "It's writed by A!!" );};       
})();
/*=========下面是B写的==========*/
( function a(){
     global.B.a= "a is in function a(), writed by B" ;
     global.B.b= function (){alert(global.A.a);};
     //return alert("alert("It's writed by A!!");
     //这样就实现了匿名函数间传值,又防止了命名冲突
})();

    这样子看起来是不是有些像prototype原型样式了。

1
2
3
4
var A;
A.prototype.a= function (){ };
A.prototype.b= function (){ };
A.prototype.c= function (){ };

    写个封装函数吧,不然每次都要写一大堆。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var globale={ };
global.namespace= function (str){
     var arr = str.split( "." ), o=global;
     for (i=(arr[0] == "global" ) ? 1 : 0 ; i<arr.length; i++){
         o[ arr[ i ] ] = o[ arr[ i ] ] = { };
         o=o[ arr[ i ] ];   
     }
};
/*===========测试===========*/
global.namespace( "A.start" );
global.namespace( "A.end" );
 
global.A.start= function (){ alert( "test:global.A.start" ) };
global.A.end= function (){ alert( "global.A.end" ) };

二、函数入口     javascript是种脚本语言,浏览器执行渲染工作,javascript加载到哪一行,就渲染哪一行的语句,所以js的排放位置很重要,js的函数入口也很重要。

1
2
3
4
5
6
function A(){
     alert( "just test" );
}
var B = function (){
     alert( "just test" );
}

    其实这两个函数都是一样的结果,但是,函数的意义不一样。当函数加载进来,就会直接执行A();然而函数B要调用。

  • 用window.onload监听,会在网页元素全部加载完毕后触发onload事件。
  • 用init();在DOMReady加载。

DOMReady只判断节点是否加载完毕,所以触发速度比window.onload快。 DOMReady不是原生的Javascript事件,要通过就是框架调用。

三、扩展原型函数

javascript是基于原型的语言,但是,并不是所有函数都要new实例化。

在js里面却没有each,clone等函数,所以我们可以拓展,重写内置类行为:

1
2
3
4
5
6
7
8
9
10
11
12
13
Array.pototype.each= function ( callback ){
     for ( var i=0; i< this .length; i++)
         callback( this [ i ], i ); //对每个对象实行回调函数
}
 
Array.pototype.clone= function (){
     var o = [];
     this .each( function (k, v){
         o[ k ] = v;
     });
     return o;
     //我感觉我在写jquery的内核函数了。。
}

并且,还可以扩展内置类了。所有类的祖先都是在Object里面。

1
2
3
4
5
6
7
8
9
Object.prototype.test= function (){
     return this .value; 
};
/*==========测试=========*/
var xiaocao={ };
xiaocao.value= "小草是帅哥" ;
 
alert(xiaocao.test());
//return 小草是帅哥;

四、改变DOM

方法一:

1
2
3
4
<div class= "test" id= "test" >测试</div>
<script>
     document.getelementById( "test" ).style= "font-size:20px;" ;
</script>

不实用。

方法二:

1
2
3
4
5
6
7
8
<style>
     class_name:{font-size:30px;}
     </style>
     <div id= "test" >测试</div>
     <script>
     var node = document.getelementById( "test" ).style= "font-size:20px;" ;
node.className= "class_name" ;
     </script>  

方法三:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<script>
function addStyle(str){
     var style_node = document.creatElement( "style" );
     style_node.type= "text/css" ;
     if (style_node.styleSheet ){
         style_node.styleSheet.cssText = str;
     } else {
         style_node.innerHTML = str;
     }
     document.getElementByTagname( "head" )[0].appendChild(style_node);
     }
     /*==============可以调用了============*/
     addStyle( "#test{font-size:30px;}" );
</script>  

获取节点的属性:

1
2
3
4
5
6
7
8
9
10
11
12
<div id= "test" nick_name= "xiaocao" ></div>
<script>
     var node=document.getElementById( "test" );
     function (){
         alert(node.nick_name);
         //IE==>>xiaocao
         //firfox==>>null
 
         alert(node.getAttribute);
         //IE&&firfox==>>xiaocao
     }
</script>

也就是说,自定义标签属性,最好用attribute节点访问。


五、看看自己究竟写了什么恶心的代码:

    其实,让我们来看个几个我以前写代码风格的例子,就会发现,一些问题。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
function count_keys(symbol){
     var key;
     var _key=localStorage.getItem( "result1" );
     var _key_=localStorage.getItem( "result2" );
     var key_=localStorage.getItem( "result3" );
 
  if (symbol.slice(0,1)==symbol.slice(1)) //符号为+ +,- -,x x
key=count(count(_key,_key_,symbol.slice(0,1)),key_,symbol.slice(1));
     if (symbol.slice(0,1)==1 && symbol.slice(1)==0 || symbol.slice(0,1)==0 && symbol.slice(1)==1) //符号为- +;+ -
key=count(count(_key,_key_,symbol.slice(0,1)),key_,symbol.slice(1));
     if (symbol.slice(0,1)==0 && symbol.slice(1)==2 || symbol.slice(0,1)==1 && symbol.slice(1)==2) //符号为+ x;- x
key=count(_key,count(_key_,key_,symbol.slice(1),symbol.slice(0,1)));
     if (symbol.slice(0,1)==2 && symbol.slice(1)==0 || symbol.slice(0,1)==2 && symbol.slice(1)==1)
key=count(count(_key,_key_,symbol.slice(0,1)),key_,symbol.slice(1));  //符号为x + ; x -
 
     return key;
}  

    看自己以前写的代码真觉得,很多废话,最主要的是,感觉逻辑性好差,构思一个代码段真的很难,高质量代码也好难,要先想好多逻辑性问题,列表,流程图,不然都是废话。     还有一点就是,参数逻辑性不强,每个函数的对接性不强,模式化基本没有。

1
2
3
4
5
6
7
8
var test=JSON.stringify(test);
var students = JSON.stringify(datas);
storage.setItem( 'data' ,students);
storage.setItem( 'xiaocao.test.1' ,test);
//var obj = storage.getItem('data');
var obj = eval( "(" + storage.getItem( 'data' ) + ")" ); //将json转化为对象
console.log( '数量是:' +obj[1]+obj[2]+obj[3]+obj[4]+ '哈哈哈哈' +obj.num);
//console.log('名称分别是:'+obj.2);

全局变量很多,函数的封装性很差,没有模式化。总的来说,就是,功能实现了,但是,没头没脑想到什么写什么。

看几个例子:

很喜欢腾讯alloy团队那种封装好的代码。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
addEvent= function (selector, eventType, func){
             var proName = "" ;
             switch ( true ){
                 case /^\./.test(selector) :
                     proName = "className" ;
                     selector = selector.replace( "." , "" );
                     break ;
                 case /^\ #/.test(selector) :
                     proName = "id" ;
                     selector = selector.replace( "#" , "" );
                     break ;
                 default :
                     proName = "tagName" ;
             }
 
             document.body.addEventListener(eventType, function (e){
                     function check(node){
                         if (! node.parentNode) return ;
 
                         if (node[proName] == selector){
                             func.call(node, e);
                         };
                         check(node.parentNode);
                     }
                     check(e.target);
             }, false );
         }
     //这段超爱,后来,我就收藏了。

javascript进阶就到这里了。

接下来要做的事情就是准备后台了。先练熟python,然后用web.py和tornado.py框架做web。


夏日小草 2013/12/5 19:57:13
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值