我用的“模板”

原创 2005年05月29日 22:21:00

PHP里面有一个很流行的词:“模板”,所谓“模板”,是一种在Web开发中将html文件和脚本分离的一种做法,试图更清楚的划分程序员和美工的界限,等等功能。

我一直很郁闷的就是,写程序的时候必须在模板和PHP之间来回奔波,每用一种模板,都要适应它们的语法,抱怨它们的不足。

至于模板的好处,我就不说了,网上多的是。

为什么不用传统的html和php混合编写的方式?各有各的看法。
如果用模板,至少有两个缺点:

1、速度
不管哪一种模板,都要将模板语言转换成PHP语句,即使是号称有“编译”功能的Smarty、smarttemplate等等。尤其是Smarty,Smarty过于庞大和复杂,即使经过编译,php程序每次还是得初始化Smarty类、经过一系列判断……
如果你去看看Smarty缓存文件,或许你会觉得,里面的代码象你刚学php的时候写的……

2、功能
在用模板写程序的时候,“多种循环”和“文件嵌套”经常会将人折磨的很郁闷,反正我在刚开始用这些模板的时候就是。
如果直接用混合PHP和html的方式,这种问题马上就迎刃而解了。


最近做的一个项目里面,一直被Smarty的庞大和效率所困扰,最终决定放弃这个庞然大物,选择了最古老的PHP与HTML代码混合的方式。但是姑且还是将其称为“模板”吧。

用Smarty的时候,我是自己写了一个类,按照phplib的方法名重写封装了一下Smarty。决定放弃Smarty以后,模板文件肯定要全部重写,但是为了尽量减少程序的修改,我将这个类全部重新改写了,去处了所有与Smarty相关的代码,取而代之的是下面这个简单的类:

<?php


class ezj_template
{
/**
* @access public
* @var string
*/
var $t_dir = '';
var $skin   = '';
var $common  = '';
var $template_cfg = array();
var $main  = '';
var $vars   = array();

function ezj_template()
{
global $ezj;

$this->t_dir = ROOT_PATH . $ezj->cache['template']['tpl_path'] . '/';

@include( $this->t_dir . '_config.php' );
$this->template_cfg = $_template_config;
}//-- end of constructor

/*
* 将模板内容输出到浏览器
@param string $cache_id
@param string $compile_id
@access public
@return void
*/
 function output($cache_id = null, $compile_id = null)
 {
global $ezj , $db;

require_once( VIEWS . 'template/class.template_common.php' );
$this->common = new template_common(&$this);
$this->common->run();

@header("HTTP/1.0 200 OK");
@header("HTTP/1.1 200 OK");
@header("Content-type: text/html;charset=utf-8");

if ($ezj->vars['header_no_cache'])
{
 @header("Cache-Control: no-cache, must-revalidate, max-age=0");
 @header("Expires: Mon, 26 Jul 1997 05:00:00 GMT");
 @header("Pragma: no-cache");
}

if ( $ezj->vars['gunzip_enabled']==1 )
{
    $buffer = @ob_get_contents();
    @ob_end_clean();
    @ob_start('ob_gzhandler');
    print $buffer;
}

extract($this->vars);
$t = &$this->t_dir;

@include_once( $t . $this->main );

if ( defined('WITHOUT_SHUTDOWN') )
{
 $ezj->_destruct();
}
 }//-- end of method `output`

function set_var($tpl_var, $value = null)
{
$this->assign($tpl_var , $value);
}

function set_file($file)
{
$this->main = $file;
}

function assign($var , $value=null)
{
if ( is_array($var) )
{
 foreach($var as $k=>$v)
 {
 $this->vars[$k] = $v;
 }
}else
{
 $this->vars[$var] = $value;
}
}
}//-- end of class `ezj_template`
?>

 

这个类里面比较关键的$main , $vars , function output(),第一个记录了将要输出的模板(其实是一个php文件),第二个以数组方式保存所谓的“模板变量”,第三个是将模板内容输出到浏览器。

在我的思路里面,所谓的“模板”不再是单纯的HTML和模板语言结合的文件,而是一个传统的PHP与HTML混合的文件,在模板类向浏览器输出内容的时候,把这个“模板”include进来就可以了,下面就是一个我项目里的“模板”文件:

