- var foo = 1,
- bar = foo;
-
- bar = 9;
-
- console.log(foo, bar); // => 1, 9
复杂类型: 相当于传引用
- var foo = [1, 2],
- bar = foo;
-
- bar[0] = 9;
-
- console.log(foo[0], bar[0]); // => 9, 9
- // bad
- var item = new Object();
-
- // good
- var item = {};
- // bad
- var superman = {
- class: 'superhero',
- default: { clark: 'kent' },
- private: true
- };
-
- // good
- var superman = {
- klass: 'superhero',
- defaults: { clark: 'kent' },
- hidden: true
- };
- // bad
- var items = new Array();
-
- // good
- var items = [];
- var someStack = [];
-
- // bad
- someStack[someStack.length] = 'abracadabra';
-
- // good
- someStack.push('abracadabra');
- var len = items.length,
- itemsCopy = [],
- i;
-
- // bad
- for (i = 0; i < len; i++) {
- itemsCopy[i] = items[i];
- }
-
- // good
- itemsCopy = items.slice();
- function trigger() {
- var args = [].slice.apply(arguments);
- ...
- }
- // bad
- var name = "Bob Parr";
-
- // good
- var name = 'Bob Parr';
-
- // bad
- var fullName = "Bob " + this.lastName;
-
- // good
- var fullName = 'Bob ' + this.lastName;
- // bad
- var errorMessage = 'This is a super long error that was thrown because of Batman. When you stop to think about how Batman had anything to do with this, you would get nowhere fast.';
-
- // bad
- var errorMessage = 'This is a super long error that \
- was thrown because of Batman. \
- When you stop to think about \
- how Batman had anything to do \
- with this, you would get nowhere \
- fast.';
-
- // good
- var errorMessage = 'This is a super long error that ' +
- 'was thrown because of Batman.' +
- 'When you stop to think about ' +
- 'how Batman had anything to do ' +
- 'with this, you would get nowhere ' +
- 'fast.';
- var items,
- messages,
- length, i;
-
- messages = [{
- state: 'success',
- message: 'This one worked.'
- },{
- state: 'success',
- message: 'This one worked as well.'
- },{
- state: 'error',
- message: 'This one did not work.'
- }];
-
- length = messages.length;
-
- // bad
- function inbox(messages) {
- items = '<ul>';
-
- for (i = 0; i < length; i++) {
- items += '<li>' + messages[i].message + '</li>';
- }
-
- return items + '</ul>';
- }
-
- // good
- function inbox(messages) {
- items = [];
-
- for (i = 0; i < length; i++) {
- items[i] = messages[i].message;
- }
-
- return '<ul><li>' + items.join('</li><li>') + '</li></ul>';
- }
- // 匿名函数表达式
- var anonymous = function() {
- return true;
- };
-
- // 有名函数表达式
- var named = function named() {
- return true;
- };
-
- // 立即调用函数表达式
- (function() {
- console.log('Welcome to the Internet. Please follow me.');
- })();
- // bad
- if (currentUser) {
- function test() {
- console.log('Nope.');
- }
- }
-
- // good
- if (currentUser) {
- var test = function test() {
- console.log('Yup.');
- };
- }
- // bad
- function nope(name, options, arguments) {
- // ...stuff...
- }
-
- // good
- function yup(name, options, args) {
- // ...stuff...
- }
- var luke = {
- jedi: true,
- age: 28
- };
-
- function getProp(prop) {
- return luke[prop];
- }
-
- var isJedi = getProp('jedi');
- // bad
- superPower = new SuperPower();
-
- // good
- var superPower = new SuperPower();
- // bad
- var items = getItems();
- var goSportsTeam = true;
- var dragonball = 'z';
-
- // good
- var items = getItems(),
- goSportsTeam = true,
- dragonball = 'z';
- // bad
- var i, len, dragonball,
- items = getItems(),
- goSportsTeam = true;
-
- // bad
- var i, items = getItems(),
- dragonball,
- goSportsTeam = true,
- len;
-
- // good
- var items = getItems(),
- goSportsTeam = true,
- dragonball,
- length,
- i;
- // bad
- function() {
- test();
- console.log('doing stuff..');
-
- //..other stuff..
-
- var name = getName();
-
- if (name === 'test') {
- return false;
- }
-
- return name;
- }
-
- // good
- function() {
- var name = getName();
-
- test();
- console.log('doing stuff..');
-
- //..other stuff..
-
- if (name === 'test') {
- return false;
- }
-
- return name;
- }
-
- // bad
- function() {
- if (!arguments.length) {
- return false;
- }
-
- var name = getName();
-
- return true;
- }
-
- // good
- function() {
- var name = getName();
-
- if (!arguments.length) {
- return false;
- }
-
- return true;
- }
- if ([0]) {
- // true
- // An array is an object, objects evaluate to true
- }
- // bad
- if (name !== '') {
- // ...stuff...
- }
-
- // good
- if (name) {
- // ...stuff...
- }
-
- // bad
- if (collection.length > 0) {
- // ...stuff...
- }
-
- // good
- if (collection.length) {
- // ...stuff...
- }
- // bad
- if (test)
- return false;
-
- // good
- if (test) return false;
-
- // good
- if (test) {
- return false;
- }
-
- // bad
- function() { return false; }
-
- // good
- function() {
- return false;
- }
- // bad
- // make() returns a new element
- // based on the passed in tag name
- //
- // @param <String> tag
- // @return <Element> element
- function make(tag) {
-
- // ...stuff...
-
- return element;
- }
-
- // good
- /**
- * make() returns a new element
- * based on the passed in tag name
- *
- * @param <String> tag
- * @return <Element> element
- */
- function make(tag) {
-
- // ...stuff...
-
- return element;
- }
- // bad
- var active = true; // is current tab
-
- // good
- // is current tab
- var active = true;
-
- // bad
- function getType() {
- console.log('fetching type...');
- // set the default type to 'no type'
- var type = this._type || 'no type';
-
- return type;
- }
-
- // good
- function getType() {
- console.log('fetching type...');
-
- // set the default type to 'no type'
- var type = this._type || 'no type';
-
- return type;
- }
- function Calculator() {
-
- // FIXME: shouldn't use a global here
- total = 0;
-
- return this;
- }
- function Calculator() {
-
- // TODO: total should be configurable by an options param
- this.total = 0;
-
- return this;
- }
- // bad
- function() {
- ∙∙var name;
- }
-
- // bad
- function() {
- ∙var name;
- }
-
- // good
- function() {
- ∙∙∙∙var name;
- }
- // bad
- function test(){
- console.log('test');
- }
-
- // good
- function test() {
- console.log('test');
- }
-
- // bad
- dog.set('attr',{
- age: '1 year',
- breed: 'Bernese Mountain Dog'
- });
-
- // good
- dog.set('attr', {
- age: '1 year',
- breed: 'Bernese Mountain Dog'
- });
- // bad
- $('#items').find('.selected').highlight().end().find('.open').updateCount();
-
- // good
- $('#items')
- .find('.selected')
- .highlight()
- .end()
- .find('.open')
- .updateCount();
-
- // bad
- var leds = stage.selectAll('.led').data(data).enter().append('svg:svg').class('led', true)
- .attr('width', (radius + margin) * 2).append('svg:g')
- .attr('transform', 'translate(' + (radius + margin) + ',' + (radius + margin) + ')')
- .call(tron.led);
-
- // good
- var leds = stage.selectAll('.led')
- .data(data)
- .enter().append('svg:svg')
- .class('led', true)
- .attr('width', (radius + margin) * 2)
- .append('svg:g')
- .attr('transform', 'translate(' + (radius + margin) + ',' + (radius + margin) + ')')
- .call(tron.led);
- // bad
- var once
- , upon
- , aTime;
-
- // good
- var once,
- upon,
- aTime;
-
- // bad
- var hero = {
- firstName: 'Bob'
- , lastName: 'Parr'
- , heroName: 'Mr. Incredible'
- , superPower: 'strength'
- };
-
- // good
- var hero = {
- firstName: 'Bob',
- lastName: 'Parr',
- heroName: 'Mr. Incredible',
- superPower: 'strength'
- };
- // bad
- var hero = {
- firstName: 'Kevin',
- lastName: 'Flynn',
- };
-
- var heroes = [
- 'Batman',
- 'Superman',
- ];
-
- // good
- var hero = {
- firstName: 'Kevin',
- lastName: 'Flynn'
- };
-
- var heroes = [
- 'Batman',
- 'Superman'
- ];
- // bad
- (function() {
- var name = 'Skywalker'
- return name
- })()
-
- // good
- (function() {
- var name = 'Skywalker';
- return name;
- })();
-
- // good
- ;(function() {
- var name = 'Skywalker';
- return name;
- })();
- // => this.reviewScore = 9;
-
- // bad
- var totalScore = this.reviewScore + '';
-
- // good
- var totalScore = '' + this.reviewScore;
-
- // bad
- var totalScore = '' + this.reviewScore + ' total score';
-
- // good
- var totalScore = this.reviewScore + ' total score';
- var inputValue = '4';
-
- // bad
- var val = new Number(inputValue);
-
- // bad
- var val = +inputValue;
-
- // bad
- var val = inputValue >> 0;
-
- // bad
- var val = parseInt(inputValue);
-
- // good
- var val = Number(inputValue);
-
- // good
- var val = parseInt(inputValue, 10);
-
- // good
- /**
- * parseInt was the reason my code was slow.
- * Bitshifting the String to coerce it to a
- * Number made it a lot faster.
- */
- var val = inputValue >> 0;
- var age = 0;
-
- // bad
- var hasAge = new Boolean(age);
-
- // good
- var hasAge = Boolean(age);
-
- // good
- var hasAge = !!age;
- // bad
- function q() {
- // ...stuff...
- }
-
- // good
- function query() {
- // ..stuff..
- }
- // bad
- var OBJEcttsssss = {};
- var this_is_my_object = {};
- var this-is-my-object = {};
- function c() {};
- var u = new user({
- name: 'Bob Parr'
- });
-
- // good
- var thisIsMyObject = {};
- function thisIsMyFunction() {};
- var user = new User({
- name: 'Bob Parr'
- });
- // bad
- function user(options) {
- this.name = options.name;
- }
-
- var bad = new user({
- name: 'nope'
- });
-
- // good
- function User(options) {
- this.name = options.name;
- }
-
- var good = new User({
- name: 'yup'
- });
- // bad
- this.__firstName__ = 'Panda';
- this.firstName_ = 'Panda';
-
- // good
- this._firstName = 'Panda';
- // good
- function() {
- var self = this;
- return function() {
- console.log(self);
- };
- }
- // bad
- if (!dragon.age()) {
- return false;
- }
-
- // good
- if (!dragon.hasAge()) {
- return false;
- }
- function Jedi(options) {
- options || (options = {});
- var lightsaber = options.lightsaber || 'blue';
- this.set('lightsaber', lightsaber);
- }
-
- Jedi.prototype.set = function(key, val) {
- this[key] = val;
- };
-
- Jedi.prototype.get = function(key) {
- return this[key];
- };
- function Jedi() {
- console.log('new jedi');
- }
-
- // bad
- Jedi.prototype = {
- fight: function fight() {
- console.log('fighting');
- },
-
- block: function block() {
- console.log('blocking');
- }
- };
-
- // good
- Jedi.prototype.fight = function fight() {
- console.log('fighting');
- };
-
- Jedi.prototype.block = function block() {
- console.log('blocking');
- };
- // bad
- Jedi.prototype.jump = function() {
- this.jumping = true;
- return true;
- };
-
- Jedi.prototype.setHeight = function(height) {
- this.height = height;
- };
-
- var luke = new Jedi();
- luke.jump(); // => true
- luke.setHeight(20) // => undefined
-
- // good
- Jedi.prototype.jump = function() {
- this.jumping = true;
- return this;
- };
-
- Jedi.prototype.setHeight = function(height) {
- this.height = height;
- return this;
- };
-
- var luke = new Jedi();
-
- luke.jump()
- .setHeight(20);
- function Jedi(options) {
- options || (options = {});
- this.name = options.name || 'no name';
- }
-
- Jedi.prototype.getName = function getName() {
- return this.name;
- };
-
- Jedi.prototype.toString = function toString() {
- return 'Jedi - ' + this.getName();
- };
- // bad
- $(this).trigger('listingUpdated', listing.id);
-
- ...
-
- $(this).on('listingUpdated', function(e, listingId) {
- // do something with listingId
- });
更好:
- // good
- $(this).trigger('listingUpdated', { listingId : listing.id });
-
- ...
-
- $(this).on('listingUpdated', function(e, data) {
- // do something with data.listingId
- });
- // fancyInput/fancyInput.js
-
- (function(global) {
- 'use strict';
-
- var previousFancyInput = global.FancyInput;
-
- function FancyInput(options) {
- this.options = options || {};
- }
-
- FancyInput.noConflict = function noConflict() {
- global.FancyInput = previousFancyInput;
- return FancyInput;
- };
-
- global.FancyInput = FancyInput;
- })(this);
- // bad
- var menu = $(".menu");
-
- // good
- var $menu = $(".menu");
- // bad
- function setSidebar() {
- $('.sidebar').hide();
-
- // ...stuff...
-
- $('.sidebar').css({
- 'background-color': 'pink'
- });
- }
-
- // good
- function setSidebar() {
- var $sidebar = $('.sidebar');
- $sidebar.hide();
-
- // ...stuff...
-
- $sidebar.css({
- 'background-color': 'pink'
- });
- }
- // bad
- $('.sidebar', 'ul').hide();
-
- // bad
- $('.sidebar').find('ul').hide();
-
- // good
- $('.sidebar ul').hide();
-
- // good
- $('.sidebar > ul').hide();
-
- // good (slower)
- $sidebar.find('ul');
-
- // good (faster)
- $($sidebar[0]).find('ul');
- $(function(){
- //do your page init.
- });
- // bad
- <a id="myLink" href="#" onclick="myEventHandler();"></a>
-
- // good
- <a id="myLink" href="#"></a>
-
- $("#myLink").on("click", myEventHandler);
- // bad
- $.ajax({
- ...
- success : function(){
- },
- error : function(){
- }
- })
-
- // good
- $.ajax({.
- ..
- }).then( function( ){
- // success
- }, function( ){
- // error
- })
- var dtd = $.Deferred(); // 新建一个deferred对象
- var wait = function(dtd){
- var tasks = function(){
- alert("执行完毕!");
- dtd.resolve(); // 改变deferred对象的执行状态
- };
- setTimeout(tasks,5000);
- return dtd;
- };
尽量采用ES5方法,特别数组map、filter、forEach方法简化日常开发。在老式IE浏览器中引入ES5-shim。或者也可以考虑引入underscore、lodash常用辅助库。
- 参考Kangax的 ES5compatibility table。