【问题标题】:template engine implementation模板引擎实现
【发布时间】:2010-12-10 02:27:58
【问题描述】:

我目前正在构建这个小型模板引擎。 它需要一个包含模板的字符串参数,以及一个“标签,值”的字典来填充模板。

在引擎中,我不知道模板中的标签和不会出现的标签。

我目前正在对字典进行迭代(foreach),解析我放在字符串生成器中的字符串,并将模板中的标签替换为相应的值。

有没有更有效/方便的方法来做到这一点? 我知道这里的主要缺点是 stringbuilder 每次都完全针对每个标签进行解析,这非常糟糕......

(我也在检查,虽然没有包含在示例中,但在我的模板不再包含任何标签的过程之后。它们都以相同的方式格式化:@@tag@@)

//Dictionary<string, string> tagsValueCorrespondence;
//string template;

StringBuilder outputBuilder = new StringBuilder(template);
foreach (string tag in tagsValueCorrespondence.Keys)
{
    outputBuilder.Replace(tag, tagsValueCorrespondence[tag]);
}

template = outputBuilder.ToString();

回应:

@马克:

string template = "Some @@foobar@@ text in a @@bar@@ template";
StringDictionary data = new StringDictionary();
data.Add("foo", "value1");
data.Add("bar", "value2");
data.Add("foo2bar", "value3");

输出:“value2 模板中的一些文本”

而不是:“value2 模板中的一些 @@foobar@@ 文本”

【问题讨论】:

  • 很好...使用 Dictionary 而不是 StringDictionary,它会为丢失的键引发错误...并不棘手。

标签: c# .net template-engine


【解决方案1】:

Regex 和 MatchEvaluator 怎么样?像这样:

string template = "Some @@Foo@@ text in a @@Bar@@ template";
StringDictionary data = new StringDictionary();
data.Add("foo", "random");
data.Add("bar", "regex");
string result = Regex.Replace(template, @"@@([^@]+)@@", delegate(Match match)
{
    string key = match.Groups[1].Value;
    return data[key];
});

【讨论】:

  • 一旦模式出错(就像另一个@错位)完全没用。除非其他人有更好的解决方案,否则我会坚持使用我的替换方法...
  • 编辑:实际上,如果你有一个像@@foo2 bar@@ 这样的标签,那也没用。如果在模板中你有类似@@foo bar@@ 的东西,它会被一个空格代替。错误检测的糟糕解决方案
  • 你能在任何一点上展开吗? “foo bar”应该仍然可以正常工作......我也不明白你的“另一个@错位”点。有什么例子吗?
【解决方案2】:

这里是您可以用作起点的示例代码:

using System;
using System.Collections.Generic;
using System.Text.RegularExpressions;

class Program {
    static void Main() {
        var template = " @@3@@  @@2@@ @@__@@ @@Test ZZ@@";
        var replacement = new Dictionary<string, string> {
                {"1", "Value 1"},
                {"2", "Value 2"},
                {"Test ZZ", "Value 3"},
            };
        var r = new Regex("@@(?<name>.+?)@@");
        var result = r.Replace(template, m => {
            var key = m.Groups["name"].Value;
            string val;
            if (replacement.TryGetValue(key, out val))
                return val;
            else
                return m.Value;
        });
        Console.WriteLine(result);
    }
}

【讨论】:

    【解决方案3】:

    您可以将单声道字符串格式实现修改为接受您的字符串字典。例如 http://github.com/wallymathieu/cscommon/blob/master/library/StringUtils.cs

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-25
      • 1970-01-01
      • 2011-06-25
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-01-21
      相关资源
      最近更新 更多