`

JQlite

阅读更多
在电影《叶问》中,甄子丹饰演的叶问每天会利用木人桩练习武艺,使得泳春拳法成为肌肉记忆的一部分。临场迎敌时,身体会使用正确的拳式,自然而然。

我以为JS编程基本功的练习于武术拳法的练习是一样的。通过一套有效的『拳法』将JS基本功内置其中,反复练习,使得JS技艺成为手指记忆的一部分。这样,当面对实际开发时,我们就不需要为基本技艺而费神,将更多时间应用在业务逻辑的思考上。

那么哪一套『拳法』更适合作为木人桩的演习拳法呢?我个人推荐jQuery。一方面是因为jQuery作为使用量最大的JS类库,最适合学以致用的原则;另一方面,jQuery的设计几乎涵盖了JS编程基本功需要的所有技巧。

基于此,我从jQuery中抽取了一些核心技术实现,并将其设计成为了一套可以反复练习的JSKata。其中涉及了JS在实战过程中会反复出现的技艺和模式,勤加练习,便可轻松应用大部分的JS开发实践了。

函数定义

函数,是JavaScript语言中的一等公民。何以见得?见下图:
> var i = 5;
undefined
> var str = 'abc'
undefined
> typeof i
'number'
> typeof str
'string'
> typeof Number
'function'
> typeof String
'function'
> typeof Function
'function'


函数有三种定义方式。

匿名函数
var fn = function(name) {
    return 'hello, ' + name;
};

具名函数
function fn (name) { 
   return 'hello, ' + name;
}

函数对象的创建
var fn = new Function('name','return "hello, " + name');

匿名函数是最常用的一种函数定义方式,具名函数相对于匿名函数会提升变量的声明时机,在调试的时候,也会有名称标识。 然而匿名函数是通过一个变量来指向一个匿名函数,当这个函数不再需要时,JS的运行时环境会自动收集内存垃圾。

jQuery的$

jQuery的$可以非常方便的选取DOM对象。而它实际上是一个函数:
var $ = function(selector) {
    return document.querySelector(selector);
};

字面量对象

JavaScript是一种动态的面向对象语言:
var o = new Object();
o.name = 'jobs';
o.age = 55;
o.sayHello = function() {
    console.log(this.name + ":" + this.age);
};

但它更推荐字面量的定义方式:

var o = {
    name:'jobs',
    age:55,
    sayHello:function() {
        console.log(this.name + ":" + this.age);
    }
};

jQuery的show/hide方法

show/hide函数利用DOM封装了CSS样式表操作,作为方法以对象的属性存在:

var $ = function(selector) {
    var el = document.querySelector(selector);
    var o = {
        hide:function() {
            el.style.display = 'none';
        },
        show:function(){
            el.style.display = 'block';
        }
    };
    return o;
};


JS对象是一种集合

JavaScript对象以一种类集合的方式存在:
for(var key in o){
    console.log(key + ":" + o[key]);
}
console.log(o.name === o['name']);

这个特性非常灵活,可以动态的根据字符串获取或者设置属性信息。

jQuery的getStyle/css方法
getStyle: function(name) {
    var style = document.defaultView.getComputedStyle(el);
    return style[name];
},
css:function(options) {
    for(var attr in options){
        el.style[attr] = options[attr];
    }
}


回调

函数也是对象:
var fn = new Function('name','return "hello, " + name');

和其它对象一样,JavaScript也允许将函数对象作为参数传给另外一个函数:

var foo = function(arg) {
    if(typeof arg === 'function')
        console.log(arg('jobs'));
    else
        console.log(arg);
};
foo(function(arg){
    return 'hello, ' + arg;
});

因为不知道会有什么样的客户实现,所以可以利用回调将客户实现的定义延迟到服务调用的时候,如jQuery的ready方法:
$(document).ready(function(){
    
});

下面这个示例是NodeJS利用回调函数快速构建的一个静态服务器:
var http = require('http'),
    fs = require('fs');
http.createServer(function(req, res) {
    var path = req.url.slice(1);
    fs.exists(path,function(exist){
            console.log(path);
        if(exist){
            fs.readFile(path,'utf-8',function(err,content){
                res.write(content);
                res.end();
            });
        }        else{
            res.write('404');
            res.end();
        }
    });
}).listen(9432);

jQuery的bind方法

bind: function(event, fn) {
    el.addEventListener(event, fn);
}

构造器

JavaScript的字面量对象非常方便,但是当我们需要创建一批具有相同方法的对象时,使用构造器会更加便捷:

var Person = function(name) {
    this.name = name; 
    this.sayHello = function() {
       return "Hello, " + this.name;
    };
};
var o1 = new Person('jobs');
var o2 = new Person('gates');

o1、o2都可调用sayHello方法,但是却来自两块内存。创建的对象越多,浪费的内存就越多。 可是如何减少内存的浪费呢?

函数作用域

默认情况下,函数的作用域由local和global组成。 有时候,我们应该将经常使用的global对象通过参数传递到local里,以节省内存:

var fn = function(document,a,b,c) {
    console.log('break');
    var e,d,f;
    e = function() {};
    function d () {}
    f = 5;

};
fn(document);

也可以将变量封装到函数中,以达到Private的效果:

var Person = (function() {    //private
    var sayHello = function() { 
       return 'Hello, ' + this.name;
    }    //public
    return function(name) {
       this.name = name;
       this.sayHello = sayHello;
    };
})();

Prototype

prototype属性允许通过构造器创建的对象重用现有方法:

var Person = function(name) {
    this.name = name;
};
Person.prototype.sayHello = function() {
    return "Hello, " + this.name;
};
var o1 = new Person('jobs');
var o2 = new Person('gates');

o1与o2的sayHello方法指向同一块内存地址。var o1 = new Person('jobs');等同于以下代码:

var o1 = new Object();
o1.__proto__ = Person.prototype;
Person.call(o1,'jobs');

使用prototype,可以为JavaScript插上飞翔的翅膀:
Function.prototype.method = function(name,fn) {
    this.prototype[name] = fn;
    return this;
};
function Person (name) {
    this.name = name;
}
Person
.method('sayHello',function() {
     return 'Hello,' + this.name;
})
.method('show',function() {
     return 'show';
});
var jobs = new Person('jobs');
console.log('Hello,jobs' === jobs.sayHello());
console.log('show' === jobs.show());

this

如果函数是直接调用的,那么this应该是全局作用域(window or global)

var fn = function(name) {
    this.name = name;
};
fn('jobs');

如果函数是通过对象调用的,那么this应该就是那个对象:
var fn = function(name) {
    this.name = name;
};
var o = {
    setName:fn
}
o.setName('jobs');

this取决于函数的调用,而不是函数的定义:

var fn = function(name) {
    this.name = name;
};
var o = {
    setName:fn
}
var method = o.setName;
method('jobs');

因为函数实际上是函数对象,其中包括了两个方法call,apply。 通过call和apply,可以通过第一个参数指定this:

var fn = function(name) {
    this.name = name;
};
// var fn = new Function('name','this.name = name');
var o = {};
fn.call(o,'jobs');
fn.apply(o,['jobs']);

如果通过构造器来调用,那么this就是创建出来的那个对象:

var Person = function(name) {
    this.name = name;
    this.sayHello = function() {
            return 'Hello, ' + this.name;
    };
    this.show = function() {
            console.log(this.name);
    }
};
var o1 = new Person('jobs');

arguments

arguments是JavaScript的关键字,实际的参数是传给arguments的,而定义的参数实际上相当于根据index取arguments相对应的值

var fn = function() {
    console.log(arguments);
};

fn(5,6,'abc',[3,4,5]);

jQuery的fn

var $ = function(selector) {
    return new $.fn.init(selector);
};
$.fn = $.prototype = {
    init:function(selector) { 
        this.el = document.querySelector(selector);
        for(var method in $.fn){
           this[method] = $.fn[method];
        }
    },
    slideDown: function() {
        var height = parseInt(this.getStyle('height'));
        this.el.style.overflow = 'auto';
        var that = this;
        for (var i = 0; i <= height; i++) {
            (function(i) {
                var h = i;
                setTimeout(function() {
                    that.el.style.height = h + "px";
                }, h * 50);
            })(i);
        }
    },
    val:function(content) {
        if(typeof content === 'string'){ 
            this.el.value = content;
        }
        else{
            return this.el.value;
        }
    },
    append:function(e) {
       var tagRegexp = /^<(\w+)>(.*)<\/\1>$/;
       var match = tagRegexp.exec(e);
       var tag = document.createElement(match[1]);
       tag.innerHTML = match[2];
       this.el.appendChild(tag);
    },
    hide: function() {
       this.el.style['display'] = 'none';
    },
    show: function() {
       this.el.style['display'] = 'block';
    },
    getStyle: function(name) {
       var style = document.defaultView.getComputedStyle(this.el);
       return style[name];
    },
    css:function(options) {
       for(var attr in options){
           this.el.style[attr] = options[attr];
       }
    },
    bind: function(event, fn) {
       this.el.addEventListener(event, fn);
    }
}


转载至  [url=https://mp.weixin.qq.com/s?__biz=MzIxMjE4NzM5MA==&mid=402734795&idx=1&sn=4aad46fb822b73cbbe677e7fd7c717aa&scene=1&srcid=07011aI7OWcfb11SWIPkBZbd&key=77421cf58af4a65305382e3f51eb8831d39401df98d3686797e45cbf551866ea9a23f321906fcaee5e2e59156a2f0dbf&ascene=0&uin=MjAzNzM1NjQwMQ%3D%3D&devicetype=iMac+MacBookPro12%2C1+OSX+OSX+10.10.5+build(14F1808)&version=11020201&pass_ticket=GOKC%2BtdzItwvKmfRnnbZkw3quvjSCwM9a%2FC0UsWD1oVTWUQWQ8DPXMYI5MbjgTsT]JQlite
[/url]
分享到:
评论

相关推荐

    前端开源库-jeefo_jqlite

    **Jeefo_jqlite:前端开发中的轻量级库** Jeefo_jqlite是一款专为前端开发者设计的开源库,它源自Jeefo框架,致力于提供类似于jQuery的API,帮助开发者更高效地处理DOM操作。在JavaScript的前端开发环境中,jQuery...

    jqlite:使用系统SQLite构建的Janet SQLite模块

    **jqlite: 利用SQLite构建的Janet模块详解** `jqlite`是一个针对Janet编程语言的SQLite库,它允许Janet程序利用系统级别的SQLite数据库引擎进行数据存储和管理。Janet是一种动态类型的、快速的、通用的脚本语言,而...

    jqLite-standalone:angularjs中使用的lib jqLit​​e.js的独立版本

    这个压缩包文件"jqLite-standalone-master"包含了jqLite的独立版本,允许开发者在项目中单独使用这一组件,而无需引入整个jQuery库。 ### jqLite简介 jqLite提供了与jQuery类似的API,包括选择器、DOM操作、事件...

    angular-drag:一个简单的指令,用于拖动给定容器中的元素,仅依赖于angular提供的jqlite

    一个简单的指令,它仅依赖于angular提供的jqlite来拖动给定容器中的元素。 执照 MIT许可证(MIT) 版权所有(c)2016 drayvock 特此免费授予获得此软件和相关文档文件(“软件”)副本的任何人无限制地处理软件的...

    通过angular.element,变成jquery对象,改样式

    如果没有,它会返回一个类似于jQuery功能的JQLite对象,JQLite是AngularJS内部的一个轻量级版本的jQuery,包含了一些基本的DOM操作方法。 要使用`angular.element`,你可以直接传入一个DOM元素、HTML字符串或者选择...

    angularjs初学者速成笔记

    6. **JQLite**:AngularJS 自带了一个轻量级的jQuery库,称为JQLite。它提供了基本的DOM操作,如选择元素、事件绑定和CSS操作。在没有完整jQuery环境中,JQLite是AngularJS的标准选择。 7. **angular模块设计**:...

    Angular.js指令学习中一些重要属性的用法教程

    `scope`是指令作用域,`iEle`是元素对象,可以使用jqLite操作,`iAttrs`是元素属性的集合。例如,我们可以通过`link`函数绑定事件和处理逻辑: ```javascript link: function(scope, iEle, iAttrs) { iEle.bind('...

    AngularJS的启动过程---加上了指令执行机制框图.pdf

    - 如果项目中使用了jQuery,AngularJS会尝试绑定jQuery,使其成为Angular内部的JQLite库的默认实现。如果没有jQuery,Angular将使用其内置的JQLite库。 3. **发布ng提供的API**: - `publishExternalAPI(angular);...

    在AngularJS应用中实现一些动画效果的代码

    `element`参数是正在执行动画的DOM元素,可以是jQlite对象或jQuery对象。`done`是一个回调函数,表示动画结束,它必须在动画完成时被调用,以便告诉AngularJS动画已经完成,可以继续执行后续操作。 AngularJS内置...

    angular和jquery例子--IntegralUI-Studio-Web-TRIAL

    此外,你可能还会遇到一些关于如何在 Angular 中优雅地集成 jQuery 的最佳实践,比如使用 Angular's jqLite(一个小版本的 jQuery)来避免引入完整的 jQuery 库,从而减少页面加载时间。或者,你可能看到如何使用 ...

    AngularJS封装jQuery DateTimepicker

    然而,有时出于性能或兼容性的考虑,可能需要将jQuery或其轻量级版本jQuery Lite(也称为jqLite)引入项目中。这篇博文可能会介绍如何在AngularJS的应用环境中引入jQuery,以及如何使用jQuery DateTimepicker插件。 ...

    Inputmask:输入掩码插件

    Inputmask可以针对原始javascript,jQuery和jqlite运行。 输入掩码通过确保预定义格式来帮助用户进行输入。 这对于日期,数字,电话号码等有用。 强调: 便于使用面罩中任何位置的可选部件定义别名以隐藏复杂性的...

    angular-tutorial:一些角度教程-《 Angular学习笔记》

    "jqlite"是Angular内嵌的一个轻量级jQuery库,名为jQuery Lite或 jqLite。它提供了基本的DOM操作,如选择元素、事件处理和CSS操作,但功能比完整的jQuery库更为有限。在没有完整jQuery环境的场合,jqlite确保了...

    AngularJS中的DOM操作用法分析

    2. jQLite:在AngularJS中,jQLite是一个轻量级的jQuery实现,它提供了一些基本的jQuery操作方法。jQLite是为那些希望在AngularJS中继续使用jQuery语法的开发者提供的。当一个页面中已经包含了jQuery时,AngularJS会...

    Angular.JS通过指令操作DOM的方法

    AngularJS内建了一个轻量级的jQuery库——jqLite,它提供了一些基本的DOM操作功能。 jqLite虽然不包含jQuery的所有方法,但足以满足大部分基础操作,如选择元素、事件处理、属性操作等。如果你的项目已经包含了...

    jquery.redirect:jQuery重定向插件

    与jQuery,jQlite和Zepto.js兼容 支持嵌套对象和数组 它是如何工作的? jQuery.redirect函数将创建一个表单,并使用数据填充它(它支持嵌套值)。 安装 使用凉亭 bower install jquery.redirect 使用NPM npm ...

    angularJs中跳转到指定的锚点实例($anchorScroll)

    $anchorScroll ... 监听$location.hash()并且滚动到url指定的锚点的地方。 可以通过$anchorScrollProvider.disableAutoScrolling()禁用。...属性:number function(){} jqLite 如果设置了这个值,将会

    fz_select:使用angularjs的引导选择组件

    要求:Angular 1.0+ Jquery(仅因为jqlite没有prev()) 使用angularjs的引导选择组件 大多数文档位于fz_select.js中,将在以后进行更新 这是组件的演示 这是重写组件样式的方法,这将更改fz-select-bs样式的...

    AngularJS-simple-introduction:AngularJS简易入门

    angular 对象包含了一个精简版的jQuery ,叫做jqLite 。可以使得Angular做一些简单的DOM操作。AngularJS 模块在AngularJS中,一切都被封装在模块之中。AngularJS需要至少一个模块来进行操作。应用模块AngularJS需要...

    angular-scroll-website

    角滚动 Angular 只是依赖(没有 jQuery)。 8K 缩小或 2K 压缩。 例子 查看或。... 在名称冲突的情况下,现有的 jQuery 或 jqlite 函数将被保留,只需使用前缀版本:即.duScrollTo()而不是.scrollTo

Global site tag (gtag.js) - Google Analytics