URL_PATHINFO_DEPR, depr表示 网页路径"分隔符",用"-", 有利于seo,注意是从 sername/index.php(开始的)/home-user-login-var-value开始的,pathinfo也支持普通的参数传值(仅仅支持参数...). 在thinkphp中,有两个地方使用depr,另一个就是tpl的文件目录组织分隔符: 'TMPL_FILE_DEPR'=>'-'
URL_PATHINFO: 意思是路径信息,意思是 网页的url地址就表明了 网页的模块/控制器/操作等信息, 即path indicates info of the page.
'TAGLIB_BEGIN' => '<' 如果修改为[, 则扩展标签(也叫xml标签)的调用就是 [volist....]... [/volist], xml标签定界符 不能跟基本标签符号如{,相冲突...否则会引起解析错误.
如何生成tp3.2.3的多个模块?
- 可以用手动创建类似Home模块的Admin模块目录
- 用
define('BIND_MODULE' => 'Admin');
将index.php入口文件绑定到Admin模块,由于Admin模块不存在,所以第一次访问localhost时会自动创建 Admin模块的目录. - 以后要注释掉 BIND_MODULE 模块, 恢复默认的入口为Home模块..., 以后使用Admin模块就如同Home模块一样的方法使用了...
标签库的配置,TAGLIB_PRE_LOAD => "cx,custom"
和TAGLIB_BUILT_IN=>"cx,custom"
是两个不同的配置,前者主要是 用于外在的 自定义的 自己创建的标签库在tp启动时就载入,适用于外在标签在多个模板大量使用的场合,不必在 模板页面再用<taglib name="custom"> 注意,所有的标签都是小写的
载入;后者是指在使用标签时不必在前面加上标签库名称,如<custom:great name="uid" value="1">...</custom:great>, 如果定义了custom为内置标签,则直接写<great name="uid" value="1">....</great>
在tp中,在模板html文件中,凡是可以使用普通变量如 {$name} 的地方,都可以使用系统变量,{$_Get["name"]},{$Think.config.name},而且可以使用函数...
在xml标签中,注意区分 "变量" 和 "变量名称"的区别, 变量是要加$,而变量名称 则不加$. 通常像 <volist name="user" id="vo">....</volist>
中的name属性使用的是变量名称, 在value属性中要使用变量,则要加上$. 同时在标签外面的,纯粹的普通变量的输出要加$: {$name}
volist和foreach?
volist 中的vo可以认为是, vector output,(数组/矢量输出) 也可以认为是数组/矢量 对象vector object. volist就是矢量对象列表. volist主要是用于数据表查询结果或二维数组的输出, foreach主要用于对象或数组的输出. volist的属性主要有name, id, offset-length(用于部分输出),mod. 而foreach的属性有name,item ,key
volist的mod?
它是一个属性,也可以认为是一个赋值, <volist ... mod="2,5,x"> 等价于 <volist name="result" id="vo" key="i"> ...<assign name="mod" value="$i mod x"> mod="2" 实际上是 mod="key % 2"
但是你不能单独的去赋值mod, 要在volist循环中赋值,所以就直接 写在volist的属性中了, 通常要把olist mod="x" 和 eq name="mod" value="1""2""..." 结合起来使用.
通常写volist的 id就直接写成 vo, 这是约定 习惯:<volist name="result" id="vo">
对tp标签库的理解,不管有多复杂, 就是把它理解为 解释扩展的 <?php .... ?>
代码. 解析后的代码实际上是一个 php和html混合的页面. 扩展的xml标签是为了在 html中不只是 "肯定的,不变的"输出 模板变量, 而且还要实现如同 php/js等代码程序中的 条件语句if, switch, 和循环语句for foreach volist等, 用"纯粹的html标签式的页面" 来代替html和php的混合页面.
compare标签和eq等标签, range标签和between等标签?
eq, gt等比较标签,是compare标签的别名, 都有name, value属性,只是compare标签多了一个type属性来指明是eq, gt,lt(less than)等.注意, 比较标签和范围标签其实都是 条件标签 if,都要解析为if条件语句... 只是比if标签更简洁.
tp中的模板标签和 html标签 的用法不同!! html标签是不允许 在标签名 中 嵌套的, 如:<p <span> span text</span>> para text </p>
的写法是错误的, 但是tp中的 模板标签, 由于要解析成php代码, 所以 在 一个标签的名称中, 在标签的属性中, 是可以"嵌套" 其他tp标签的, 如: <tr <eq id="uid" value="1">style="background-color:#eee"</eq>> ....<td>....</td> </tr>
php中的empty和isset的区别?
empty是判断是否为空,而isset是判断该变量或数组的元素是否设置,
通常, 如果 $var=0,false,null,'', 则empty($var)====true
对于isseet来说, 跟上面的一样,当 $var=0,false,''时, 则isset($var)=true,只有一个, 当$var=null的时候, isset($var)===false.
数组和对象的写法区别?数组的写法是 $arr['key'], 对象的写法则是用冒号表示: $obj:member, 而要自动识别时,则用点号 $some.member, 但是,在能够确定时,最好是写明确些
import和vendor函数的区别?
它们其实都是在内部调用的 require, 只是开始的部分做了些调整, 如果是ThinkPHP下的 Library/Think(或者core)下的类都是可以直接使用 , 如果是 Library下的Org,则用import来引入类, 如果是Vendor下的类,要引入, 则用vendor函数, 他们的区别, 只是针对的路径不同.
通常自己写的类/类库,或引入的 按tp的规则 写的其他人,开发团队写的 类库, 都放在 Org目录下, 使用import来引入; 如同在C++中一样,如果是没有按tp默认约定规则来写的\放在vendor目录下的类库, 就用vendor方法来引用, 只是import和vendor的参数的默认值不同.
tp的show,display,直接echo的区别?
echo就是直接输出内容,跟tp函数没有毛关系; display和show都是View类的成员函数, 都有三个参数('tmpl对应文件','charset,doc-type),但是display要求要有对应的tmpl文件, 而show则不一定要有对应的tmpl文件, 可以直接输出html内容...
php是解释型语言, 解释一句,再执行一句,所以前面有输出,当后面有错误时,会终止运行,只是并不是直接翻译成机器码: 先将php源代码转换为opcode(如同在汇编语言中,nop是助记符, 0x90是opcode...,即计算机的中间代码),然后由php的解释引擎(php虚拟机,pvm): zend 来运行,也可以用jit技术在虚拟机上运行时编译成机器码来提高运行速度. 现在的语言,编译和解释的分别都不是那么严密了.
使用高版本的php, 功能更强大,
像__ROOT__, PUBLIC,...等都是在模板文件中,使用的, 不是在 控制器/方法|操作,中使用的, 而且是在 配置文件中的 TMPL_PARSE_STR' => array( '__PUBLIC' => ...,.....)
中定义的, 因为在默认情况下, ROOT, __PUBLIC__这些都是要被解析\替换的,所以如果确实要输出 像ROOT, __PUBLIC__这样的字符串, 则可以使用 另外的模板字符串定义 TMPL_PARSE_STR' => array( '--PUBLIC--' => '__PUBLIC__' ...,.....)
ThinkPHP的内置标签库在哪里?
内置标签库的基类是: \ThinkPHP\Library\Think\Template\TagLib.class.php, 内置的标签库cx(标签库的名称都用小写)在\ThinkPHP\Library\Think\Template\TagLib\Cx.class.php文件中.
C/C++为什么要使用指针分配对象?
Object myobj这种方式是自动分配,作用域在函数范围内,当1. (使用指针会带来两个作用,也可以说是 两个问题,看你是需要还是避免) 要延长对象的作用域和生命期, 并且要使用的是对象指向内存的本身, 而不是对象的拷贝; 2.要指向的对象本身分配的内存比较大,如果用对象的拷贝,耗费的内存比较大,可能溢出栈 时, 使用只能指针比较好, 具有RAII std::unique_ptr, std::shared_ptr, ...(这个比较少见)
因此, 如果只是要在文件作用域内,进行 函数传参时, 使用 对象的本身,但是不需要延长生命期的时候, 就不要使用 指针, 而是使用 引用 就可以了, 这样就避免了指针的 "延长生命期"的 "副作用" . 当然还有其他需要使用指针的时候, 如多态的实现...
php中的对象, 因为都是用new来实例化的,所以都用 ->(叫对象运算符)来引用(对象的成员变量,也叫属性,字段,features), 静态用::(叫双冒号)来引用. 但是在tp的模板中使用冒号:来引用对象的成员.
后台模块 Admin 的配置参考 http://www.mamicode.com/info-detail-1181250.html
页面trace是怎样做到的过程?
定义'SHOW_PAGE_TRACE' => true,
模型类的定义问题? - 注意tp中的路径问题, 很多路径,都是 规定, 系统约定, 系统中的解析器, 会从约定的路径开始解析...
自定义模型类, 要使用"相对路径", 不用加 , 从模块开始写起:<?php namespace Home\Model; use Think\Model; class FooModel extends Model{...} ?>
而实例化自定义的模型类时, 要使用 "形式上的 绝对路径" ,从 写起:$User = new \Home\Model\FooModel();
数据库的连接查询?
目的是为了从多个表中获取字段的信息,条件是两个表 中要有相关联的字段,字段的数据类型要相同,名称不一定相同.
内连接的方式:
mysql默认的方式就是内连接,即join=inner join, 使用join要结合on使用, on是指明两个表用 哪两个字段 进行连接查询; 不同于where,where是过滤 连接查询结果 后的条件. 如果不使用join, 则使用 "隐含"内连接, 连接字段就放在where中(这时候的where就相当于on...).
mysql支持 中文下标key吗? 是的:如{$vo["学号"]}
thinkphp中为什么要使用query函数?
如果是针对 单一的一个表, 的insert delete update select等操作, 就使用tp的 链接操作函数,
但是如果要操作的情况比这个复杂, 如查询的表不是一个表,操作的是多个表, 或者是不是普通的Crud,而是联合查询,那么这个时候,就不能使用链式函数, 而要使用原生的sql语句,调用query函数了.如下:
$Sql= M();$query = "select foo.uid as '学号',foo.name,score.score from foo,score where foo.uid=score.sno and foo.name='john'";$query = "select foo.uid, foo.name, score.score from foo join score on foo.uid=score.sno where foo.name='john'";$result = $Sql->query($query);dump($result);
tp支持标准的orm和AR及原生的sql操作,为什么要写这么多"眼花缭乱"的方法呢? 是因为在实际中的需求就有这么多,有的是功能的需求,有的是效率性能上的需求.
tp的"增删改查"就是add, delete, save, select,跟原生的sql操作名称不一样,一是,不能去"占用""覆盖"原生的操作名称,二是正好与日常的"叫法"相一致.
$User=M('user')就是数据表对应的类的实例化对象,从oop的观点来看,它本身就应该,也可以用来操作数据表的curd操作.
通常只有在add和save方法中,才需要创建数据对象DO, 调用`$User->create(); create($data);create($another_do); 也可以使用
data($data)方法`, 只有创建了do(在内存中),才能用add/save方法写入数据库
create和data创建do的区别?
create做的工作很多,包括了获取ds,ds合法性检验,检查字段映射, 字段验证,自动完成,令牌检查等. 而data则没有那么多的附加工作和
功能,要自己去完成.
select子查询的作用主要有四点?
1.用作生成子表(返回多条数据), 如 join (select....)as another_table...
2.用作生成一个静态数值, 在算术表达式中使用
3.用作生成 "一个" "相关子查询""动态子查询" 数值, 用在 条件等 算数表达式中
4.用作生成数值范围,用在exist,not exist语句中.
rand和mt_rand?
mt_rand比rand的速度更快(快4倍?),生成的随机数更好? 在windows下, RAND_MAX的值是32768, 并且rand和mt_rand都不需要播种.
php中生成m,n之间的随机数?
php生成随机整数值,比aspx,java更简洁,不需要去/100, 不需要去round,ceil等,直接用mt_rand(m, n)就得到了.
count(*)和count(column)的区别?
http://www.cnblogs.com/wzmenjoy/p/4244590.html count(column)不计 column为null的条数?
sum(参数), 如果参数是列名, 则表示整个列的数值的和, 如果是条件表达式,则是表示 列值满足条件表达式 的记录 行数的 总和
不能用count(条件表达式) 如count(score<60) 来统计不及格的总数, 因为 count(参数)中,只要参数 !=NULL 则都表示计算总的记录条数. 所以,count(0)=count(1)=count(2)...=count(*)... 的
group by ,having等的用法:http://blog.csdn.net/zuiwuyuan/article/details/39431639
group: 意思是: 分组,聚合,组合,统计函数
having和where的区别?
where是对记录进行原始条件过滤,在分组 group by语句前使用; where中不能使用聚合函数.
having是对分组后的结果,进行条件过滤, 在having中可以使用 聚合函数,也可以使用 一般过滤条件.
where score > max(score): error: invalid use of group function.?
这个问题就是,"为什么在 where 子句中 要使用where score > = (select avg(score) from table)' 而不是直接使用 where score> avg(score)', 上面已经做了回答: 因为在where字句中不能使用group function! 所以,要用子查询...
mysql 为什么要使用group by 分组?
因为实际项目中, 有"需要分组, 按类别"进行数据查询,统计的需求. 将"某列(某个字段)具有相同值的多条记录合并为一组,最后作为一条记录输出", 注意这里是说 作为一条记录输出. 通常分组是和 聚合函数一起进行输出的, 通常输出的字段是 '分组字段1', '分组字段2...', '字段的聚合函数' from table group by '分组字段1', '分组字段2...'. 分组字段的选择是关键,要选择"某一列的值都相同的" 那个字段作为 "分组字段", 否则就失去了分组的意义,因为就没有办法分组.
(如果select语句中的 字段 没有使用组函数,那么它就必须出现在group by字句中, 即作为分组字段,否则,就只会显示第一条记录 的那个 字段值). 也就是说, 如果group by 不跟聚合函数一起使用, select中不是使用的分组字段/group function,则就是没有意义的分组,就是根本不懂分组的人.
mysql->php->browser的中文乱码问题?
下面的说法是不正确的!!!
很简单: 在mysql中不管,不要修改,保持为默认的utf-8; php就是连接的桥梁,是保证无乱码的核心; browser不用手动去设置, 它的内容的编码, 可以通过php的header函数来指定,来控制.
也就是说, 只要保证 *.php文件 要写入到 mysql数据库的文件编码是 utf-8 就 一切ok
一是, 跟php文件的 编辑器/ide有关, 看editor能不能设置为utf-8编码;
二是, 如果编辑器不能设置为utf-8编码,就要用字符集转换函数
php的 iconv和mb_convert_encoding?
两者都不是php的原生函数库函数, 要通过扩展开启才能使用: php_icon.dll, php_mbstring.dll(可以通过phpinfo查看);
iconv的效率比mb_convert_encoding快, 只有当不知道原来的编码,或iconv转换出错时,才使用后者;
iconv(in_charset, out_charset, str): out_charset//TRANSLIT(TRANSLATE + IT, 表示不能准确转换时,转换成一个近似的字符也可以),//IGNORE表示不能转换时,忽略它.
iconv和mb_convert_encoding, 他们的参数都是一样的, 但参数的方向正好相反. mb_convert_encoding(str, out_charset, [in_charset]最后这个"原来的字符编码集"参数是可选的)...
php header的格式
header函数调用, 要放在方法函数中, 不能放在php标签后,函数外部.header("字符串 Content-type: text/html; charset=utf-8 ");
mysql的查询操作 "时间"概念?
通常,一个简单的查询操作, 费时: 0.000几秒, 即万分之几秒, 多一点的操作 是 0.00几秒, 即千分之几秒.
php的类中的成员变量和成员方法 都要显式的说明其 访问类型, public,protected,private, 默认的,如果不写访问类型,则是public.
PHP_EOL: end of line
在mac中: \r, unix-like: \n, windows: \r\n. 只是换行符, 但是在html中仍然只是表现为一个空格, 不会换行.
控制器中的方法,总是 先输出本方法中输出的内容, 然后,(如果有this->display()的话), 再输出对应的视图页的内容.
注意区别常量和"模板解析字符串"的区别?
因为这些常量和"convention"配置很容易混淆,所以要注意区别:
tp的常量包括: 预定义常量(如: THINK_VERSION,URL_COMMON...), 路径常量(THINK_PATH,LIB_PATH,CORE_PATH)等,系统常量(APP,ROOT,MODULE,CONTROLLER,ACTION,SELF, IS_POST)等等(这些系统常量中, 分成两种,有的只能用在PHP文件中,如: IS_POST,有的既可以用于php文件中,又可以用于View视图的html页面中, 如: URL之类的系统常量,SELF,MODULE,CONTROLLER,__ACTION__等, 而且这些变量可以用在html模板中的任意地方,既可以是地址之类的,如href,form的action,也可以直接在页面内容中输出...)
前面的常量, **只是限于系统已经定义了的(__PUBLIC__这个好像是已经定义了的, 好像不一定只是帮组手册上所提到的那些), 如果没有定义,你就不能在view视图页面内直接使用,要使用自己定义的模板变量进行地址替换, 就必须在配置文件的TMPL_PARSE_STRING中进行设置和规定.**
系统常量中的URL地址之类的东西,总是从根路径 "/"开始输出的(并且除了__ROOT__之外,其余都是带index.php入口地址的), 如: ROOT:/, MODULE: /index.php/Home, CONTROLLER: /index.php/Home/Index, 而且通常URL地址类的系统常量,是不带最后面的斜杠的,所以后面要接地址时,要自己加/
R函数是做什么的?
在同一个控制器内,调用方法时,可以直接使用 funcName(); 但是如果一个控制器的方法, 要调用另一个控制器的方法, 那么就要用R 函数了,支持从 R(module/controller/method)
A方法和R方法的区别?
都是跨"模块/控制器"调用方法的, A方法是明确实例化一个控制器的对象,然后调用其中的方法$Con=A('Foo'); $Con->method1(); $Con->method2()..., 相当于$Con=new FooController()...
, 而R方法是每次都要实例化一个类的对象,R('Foo')->method1(); R('Foo')->method2(); 这个会生成两个实例
. 因此,如果要使用其他模块的多个方法,建议使用A方法.如果只使用其他模块内的一个方法, 用R方法最简洁.
U方法和"地址类系统变量"的区别?
"地址类系统变量" 只能使用本模块/本控制器/本操作的方法, 如果要使用其他模块或控制器的方法地址时,就 要使用U方法了. U方法可以通过在php操作中赋值然后assign的方式使用,也可以直接在模板中使用 {:U(oper)} 会一直生成完整 的路径 /index.php/Home/Index/oper.html(很奇怪,这个也可以访问,其实应该是重定向了?)
如何根据md5值反向 找到是哪个方法生成的cache?
这个是不可以的! 因为md5: message-digest algorithm 5,将任意长度的字符串,经过算法处理,转换成128bit的整数,共32为16进制数字 md5是 哈希混淆,不可逆的, 也就是md5是不可解密的,将用户的密码经过md5加密后放入数据库中, 即使是管理员也不能看到用户的密码,做到了地位平等 要暴力破解,也是用一些常用的字符串经过md5加密后,做成一个表,然后遍历比较.密码验证的原理也是这样的: 将输入的密码,md5转换后,然后与数据库中保存的相比较...
Application/Runtime/Cache/Home/缓存规则名称??.php缓存文件名称是怎么来的,如何知道它是哪个 html文件的缓存?
为什么thinkphp的 View/Controller_name/oper_name.html 的缓存竟然成了????.php文件呢? 因为tp的view下的模板文件中使用了 模板标签,如{$varname}, {:U(....)}等, 所以经过缓存后,就成了<?php echo $varname} , echo U(...)...?>
的 php文件 tp手册上有说明, 静态缓存文件的 名称 有 多种 规则,(当然绝对不是模板文件的名称, 所以就不要用模板文件名去试探了...) 最后可能使用了md5函数
肯定的: convention.php中并没有包含完全/所有的配置项, 如关于静态缓存的配置 TMPL_CACHE_ON => true, TMPL_CACHE_TIME => 60秒...
**注意这里应该是TMPL,不是HTML. 有些所谓的手册或文章是错误的!
part: n.部分,零件;v. 使分割,分开,分隔.
apart: a-part: 分开的;
partial: 部分的, 偏爱的, 钟爱的 be partial to Chinese food.
impartial: 不偏不倚的,公平的,公正的,持平的 as an impartial observer, an impartial view.
partly:部分地
depart: de-(分开)-part(分隔): 分隔|分开| -> 离开 he departed from Beijing.
因此, thinkphp中的DEPR,就是分隔符,分割符的意思.包括: TMPL_FILE_DEPR, URL_PATHINFO_DEPR等.
thinkphp为什么能够 全盘(在任何目录或文件中都可以)应用那些 常量/变量/设置/类/函数?
- 所有的请求都被应用程序的入口文件index.php所拦截了
- 入口文件包含了ThinkPHP框架的入口文件 require ...ThinkPHP.php
在ThinkPHP.php, 首先定义了 (最基本的一些常量) 包括框架的const 预定义常量(const URL_COMMON=0 ... const EXT='.class.php' const THINK_VERSION = '3.2.3'...) , 路径常量(THINK_PATH, LIB_PATH, CORE_PATH,....), 跟系统信息 有关的常量(IS_WIN, IS_CGI,IS_CLI) 还有一个 ROOT,是在ThinkPHP.php文件中定义的.
- 然后调用了 require CORE_PATH.'Think'.EXT
在Think.class.php是tp 整个底层框架的 引导类, 由它加载所有的底层架构,包括模型/视图/缓存/日志/配置等等... 所以可以实现上面的目的...
6 最后引导应用程序启动 Think\Think::start();
Thinkphp为什么能够拦截所有请求, 实现单一入口?
由index.php来响应所有的http请求,来统一调度 :如同一栋房子中的多个房间只有一扇门,进入门之后, 再到哪个房间,则由 dispatch::dispatch() 来决定路由和哪个控制器和action,在dispatch中有 $_SERVER['HTTP_URI'],解析它就知道是哪个controller和action了. 这个 dispatch::dispatch() 里面就对url进行了分析, 结合 getController /Action/ Module 确定出了 ...
Runtime目录是在App目录下, 不是在模块目录下Home, 它是包括Cache, Data, Log等在内的,其中Cache下再分模块Home等...
页面布局: 按钮元素靠两边, 内容占中间.
开发功能模块的思路?
先要进行功能整理, 弄清该模块(管理)包括哪些功能, 然后可以用两种方式来组合实现: 一是模块为目录,每个功能为一个单独的文件,这样功能之间相互独立,但是不利于代码的共享; 二是,模块定义为一个类文件,其中的功能定义为类中的方法...
有关/module/controller/action____的系统常量 是在: CORE_PATH/dispatch.class.php中定义的, dispatcher类就是完成 /module/controller/action对应的常量的定义, 以及解析pathinfo的路径地址进行 路由和调度 ,将模块/控制器/动作的形式 解释调度到 对应的视图html模板上去...
class dispatcher{ //这里是erstatic public function dispatch(){ // 这里没有-er....define('__CONTROLLER__', __MODULE__.$depr.(defined(BIND_CONTROLLER) ? '' :($urlCase ? parse($controller) : $controller ));...}}
而__PUBLIC__, ROOT, __MODUEL__等在模板中的替换工作, 则是在 THINK_PATH/Behavior/ContentReplace.class.php中 的 入口函数 public function run(&$content)->templateContentReplace($content)中,作为$replace=array(..., 'PUBLIC' => ROOT."/Public"...); 来替换的...
static 和publi private等的位置关系?
static和public等位置可以颠倒. 说法是: 编译的先后顺序不同,但结果是一样的; 静态的公开成员和公开的静态成员; 跟不同语言的编写"约定"的风格有关,比如c++中就把public放在static的前面, php中就把static放在public的前面,遵循大多数人的/语言的默认风格就好. 在php中, 类都是public的 ,static是类层次的,public是成员层次的.php中大多数都是将static放在public的前面的,如: static public function dispatch(){...}
如何设置地址重写?
地址重写Rewrite跟 配置文件convention.php中的 URL_REWRITE=>2, 'URL_MODEL'=>1等都没有关系,.htacess是分布式重写控制, 可以实现服务器级别和目录级别的重写. 只要放在某个目录下,那么这个目录就可以自动 实现地址重写,如果放在app的父目录下,则整个项目都可以实现重写. (原生的.htaccess实际上只是实现了隐藏index.php的功能)
要开启Rewrite, 只要开启apache的rewrite模块功能就好了 在上面打勾就行.
Rewrite目的是为了 url跳转和地址隐藏,可以实现 伪静态, 域名跳转,防止盗链.
<IfModule mod_rewrite.c>
Options +FollowSymLinks //这个是必须的,否则报错: 500 服务器内部错误RewriteEngine On测试(Perl的 (类似linux的shell)正则表达式) 匹配条件, 依次有多条, 条件成立(测试匹配,如同if...)才执行下面的Rewrite substition// %{REQUEST_FILENAME}: htaccess/mod_rewrite定义的内部变量,表示请求的文件
// -d:表示前面的%{REQUEST_FILENAME}, 存在且是目录 , -f表示 存在且为普通文件.
// !-d, !-f 就表示 要么不存在, 或者不是目录或文件. (通常的情况是 表示 "不存在", 如果要访问的地址存在,一般都是目录/文件,则直接访问,
// 因为不匹配测试条件,所以就不执行 rewrite rule了
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME} !-fRewriteRule ^(.*)$ index.php/$1 [QSA,PT,L] RewriteRule ^(.*)$ http://other.example.com/$1 [参数/标记/附加说明]RewriteRule指令/语句的格式: RewriteRule Pattern Substitution [flags] 参考:http://blog.csdn.net/paulluo0739/article/details/17711851
QSA: qsappend, PT: passthrough(在应用多个模块如mod_rewrite, mod_alias对地址进行重写时使用),L: last.</IfModule>
配置文件convention.php中的'VAR_CONTROLLER'=>'c' ,就是用来在 $_GET['c']中获取控制器的.