ctemplate模板

ctemplate解决的主要问题是将文字表达和逻辑分离开来:文字模板解决如何用合适的文字和形式来表示问题,而逻辑问题则由文字模板的调用者在源代码中完成。

ctemplate大体上分为两个部分,一部分是模板,另一部分是数据字典。模板定义了界面展现的形式(V),数据字典就是填充模板的数据(M),你自己写业务逻辑去控制界面展现(C),典型的MVC模型。

2、ctemplate模板中有四中标记,对应的数据字典也有不同的处理方式:

变量,{{变量名}},用两个大括号包含的就是变量名,在c++代码中,可以对变量赋值,任何类型的值都可以(如字符,整数,日期等)。

片断,{{#片断名}},片断在数据字典中表现为一个子字典,字典是可以分级的,根字典下面有多级子字典。片断可以处理条件判断和循环

包含,{{>模板名}}包含指的是一个模板可以包含其他模板,对应的也是一个字字典。

注释,{{!注释名}},包含注释。

3、示例程序

模板

Hello{{NAME}},
You have just won ${{VALUE}}!
{{#IN_CA}}
Well, ${{TAXED_VALUE}}, after taxes.
{{/IN_CA}}

字典逻辑

复制代码
#include<stdlib.h>
#include<string>
#include<iostream>
#include<ctemplate/template.h>
         
int main(int argc,char** argv)
{        
    ctemplate::TemplateDictionary dict("example");
    dict.SetValue("NAME","John Smith");
    int winnings = rand()%100000;
    dict.SetIntValue("VALUE", winnings);
    dict.SetFormattedValue("TAXED_VALUE","%.2f", winnings *0.83);
    // For now, assume everyone lives in CA.
    // (Try running the program with a 0 here instead!)
if(1) 
    {
        dict.ShowSection("IN_CA");
    }
    std::string output;
    ctemplate::ExpandTemplate("example.tpl", ctemplate::DO_NOT_STRIP, &dict, &output);
    std::cout << output;
    return0;
}

运行结果

HelloJohn Smith,
You have just won $89383!

Well, $74187.89, after taxes.

内部代码:
mrf::module_status_t TemplateExpandMod::run()
{

    // access check
    if (!access()) {
        return mrf::MOD_SUCCESS;
    }

    // get template name and path
    string template_name =
            LuStyleContext::current()->get_common_style_info()->show_tpl;
    //新图片排行榜实验用新模板
    //TODO: 临时用的,全流量需删除(原因新模板避免ctr冷启动问题,日志记录需要用老模板名)
    ExperimentContext* p_exp_context = ExperimentContext::current();
    const experiment::ExperimentState* _p_exp_state = p_exp_context->get_state();
    bool enable_rank_image_new_template_replace = _p_exp_state->GetFlagValues()->
        GetBoolValue(EXP_BOOL_FLAG_linkunit_rank_image_new_template_replace, false);
    if (enable_rank_image_new_template_replace){
        if (template_name.compare(TEMPLATE_NAME_RANK_IMAGE_OLD)==0){
            template_name = TEMPLATE_NAME_RANK_IMAGE_NEW;
        }
    }

    const TemplateConfiguration *template_conf =
            _template_manager->template_conf(template_name);
    if (template_conf == NULL) {
        LU_UI_WARNING("Template name do not exist. template_name=%s",
                template_name.c_str());
        return mrf::MOD_ERROR;
    }
    const string &template_path = template_conf->path;
    ctemplate::TemplateDictionary _dict(template_conf->name);
    // 将include的模板添加到dict中
    if (!_template_manager->fill_include_tpl_dict(&_dict)) {
        LU_UI_WARNING("Include Template build dict error.");
        return mrf::MOD_ERROR;
    }
    for (vector<StyleHandler*>::iterator it = _vec_style_handler.begin();
            it !=  _vec_style_handler.end(); ++it) {
        // modify template variables according to style needs
        if ((*it)->need_modify_template_dict()) {
            (*it)->build_template_dict(_dict);
        }
    }
    if (!ctemplate::ExpandTemplate(template_path, ctemplate::DO_NOT_STRIP,
            &_dict, &_html_snippet)) {
        LU_UI_WARNING("Failed to expand template. template_path=%s",
                template_path.c_str());
        _html_snippet.clear();
        return mrf::MOD_ERROR;
    }
    return mrf::MOD_SUCCESS;
}

你可能感兴趣的:(ctemplate模板)