`
baiyuxiong
  • 浏览: 177954 次
  • 性别: Icon_minigender_1
  • 来自: 西安
社区版块
存档分类
最新评论

论PHP框架设计模式及MVC的缺陷

    博客分类:
  • php
阅读更多
请勿转载。

目前主流的PHP框架设计模式均为MVC模式,比如yii或codeigniter,均是由控制器接收页面请求,并沟通模型与视图的交互。如果我们把网站整体看作一个矩阵,把网站接收用户请求并处理看作是网站的竖向,而把网站的每一个模块(比如文章模块,投票模块,论坛模块等)看作是网站的横向。那么我们可以画出这样的图:

               模块1  模块2 模块3
用户请求 ----------------------
                |      |      |
                |      |      |
数据处理 ----------------------
                |      |      |
                |      |      |
页面呈现 ----------------------

MVC的缺陷
MVC模式,侧重于竖向即请求、处理、呈现之间的协调,而忽略了模块之间的协调,从图里我们可以看出,当用户发起请求的时候,由哪个模块来处理用户的请求已经确定了,这就使模块之间呈现非常强的独立性,这该怎么理解呢,举个例子来说。
假设现在,你有两个模块,一个是新闻模块,一个是图片模块,新闻模块展示一些新闻文章,图片模块用来展示图片。
如果用MVC,我们这样实现:定义两个控制器news,pic,两个模型news_model,pic_model,两个视图news_view,pic_view,当有用户请求news控制器时,先调用news_model取得需要的数据,再用这些数据渲染news_view,最后呈现给用户。
有一天,你的领导忽然有了新想法,HEY,伙计,新闻模块只显示新闻太单调,让新闻模块,能显示图片模块里最热门的图片。这下不好办了,new_model里没有图片相关的模型,news_view里也没有显示图片列表的视图。你有解决办法?把显示图片列表相关的模型和视图分别复制一份到news的模型和视图?不,这么做不好,如果我现在全站都要显示热门图片列表你怎么办?还复制吗?不可以的。后期维护会累死人。
在codeigniter框架里,有更好一点儿的解决办法,就是把显示图片列表这个功能做成一个library,每需要的地方,调用library就可以,因为library有与控制器相同的沟通模型视图的功能。但这会带来一个新的问题:数据共享,如果页面分割成不同的library来实现,不同的library的数据很难共享,library之间是完全独立的。
现在来看,这一切的一切都是因为mvc模式注重竖向的沟通,而忽略了横向的沟通,完全割裂了模块之间的关系。

模块沟通
TextPattern(简称TXP)是一个小型的BLOG系统,它最大的特点是注重模块之间的沟通,完全模糊了不同模块间的界限,对与用户的一个请求,TXP完全没必要知道用户请求的是什么模块,新闻还是图片,只需要知道请求的页面要呈现些什么功能点。每一个小功能点都是完全独立的。
这是一种视图驱动的模式,接收到用户请求后,首先取到要请求的视图,视图文件再调用不同的功能点,这样就弱化了模块之间独立性。通俗点儿说:用户想看什么,你就给什么,不要管它是不是同一个模块,是不是有关系。wordpress也是基于视图驱动的模式的。


HMVC
层叠式的MVC,这是MVC模式的升级版本。首先把系统按功能点分,每个功能点的实现再采用MVC模式。HMVC同时兼顾了横向和竖向的沟通。

我所认为理想的模式
基于视图驱动的HMVC,基于视图驱动,就是以用户为基础,呈现用户想看到,以需求为驱动才是正确的。HMVC保证了代码的重用,易于维护。
视图驱动,可以借鉴WORDPRESS的实现,因为wordpress的模板开发、替换很容易;横向沟通的实现可以借鉴TXP;竖向沟通就是典型的MVC了。

一家之言,欢迎拍砖。请勿转载。
分享到:
评论
30 楼 renzhen 2011-04-22  
vb2005xu 写道
套用r大大那句话: 使用rails或者PHP类rails框架的 基本都是充血模型 想瘦都瘦不下来

使用 java ssh 基本就是 贫血模型 你想充也充不了 PHP的 怎么简单就怎么来好了 只要能 代码看的舒服 就怎么来 干嘛自己整那么多规矩

充血模型和贫血模型是相对于Model层而言的,而PHP框架里争议最大的似乎就是M层,一来无法实现rails那样强大的Model功能,即使实现了性能也是惨不忍睹。二来不符合长久以来PHP基于SQL的开发习惯,老实说,习惯这东西是十分强大的,曾经有一个外国人写了一篇blog,讲从Rails转回PHP开发他的网站,其中一个主要原因就是不习惯ActiveRecord的操作,习惯SQL语言开发。
29 楼 vb2005xu 2011-04-22  
昨天写程序遇到某些问题 想了一宿 突然想通了 之前是我太浅薄了 呵呵 收回之前所有的话 我就是个新手

thanks楼主 你的这个 视图驱动 解决了 我长期困扰的一个问题 呵呵 我要好好想想 然后改善我的 sfw ..

这个问题 我之前也遇到过 ... 在qee的里面 视图层 在一定程度上使用 控件 也解决了这个问题

不过你这种 视图驱动 开发的 建议 很好 , 我要好好想想了 谢谢了啊

28 楼 baiyuxiong 2011-01-31  
dwwind 写道
vb2005xu 写道
dwwind 写道
当前的php框架,都是喜欢大而全,而不是只提供一个基本的架子(基础)。
前些日子,接手一个项目用了ci,感觉不过如此。
我认为M层就应该是与框架无关的,但是很多php框架偏偏不!
你的struts框架的service层只能被特定的C用吗?当然不是了。

当然,写个php 框架也不是什么难事,可以自己试试,对mvc应该会有更深的了解!


一看就知道是PHP新手


:-) 不错!我写php尚不到3年。也用过一些框架。
   每个人对框架的理解可能不一样。自己用着顺手的才是最好的。
   日前也曾经写了个:http://rare.sinaapp.com.
 
   呵呵,现在php框架已经快到了一个泛滥的程度了。

嗯,也许自己写的才是最顺手的……
回头研究一个自己的。
27 楼 vb2005xu 2011-01-20  
套用r大大那句话: 使用rails或者PHP类rails框架的 基本都是充血模型 想瘦都瘦不下来

使用 java ssh 基本就是 贫血模型 你想充也充不了 PHP的 怎么简单就怎么来好了 只要能 代码看的舒服 就怎么来 干嘛自己整那么多规矩
26 楼 dwwind 2011-01-19  
vb2005xu 写道
dwwind 写道
当前的php框架,都是喜欢大而全,而不是只提供一个基本的架子(基础)。
前些日子,接手一个项目用了ci,感觉不过如此。
我认为M层就应该是与框架无关的,但是很多php框架偏偏不!
你的struts框架的service层只能被特定的C用吗?当然不是了。

当然,写个php 框架也不是什么难事,可以自己试试,对mvc应该会有更深的了解!


一看就知道是PHP新手


:-) 不错!我写php尚不到3年。也用过一些框架。
   每个人对框架的理解可能不一样。自己用着顺手的才是最好的。
   日前也曾经写了个:http://rare.sinaapp.com.
 
   呵呵,现在php框架已经快到了一个泛滥的程度了。
25 楼 hcw1314520 2011-01-19  
我们是将model层分为两层:DAO和SERVICE
控制器调用自己的SERVICE但是不同的SERVICE可以相互调用。
这样控制器就能通过SERVICE调用其他的服务了!
24 楼 vb2005xu 2011-01-18  
dwwind 写道
当前的php框架,都是喜欢大而全,而不是只提供一个基本的架子(基础)。
前些日子,接手一个项目用了ci,感觉不过如此。
我认为M层就应该是与框架无关的,但是很多php框架偏偏不!
你的struts框架的service层只能被特定的C用吗?当然不是了。

当然,写个php 框架也不是什么难事,可以自己试试,对mvc应该会有更深的了解!


一看就知道是PHP新手
23 楼 dwwind 2011-01-18  
当前的php框架,都是喜欢大而全,而不是只提供一个基本的架子(基础)。
前些日子,接手一个项目用了ci,感觉不过如此。
我认为M层就应该是与框架无关的,但是很多php框架偏偏不!
你的struts框架的service层只能被特定的C用吗?当然不是了。

当然,写个php 框架也不是什么难事,可以自己试试,对mvc应该会有更深的了解!
22 楼 baiyuxiong 2010-12-23  
dwangel 写道
baiyuxiong 写道
我知道控制器可以调用类库或者调用别的控制器,不过这也没什么优势,在视图里面没办法调用别的控制器。

看来楼主是觉得MVC在代码重用上不方便。
楼主是不是用过 asp.net开发项目,习惯了那里的页面控件里也嵌入逻辑的模式。

这个只是开发时思考习惯问题。

楼主是想从最终页面 看有几个视图,然后根据视图考虑显示一个完整页面需要执行哪些逻辑。
这个基于一个前提,这个View是跟逻辑密不可分的。

如果这样的话,codeigniter 我不熟,但刚看了文档,可以把逻辑写成在library里的一个类,由这个逻辑负责调用相应的视图。
abstract public class ViewLogic{
  protected $controller;
  public __constructor($controller) {
    $this->controller = $controller;
  }
  public function execute() {
    doTask();
    $this->controller->loadView($this->getViewName());
  }
  abstract protected function doTask();
  abstract protected function getViewName();
}
public class NewsViewLogic {

  public function getViewName() { return "NewsView"; }
  public function doTask() {
    .....
  }
}

在控制器里仅仅是调用library。
$this->load->library('NewsViewLogic', array('controller'=>$this) );
$this->newsviewlogic->execute();

你有几个页面要用NewView,就copy几个调用字段就行。
甚至可以这样:
$logics = array("NewsViewLogic", "ddddLogic");
foreach($logics as $logic) {
  $this->load->library($logic, array('controller'=>$this) );
  $logicName = strtolow($logic);
  $this->$logicName->execute();
}

做个基类,把循环部分放到公用方法也行。
每个页面的Controller也就是配配 $logics 了。
以上代码只是示意,未经测试。


嗯,这种做法不错,学习了。
我发现我写程序总是用面向过程的思想写面向对象的程序
这个思维习惯真难改。
21 楼 baiyuxiong 2010-12-23  
vb2005xu 写道
你可以看看 QEEPHP框架 或者 我写的 xser php 框架

有什么特别之处呢?
20 楼 vb2005xu 2010-12-23  
你可以看看 QEEPHP框架 或者 我写的 xser php 框架
19 楼 vb2005xu 2010-12-23  
baiyuxiong 写道
lxholding 写道
baiyuxiong 写道
smilerain 写道
lz 对 mvc的理解很清晰,不过感觉不能灵活的使用,所以才会碰到这些问题。
利用好逻辑接口,配合view部分的继承关系,view不一定是一个页面,也可以是一个区域。MVC只是一个构架概念,自己的程序能够清晰的分层利于维护就算可以了。


明白了,我的理解太局限于CI这个框架了,因为我用这个框架用的多,把这个框架的缺点理解成MVC的缺点了。

yii或codeigniter的帮助和例子里的model层都是实体model,楼主应该是被这个误导了,在控制层完全能够调用自己的类干活


我知道控制器可以调用类库或者调用别的控制器,不过这也没什么优势,在视图里面没办法调用别的控制器。



在视图里面没办法调用别的控制器 ...

对这一句话 我有点异议: 你在这里为什么要调用控制器???/ 我很不解


视图里面 我认为 他就是 输出数据的模版 , 此处调用控制器 应该就是 连接或者 ajax请求的事情了 和视图又有什么关系


18 楼 dwangel 2010-12-21  
baiyuxiong 写道
我知道控制器可以调用类库或者调用别的控制器,不过这也没什么优势,在视图里面没办法调用别的控制器。

看来楼主是觉得MVC在代码重用上不方便。
楼主是不是用过 asp.net开发项目,习惯了那里的页面控件里也嵌入逻辑的模式。

这个只是开发时思考习惯问题。

楼主是想从最终页面 看有几个视图,然后根据视图考虑显示一个完整页面需要执行哪些逻辑。
这个基于一个前提,这个View是跟逻辑密不可分的。

如果这样的话,codeigniter 我不熟,但刚看了文档,可以把逻辑写成在library里的一个类,由这个逻辑负责调用相应的视图。
abstract public class ViewLogic{
  protected $controller;
  public __constructor($controller) {
    $this->controller = $controller;
  }
  public function execute() {
    doTask();
    $this->controller->loadView($this->getViewName());
  }
  abstract protected function doTask();
  abstract protected function getViewName();
}
public class NewsViewLogic {

  public function getViewName() { return "NewsView"; }
  public function doTask() {
    .....
  }
}

在控制器里仅仅是调用library。
$this->load->library('NewsViewLogic', array('controller'=>$this) );
$this->newsviewlogic->execute();

你有几个页面要用NewView,就copy几个调用字段就行。
甚至可以这样:
$logics = array("NewsViewLogic", "ddddLogic");
foreach($logics as $logic) {
  $this->load->library($logic, array('controller'=>$this) );
  $logicName = strtolow($logic);
  $this->$logicName->execute();
}

做个基类,把循环部分放到公用方法也行。
每个页面的Controller也就是配配 $logics 了。
以上代码只是示意,未经测试。
17 楼 keete 2010-12-21  
回复是亮点。。
16 楼 zuowj 2010-12-20  
squall2825 写道
其实说句实话,很多程序员都知道MVC,但很多程序员(包括我在内)都不非常透彻的理解MVC,从JAVA提倡MVC框架开始到PHP的开发,有很多程序员都只是在开发框架的模式下进行所谓MVC的分层,个人认为只熟悉MVC框架并不等于真正了解MVC概念,好比古人习武,每招每式都已经模仿的非常淋漓尽致可却总无法成为真正的高手,原因在于自身已经被某套武功所局限,从而无法真正理解到武功的真谛,所谓宗师与凡人的区别在于宗师能在一套凡人看似非常完美的武功中看出其优劣点,并能根据其特点从而进行改进,其实程序也应该是如此,从刚开始学到现在,感觉自己越来越菜,不像以前那样直观和清晰了,也是因为框架用多了,思维被模式化了,很多东西还是需要靠自己来打破这种陈规,世上本来没有路,走的人多了自然就成了路。希望写这些东西能对大家有用。


说下我的理解:
  MVC是现在WEB系统设计的主流模式,它背后的思想是"交互界面与逻辑的分离

做到良好分离,这样就可以:

    一份逻辑代码可以支持不同的展现(不同数据项、不同展现技术、 不同展现终端)
    展现界面及交互休验的改进,不用受制于逻辑代码的开发周期
    逻辑开发者(服务端工程师)与界面交互开发者(前端工程师)能专注和发挥优势。

当然这种思想不仅在WEB开发领域才有体现,在客户端开发也有体现。

而MVC的框架主要解决的问题就是: 在开发时,提供展现与逻辑分离的组织结构;在在运行时,提供两者灵活结合的机制。


15 楼 liguomin 2010-12-17  
[quote="squall2825"]其实说句实话,很多程序员都知道MVC,但很多程序员(包括我在内)都不非常透彻的理解MVC,从JAVA提倡MVC框架开始到PHP的开发,有很多程序员都只是在开发框架的模式下进行所谓MVC的分层,个人认为只熟悉MVC框架并不等于真正了解MVC概念,好比古人习武,每招每式都已经模仿的非常淋漓尽致可却总无法成为真正的高手,原因在于自身已经被某套武功所局限,从而无法真正理解到武功的真谛,所谓宗师与凡人的区别在于宗师能在一套凡人看似非常完美的武功中看出其优劣点,并能根据其特点从而进行改进,其实程序也应该是如此,从刚开始学到现在,感觉自己越来越菜,不像以前那样直观和清晰了,也是因为框架用多了,思维被模式化了,很多东西还是需要靠自己来打破这种陈规,世上本来没有路,走的人多了自然就成了路。希望写这些东西能对大家有用。

说得很透彻,我也有这种感觉,开发的时候只是在进行着所谓的MVC分层,而至于其中的概念至今都感觉不能完全理解。
14 楼 squall2825 2010-12-16  
其实说句实话,很多程序员都知道MVC,但很多程序员(包括我在内)都不非常透彻的理解MVC,从JAVA提倡MVC框架开始到PHP的开发,有很多程序员都只是在开发框架的模式下进行所谓MVC的分层,个人认为只熟悉MVC框架并不等于真正了解MVC概念,好比古人习武,每招每式都已经模仿的非常淋漓尽致可却总无法成为真正的高手,原因在于自身已经被某套武功所局限,从而无法真正理解到武功的真谛,所谓宗师与凡人的区别在于宗师能在一套凡人看似非常完美的武功中看出其优劣点,并能根据其特点从而进行改进,其实程序也应该是如此,从刚开始学到现在,感觉自己越来越菜,不像以前那样直观和清晰了,也是因为框架用多了,思维被模式化了,很多东西还是需要靠自己来打破这种陈规,世上本来没有路,走的人多了自然就成了路。希望写这些东西能对大家有用。
13 楼 baiyuxiong 2010-12-15  
等天上掉大饼 写道

楼主的说法比较费解。

news的controller只能调用new_model?

它也可以调用pic_model啊

嗯,调用model是可以的,但是调用pic_view就不方便了吧?
12 楼 等天上掉大饼 2010-12-14  

楼主的说法比较费解。

news的controller只能调用new_model?

它也可以调用pic_model啊
11 楼 nakupanda 2010-12-11  
感觉PHP用最直观的过程式开发方式是最好的了

相关推荐

    基于MVC模式下的开发框架建设与改进.pdf

    基于被动MVC模式,PHP框架可以实现快速开发、可维护性和高重用性等优点。 知识点3:THINKPHP框架的建设和改进 THINKPHP框架是基于MVC设计模式的PHP实现,旨在提高Web应用程序的开发效率、可靠性、可扩展性和可维护...

    基于PHP的MVC开发框架zentao框架源码.zip

    zentao框架是一个基于PHP实现的MVC(Model-View-Controller)模式的开发框架,广泛应用于项目管理、任务跟踪、缺陷管理等领域。它以其高效、稳定和易用性,成为了许多开发者的首选工具。本文将深入探讨zentao框架的...

    改进HMVC设计模式应用于PHP开发的探索.pdf

    1. PHP框架:HMVC设计模式可以应用于PHP框架,例如Laravel、CodeIgniter等,提高系统性能和可维护性。 2. Web应用程序开发:HMVC设计模式可以应用于Web应用程序开发,例如电子商务平台、博客平台等,提高系统性能...

    基于PHP的MVC开发框架 zentao框架.zip

    它采用MVC(Model-View-Controller)设计模式,这种模式在Web开发中被广泛使用,能够有效地分离业务逻辑、数据模型和用户界面,从而提高代码的可维护性和可扩展性。 **MVC模式详解** 1. **Model(模型)**:模型层...

    Project, 为速度和simplicty设计的轻量级 MVC PHP框架.zip

    Project, 为速度和simplicty设计的轻量级 MVC PHP框架 PHPixie框架 网站:phpixie.comPHPixie作为微框架开始,并逐渐发展成为最流行的fullstack PHP框架之一,同时保持了它的高性能。 这是因为严格的体系结构,避免...

    PHP实例开发源码—BugTrace 缺陷跟踪开源系统 php版.zip

    2. **MVC(模型-视图-控制器)架构**:BugTrace很可能采用了MVC模式,这是Web应用开发中的常见设计模式,用于分离业务逻辑、数据处理和用户界面。 3. **数据库交互**:通过PHP连接和操作数据库,如MySQL,进行数据...

    浅谈php常用的7大框架的优缺点

    ThinkPHP是一个轻量级的PHP框架,支持多种数据库和MVC模式,它的设计宗旨是简化开发和提高效率。ThinkPHP以Java的Struts框架为原型,但又进行了优化以适应PHP环境。它的优点包括对初学者友好、文档丰富、支持众多...

    PHP实例开发源码——ZenTaoPHP php框架发布正式版.zip

    【PHP实例开发源码——ZenTaoPHP php框架发布正式版】 ZenTaoPHP是一款基于PHP语言的开源框架,主要用于企业级的项目管理、产品管理、研发管理等业务流程的构建。这个压缩包包含了ZenTaoPHP框架的源代码,为开发者...

    基于PHP的Doit轻量级PhP框架MySql专业版源码.zip

    Doit框架采用MVC(Model-View-Controller)架构模式,将业务逻辑、数据处理和用户界面分离开来,便于开发和维护。其中,模型负责与数据库交互,视图负责展示数据,控制器协调模型和视图,处理用户的请求。 2. **...

    推荐一个非常棒的Titanium MVC框架

    在探索ChariTi的过程中,读者可能会对相关的MVC框架设计模式和技术有所兴趣。MVC(Model-View-Controller)是一种软件设计模式,常用于分隔应用的数据模型、用户界面和业务逻辑。PHP、.NET和PHP的Smarty等框架都是...

    网站内容管理系统大学论文.doc

    传统网站建设模式是首先设计网站的框架结构,然后设计 HTML 页面,最后把设计好的 HTML 页面纳入网站的框架结构中。这种模式适合小型网站和内容相对固定网站,但对于信息量大、结构复杂的政府门户网站和政务平台来说...

    PHP实例开发源码——Ciuten手机版黑色风格模板(php修正版).zip

    Ciuten是一款基于PHP框架开发的轻量级网站模板,尤其适用于移动端应用。这款"PHP实例开发源码——Ciuten手机版黑色风格模板(php修正版)"是针对Ciuten框架的一个定制化设计,它提供了深色主题,提升了用户体验,尤其...

    主流PHP框架的优缺点对比分析

    1. 使用多种设计模式,架构优雅,执行效率尚可。 2. 提供全面的MVC功能,强大的路由和配置文件支持。 3. 庞大的library,支持多种缓存和数据库驱动,适用于复杂应用。 4. 国内社区成熟,文档详尽。 尽管如此,Zend ...

    基于PHP的禅道项目管理软件ZenTaoPMS开源版源码.zip

    源码中包含了控制器、模型、视图、库函数等关键组件,遵循MVC(Model-View-Controller)架构模式,使代码组织清晰,便于维护和升级。 二、ZenTaoPMS核心功能模块 1. 需求管理:ZenTaoPMS允许用户记录、跟踪项目...

    软件工程……Flutter + PHP 毕业答辩ppt

    然而,由于初始设计的不足,系统存在一些缺陷,例如功能的完善性、用户账号的安全性和权限管理等方面,这些都是未来需要改进的方向。 **5、总结与致谢** 在项目实施过程中,作者感谢导师和同学们的帮助,他们的...

    zentaoPHP框架2.3版

    在深入理解这个框架之前,我们需要先了解一下PHP框架的基本概念。 PHP框架是一种预编写代码库,它提供了规范化的编程结构,帮助开发者更快速、更高效地构建PHP应用程序。它们通常包含MVC(模型-视图-控制器)架构,...

    禅道zentaoPHP框架.7z

    理解MVC(Model-View-Controller)设计模式,将有助于你更好地理解禅道的代码结构。 2. **数据库交互**:禅道与数据库紧密交互,通常使用PDO或MySQLi进行数据操作。熟悉SQL查询语句和事务处理,对理解禅道如何存储...

    PHP网站开发方案(开发新人必读)

    - 推荐使用MVC(Model-View-Controller)模式,将业务逻辑、数据模型和用户界面分离,便于管理和扩展。 - **URL重写**: - 使用Apache的mod_rewrite模块进行URL美化,例如将`...

    Vet-Game:具有php后端的mvc网络应用程序,可通过JS在前端与php进行交互。 只能通过移动设备访问的小型项目,但无法完全响应

    MVC模式是一种常见的软件设计模式,它将应用程序的业务逻辑、用户界面和数据存储分离开来,以提高代码的可维护性和可扩展性。 在Vet-Game中,PHP作为后端服务器语言,处理用户请求,执行业务逻辑,并与数据库进行...

Global site tag (gtag.js) - Google Analytics