<?php include($t.'include/header.php');?>
<?php if ( $_popup ) { ?>
<?=$_pop_window?>
<?php } ?>
<table width="780" border="0" align="center" cellpadding="0" cellspacing="0">
<tbody>
<tr>
 <td width="479" height="34" background="<?=$_tpl_path?>images/index_05.gif">
<?php if ( $_tpl_cfg_show_search ) { ?>
<?php include($t.'include/search.php');?>
<?php } ?>

 </td>
 <td width="301" background="<?=$_tpl_path?>images/index_05.gif"><IMG SRC="<?=$_tpl_path?>images/index_09.gif" WIDTH=301 HEIGHT=34 ALT=""></td>
</tr>
</tbody>
</table>
<table width="780" border="0" align="center" cellpadding="0" cellspacing="0">
</tbody>
<tr>
 <td width="213" height="404" valign="top" background="<?=$_tpl_path?>images/index_20.gif">
  <table width="100%" border="0" cellspacing="0" cellpadding="0">
   <tr>
    <td><IMG SRC="<?=$_tpl_path?>images/index_13.gif" WIDTH=237 HEIGHT=23 ALT=""></td>
   </tr>
  </table>

<?php if ( $_tpl_cfg_show_vote ) { ?>
  <table width="237" border="0" cellspacing="0" cellpadding="0">
   <tr>
    <td><table width="100%" border="0" cellpadding="0" cellspacing="0" class="black-12-20">
      <tr>
       <td width="16%"><img src="<?=$_tpl_path?>images/index_15.gif" width=37 height=33 alt=""></td>
       <td width="80%" background="<?=$_tpl_path?>images/index_16.gif"><strong><?=$_vote_module_disp_name?></strong></td>
       <td width="4%"><IMG SRC="<?=$_tpl_path?>images/index_18.gif" WIDTH=29 HEIGHT=33 ALT=""></td>
      </tr>
     </table></td>
   </tr>
   <tr>
    <td>
 <table width="100%" border="0" align="center" cellpadding="0" cellspacing="0">
      <tr>
       <td height="9"><img src="<?=$_tpl_path?>images/spacer.gif" width="1" height="1"></td>
      </tr>
     </table>
 <?php include($t.$_vote_module_file);?>
 </td>
   </tr>
  </table>
<?php } ?>

<?php if ( $_tpl_cfg_show_link ) { ?>
  <table width="237" border="0" cellspacing="0" cellpadding="0">
   <tr>
    <td>
 <table width="100%" border="0" cellpadding="0" cellspacing="0" class="black-12-20">
      <tr>
       <td width="16%"><img src="<?=$_tpl_path?>images/index_15.gif" width=37 height=33 alt=""></td>
       <td width="80%" background="<?=$_tpl_path?>images/index_16.gif"><strong><?=$_link_module_disp_name?></strong></td>
       <td width="4%"><IMG SRC="<?=$_tpl_path?>images/index_18.gif" WIDTH=29 HEIGHT=33 ALT=""></td>
      </tr>
     </table>
 </td>
   </tr>
   <tr>
    <td ><?php include($t.$_link_module_file);?></td>
   </tr>

  </table>
  <table width="33%" border="0" align="center" cellpadding="0" cellspacing="0">
   <tr>
    <td height="66">
 <?php if ( $_tpl_cfg_enable_service_module ) { ?>
<div align="center"><a href="javascript:" onClick="MM_openBrWindow('<?=$_common_files?>service/fuwutai.php','','width=531,height=373')"><img src="<?=$_tpl_path?>images/service.gif" width="177" height="49" border='0'></a></div>
<?php } ?>
</td>
   </tr>
  </table>
 <?php } ?>
 </td>
 <td width="567" valign="top">
<table width="100%" border="0" cellspacing="0" cellpadding="0">
   <tr>
    <td><IMG SRC="<?=$_tpl_path?>images/index_14.gif" WIDTH=543 HEIGHT=23 ALT=""></td>
   </tr>
  </table>

