JavaScript模板引擎-将左手三进制(不带赋值)转换为条件语句



我发现了由Krasimir构建的完美JavaScript模板引擎,这正是我所需要的
模板引擎工作得很好,但我自然忍不住想对它进行一些修改,甚至可能添加一些功能
不幸的是,我在理解某些代码时遇到了问题

这是代码:

var TemplateEngine = function(html, options) {
  var re = /<%([^%>]+)?%>/g,
    reExp = /(^( )?(if|for|else|switch|case|break|{|}))(.*)?/g,
    code = 'var r=[];n',
    cursor = 0,
    match;
  var add = function(line, js) {
    /* --begin problem  */
    js ? (code += line.match(reExp) ? line + 'n' : 'r.push(' + line + ');n') : (code += line != '' ? 'r.push("' + line.replace(/"/g, '\"') + '");n' : '');
    /* --end problem    */
    return add;
  };
  while (match = re.exec(html)) {
    add(html.slice(cursor, match.index))(match[1], true);
    cursor = match.index + match[0].length;
  }
  add(html.substr(cursor, html.length - cursor));
  code += 'return r.join("");';
  return new Function(code.replace(/[rtn]/g, '')).apply(options);
};

这是我不明白的一句话:

js ? (code += line.match(reExp) ? line + 'n' : 'r.push(' + line + ');n') : (code += line != '' ? 'r.push("' + line.replace(/"/g, '\"') + '");n' : '');

我对JavaScript并不陌生,但这是一些看起来很奇怪的代码,据我所知,它是一个没有左手赋值的三元运算符(如果我错了,请纠正我)

因此,为了更好地理解作者在做什么,我尝试将三元运算符转换为条件语句。

这就是我目前所拥有的:

if(js) {
  if(code += line.match(reExp)) {
    line += 'n';
  } else {
    line += 'r.push(' + line + ');n';
  }
} else {
  if(code += line !== '') {
    line += 'r.push("' + line.replace(/"/g, '\"') + '");n';
  } else {
    line += "";
  }
}

此操作失败,并引发错误"Uncaught SyntaxError:Unexpected token if"

有人能帮我把这段代码转换成条件语句吗?甚至可以解释一下代码的作用吗?

同样出于好奇,有人能告诉我IE8是否支持这个代码吗
注意:我不介意IE8的支持,我只是想知道这个模板引擎是否支持IE8。

您可以在Krasimir网站或Krasimir的Github 上找到模板引擎

您不应该将代码附加到必须附加到代码的行,请尝试以下操作:

if (js && type(js) !== "undefined") {
  if (line.match(reExp)) {
    code += line;
  } else {
    code += "r.push(" + line + ");";
  }
} else if (line !== "") {
  code = code + "r.push("" + line.replace(/"/g, '\"') + "");";
}

三元运算符?:在JavaScript中的工作方式与在C中一样。在这种情况下,我们可以将表达式格式化为

js? (code += (line.match(reExp)? line + 'n' : 'r.push(' + line + ');n')
  : (code += line != '' ? 'r.push("' + line.replace(/"/g, '\"') + '");n' : '');

它看起来就像一个if-else块。根据js的值,整个表达式的计算结果为两个复合赋值表达式之一。这个表达式的值被忽略了,但我们仍然可以从中得到副作用。作者只是选择写这个而不是if (js) { code += ...; } else { code += ...; }

我知道这个问题没有得到太多关注,但我想我无论如何都会发布这个答案,希望它能帮助面临这个问题的人
经过一些努力和JSHint的帮助,我已经找到了问题的解决方案
我将当前编译的行附加到"line"变量,而不是"code"变量
这导致"line"变量包含模板的最后一行和编译代码的其余部分,这意味着"code"变量没有代码:D,因此等效于null

这是我发现自己做错了什么之前的代码:

var add = function(line, js) {
  if(js) {
    if(code += line.match(reExp)) {
      line += 'n';
    } else {
      line += 'r.push(' + line + ');n';
    }
  } else {
    if(code += line !== '') {
      line += 'r.push("' + line.replace(/"/g, '\"') + '");n';
    } else {
      line += "";
    }
  }
};

在这里和那里用"代码"变量替换"行"变量并在这里进行了几次优化之后,最终的工作答案是:

var add = function(line, js) {
  if(js && typeof js !== "undefined") {
    if(line.match(reExp)) {
      code += line;
    } else {
      code += "r.push(" + line + ");";
    }
  } else if(line !== "") {
    code += "r.push("" + line.replace(/"/g, '\"') + "");";
  }
};

最新更新