一直以来JavaScript对字符串的操作比较弱,特别是做.NET的人很清楚,犹如:String.Form格式化、StringBuilder大量字符串拼接每天都是离不开。故而也会在JavaScript上模拟这些。

String.Format

其实说白一点即是字符替换,这也是模板引擎最初级做法。而这里我提供一个我多年的示例:

/**
 * demo {@code 'this is the {0}'.format('end'); }
 */
String.prototype.format = function () {
    var args = arguments;
    return this.replace(/\{(\d+)\}/g, function (m, i) {
        return args[i];
    });
};

非常简单,但很耐用且是不是比.NET更优雅呢?当然这也只能{0}…{∞}来替换字符串,并无任何实际的运算能力或格式化能力。

且因为我们还会遇到另一种问题,就是当{}过多的时候,维护变得很困难。所以我们需要另一个高级点的办法。

String.Form变体

先看示例:

String.prototype.format = function () {
    var args = arguments;
    if (args.length == 1 && typeof(args[0]) === 'object') {
        return this.replace(/\{([\w\d]+)\}/g, function (m, i) {
            return args[0][i];
        });
    } else {
        return this.replace(/\{(\d+)\}/g, function (m, i) {
            return args[i];
        });
    }
};

相比较只是将{0}变成{Variable}一个比较有意义的变量名。这两种调用方法如下:

alert('ID:{0},UserName:{1}'.format('1', 'cipchk'));
alert('ID:{ID},UserName:{UserName}'.format({ ID: 1, UserName: 'cipchk' }));

以上倒是可以非常简单的完成字符串替换工作,接下来我们还需要一个很重要的东西,字符串拼接:

StringBuilder

.net为何会提出StringBuilder就是由于字符串+=会倒置内存空间的重新定义。Javascript的String跟.NET是相同问题,所以经常会听到在JavaScript里面使用Array和Array.Join来代替传统的+=,毋庸置疑网上有非常多评测来验证这个问题。

其实不然,+=速度慢那只是针对于传统浏览器比如:IE8以前、FF2.x以前。而现代浏览器+=比Array.push快,特别是V8下速度快4.7倍。所以结合两种方式才是最合理的。

看一下我的StringBuilder版本:

function StringBuilder() {
    this.isNewEngine = ''.trim;
    this.strings = this.isNewEngine ? '' : [];
}
StringBuilder.prototype.append = function (a) {
    this.isNewEngine ? this.strings += a : this.strings.push(a);
};
StringBuilder.prototype.toString = function () {
    return this.isNewEngine ? this.strings : this.strings.join('');
};
StringBuilder.prototype.clear = function () {
    this.isNewEngine ? this.strings = '' : this.strings.length = 0;
};
var html = new StringBuilder();
html.append('1');
html.append('2');
document.write(html.toString());

为何我要先介绍字符串替换和拼接,因为目前任何一种模板引擎都离不开这2个。

而对于模板引擎的定义是:为了使用户界面与业务数据(内容)分离。而从这个定义上出发,我们可以适当的缩小运用于JavaScript范围的说法,比如说成:将HTML和数据模型的分离。

且这种分离不在是简单的字符串拼接,首先必须满足:效率、灵活、运算能力、丰富功能、缓存、插件、开源等等。好吧,我骗你,这有些要求过高;因为我们只需要一个很简单的模板引擎,因此重点是在:效率、灵活上。

artTemplate

这是我见过最小、高性能模板引擎。请看这有一篇作者很详细介绍。其中重点是:预编译和字符串拼接效率极限;包括自带错误调试。

doT

也是一个短小的家伙,相比较artTemplate灵活性更高,同时支持Node.js。

哎,我又不想写示例了,就这样子吧。