<?php if ( $_tpl_cfg_show_news ) { ?>
  <table width="95%" border="0" align="center" cellpadding="0" cellspacing="0">
   <tr>
    <td colspan="2">
 <table width="100%" border="0" align="center" cellpadding="0" cellspacing="0" class="black-12-20">
      <tr>
       <td width="2%"><img src="<?=$_tpl_path?>images/index_15.gif" width=37 height=33 alt=""></td>
       <td width="93%" background="<?=$_tpl_path?>images/index_16.gif"><strong><?=$_news_module_disp_name?></strong></td>
       <td width="5%"><IMG SRC="<?=$_tpl_path?>images/index_18.gif" WIDTH=29 HEIGHT=33 ALT=""></td>
      </tr>
     </table>
 </td>
   </tr>
<tr>
 <td colspan='2' align='center'>
 <?php include($t.$_news_module_file);?>
 </td>
</tr>

  </table>

 <?php } ?>

 <?php if ( $_tpl_cfg_show_prod ) { ?>
  <table width="95%" border="0" align="center" cellpadding="0" cellspacing="0">
   <tr>
    <td colspan="2"><table width="100%" border="0" align="center" cellpadding="0" cellspacing="0" class="black-12-20">
      <tr>
       <td width="2%"><img src="<?=$_tpl_path?>images/index_15.gif" width=37 height=33 alt=""></td>
       <td width="93%" background="<?=$_tpl_path?>images/index_16.gif"><strong><?=$_prod_module_disp_name?></strong></td>
       <td width="5%"><IMG SRC="<?=$_tpl_path?>images/index_18.gif" WIDTH=29 HEIGHT=33 ALT=""></td>
      </tr>
     </table></td>
   </tr>
   <tr>
    <td width="100%" height="121" valign="top" colspan='2'>
 <?php include($t.$_prod_module_file);?>
    </td>
     </table>

 <?php } ?>

 </td>
   </tr>
  </table>
 </td>
</tr>
</tbody>
</table>
<?php include($t.'include/foot.php');?>
</body>
</html>

 

我从这样的修改中获得了下列好处:
1、效率
根据我的调试,在用Smarty之前,项目首页在我的本本上基本上要消耗0.1x~0.2x秒之间,放弃Smarty以后,基本稳定在0.07x以下

2、更加精简的PHP文件

备注:Smarty是一个好东西,但是并不是任何时候都适合用Smarty来开发项目^^


设计模式讲解与代码实践(二十三)——模板方法

本文讲解了模板方法(Template Method)设计模式的使用目的、基本形态及各参与者,并结合示例代码,讲解了该设计模式在具体业务场景下的使用。...

MyBatis动态SQL之增、删、改、查操作模板

MyBatis动态SQL之增、删、改、查操作 MyBatis动态SQL之增删改查操作 概述MyBatis动态SQL支持 动态SQL之查询动态SQL之插入动态SQL之删除动态SQ...

IntelliJ IDEA 学习笔记 - 文件代码模板的使用

本文简单介绍IntelliJ IDEA中文件代码模板的使用

C++ 模板的显示具体化

C++ 没有办法限制类型参数的范围,我们可以使用任意一种类型来实例化模板。但是模板中的语句(函数体或者类体)不一定就能适应所有的类型,可能会有个别的类型没有意义,或者会导致语法错误。 ...

带模板的基于 SBT 的名次树

仅有参考代码

bzoj 3224 Tyvj 1728 普通平衡树 (替罪羊树模板)

想吃什么Sol 正常的二叉搜索树+暴力重构 lc,rc分别表示i的左右子树 对以i为根的子树重构当且仅当siz[lc]>siz[p]∗alphasiz[lc]>siz[p]*alpha 或者si...
  • veoery
  • veoery
  • 2017年12月08日 00:43
  • 3

设计模式的艺术之道--模板方法模式

设计模式的艺术之道–模板方法模式声明:本系列为刘伟老师博客内容总结(http://blog.csdn.net/lovelion),博客中有完整的设计模式的相关博文,以及作者的出版书籍推荐本系列内容思路...

模板方法模式深度解析(一)

1. 模板方法模式概述        在现实生活中,很多事情都包含几个实现步骤,例如请客吃饭,无论吃什么,一般都包含点单、吃东西、买单等几个步骤,通常情况下这几个步骤的次序是:点单 --> 吃东...
  • csdn_ds
  • csdn_ds
  • 2017年12月09日 13:37
  • 11

洛谷P3384 【模板】树链剖分

树链剖分

Flask(Jinja2) 服务端模板注入漏洞

其实我根本没用过flask模板,但是最近在学习python,研究下划线,莫名其妙地就学习到这里了。首先搭建一个flask环境。在github上下一个docker https://github.co...
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:我用的“模板”
举报原因:
原因补充:

(最多只允许输入30个字)