庆祝GOOGLE.cn 回归

今天,2010-8-24,打开 google.com, 赫然发现右下角的 Go to Google China, 点击进去查看时,竟然发现 google.cn 回来了,不再跳转至 google.com.hk。心中激动,发文纪念。

google

北京时间3月23日凌晨,Google在其官方博客宣布google.cn的搜索服务将跳转到google.com.hk。一时间猜测纷纷,不过互联网者大概都知晓其中的苦衷,多少人扼腕叹息。

当时的原因:
Google 中国业务成鸡肋;
Google 不接受中国网监的审查,不遵守中国法律,很奇怪,google 是遵守印度等国家的法律的,唯独就不遵守中国的?
Google 的GMAIL受到攻击;
……

业务原因还是政治原因?

产品好就是不一样,客户的忠诚度说明了一切:

自从3月谷歌将服务器转移到香港并停止过滤搜索结果之后,国内搜索引擎市场并没有如多位业内人士预测的那样,发生天翻地覆的变化。谷歌仍然保持了在市场中的份额与地位,与百度的对比关系也没有太大改变。而艾瑞咨询的数据显示,3月23日谷歌实行自动跳转后的几周内,访问谷歌的流量有所下降,同时百度有所上升。但三周之后,双方又回归到之前的稳定状态,百度占据六成份额,谷歌则稳定在三成。所以说前一段时间对于Google在中国市场这块的影响还是很小的。

有竞争才有进步,Google 的回归,希望可以使国内的搜索引擎有进步。

PHP帮助手册拾遗二:流程控制

PHP帮助手册拾遗:流程控制

1、PHP支持用冒号的if语句

1
2
3
4
5
if (expr1) :                                                     
    statement1
elseif(expr2):
    statement2
endif;

endif后面有分号

2、PHP 也支持用冒号的 for 循环的替代语法。

1
2
3
4
for (expr1; expr2; expr3):                                                
  statement;
  ...
endfor;

很python的作法,只是还是需要加上endfor作为结束标记

1
2
3
for ($i = 0; $i < 10; $i++):
    echo $i, '<br />';
endfor;

3、foreach PHP 5 起,可以很容易地通过在 $value 之前加上 & 来修改数组的单元。此方法将以引用赋值而不是拷贝一个值。
如下所示代码:

1
2
3
4
5
6
7
8
$arr = array(1, 2, 3, 4);
foreach ($arr as &$value) {                                 
    $value = $value * 2;
}
//unset($value);    //    释放$value的引用                               
var_dump($arr);
$value++;
var_dump($arr);

只是在写修改完后,需要释放$value的引用,否则在下次修改此变量时,会改变数组元素的内容,慎重!(某犯过此错误)

4、break 可以接受一个可选的数字参数来决定跳出几重循环。

1
2
3
4
5
6
7
8
9
10
11
for ($i = 1; $i < 10; $i++) :                                     
 
    for ($j = 1; $j < 10; $j++) :
       echo $i, ' ', $j, '<br />';
 
       if ($i + $j > 15) {
               break 2;    //    直接跳转所在的二重循环                                              
       }
    endfor;
 
endfor;

5、注意在 PHP 中 switch 语句被认为是可以使用 continue 的一种循环结构。
6、continue 接受一个可选的数字参数来决定跳过几重循环到循环结尾。
7、在 switch 语句中条件只求值一次并用来和每个 case 语句比较。在 elseif 语句中条件会再次求值。
case 表达式可以是任何求值为简单类型的表达式,即整型或浮点数以及字符串。不能用数组或对象,除非它们被解除引用成为简单类型。
8、declare 结构用来设定一段代码的执行指令。declare 的语法和其它流程控制结构相似
directive 部分允许设定 declare 代码段的行为。目前只认识一个指令:ticks

Tick 是一个在 declare 代码段中解释器每执行 N 条低级语句就会发生的事件。N 的值是在 declare 中的 directive 部分用 ticks=N 来指定的。
在每个 tick 中出现的事件是由 register_tick_function() 来指定的。

Ticks 很适合用来做调试,以及实现简单的多任务,后台 I/O 和很多其它任务。
手册上的示例:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
function profile($dump = FALSE)                                          
{
   static $profile;
 
   // Return the times stored in profile, then erase it
   if ($dump) {
       $temp = $profile;
       unset($profile);
       return ($temp);
   }
 
   $profile[] = microtime();
}
 
// Set up a tick handler
register_tick_function("profile");
 
// Initialize the function before the declare block
profile();
 
// Run a block of code, throw a tick every 2nd statement
declare(ticks=2) {
   for ($x = 1; $x < 50; ++$x) {
       echo similar_text(md5($x), md5($x*$x)), "<br />;";
   }
}
 
// Display the data stored in the profiler
print_r(profile (TRUE));

上面的这功能真没听说过,作为一个后学末进的程序员,看手册是必须的。

10、return
return() 是语言结构而不是函数,仅在参数包含表达式时才需要用括号将其括起来。当返回一个变量时通常不用括号,也建议不要用,这样可以降低 PHP 的负担。
注: 当用引用返回值时永远不要使用括号,这样行不通。只能通过引用返回变量,而不是语句的结果。如果使用 return ($a); 时其实不是返回一个变量,而是表达式 ($a) 的值(当然,此时该值也正是 $a 的值)。

11、include() 是一个特殊的语言结构,其参数不需要括号。在比较其返回值时要注意。
例如,test.txt中包含字符串 ‘abc’,则判断包含test.txt中是否返回’abc’语句不能以函数的调用方式。
如下所示代码:

1
2
3
4
5
6
7
8
if (include("test.txt") == 'abc') {                                            
    echo 'yes';
}
/* 以上是错误的代码,程序会执行错误,显示warning */
 
if ((include "test.txt") == 'abc') {
    echo 'yes';
}

12、从PHP3.0开始添加了goto语句,但是此语句不能跳转进入loop或switch 语句

PHP设计模式笔记:使用PHP实现命令模式

PHP设计模式笔记:使用PHP实现命令模式

【意图】
将一个请求封装为一个对象,从而使用你可用不同的请求对客户进行参数化;对请求排队或记录请求日志,以及支持可撤消的操作。
可变的方面是:何时,怎样满足一个请求
命令模式是对命令的封装。命令模式把发出命令的责任和执行命令的责任分割开,委派给不同的对象。
请求的一方发出请求要求执行一个操作;接收的一方收到请求,并执行操作。命令模式允许请求的一方和接收的一方独立开来,使得请求的一方不必知道接收请求的一方的接口,更不必知道请求是怎么被接收,以及操作是否被执行、何时被执行,以及是怎么被执行的。

【命令模式结构图】

Command模式

Command模式

【命令模式中主要角色】
命令(Command)角色:声明了一个给所有具体命令类的抽象接口。这是一个抽象角色。
具体命令(ConcreteCommand)角色:定义一个接受者和行为之间的弱耦合;实现Execute()方法,负责调用接收考的相应操作。Execute()方法通常叫做执行方法。
客户(Client)角色:创建了一个具体命令(ConcreteCommand)对象并确定其接收者。
请求者(Invoker)角色:负责调用命令对象执行请求,相关的方法叫做行动方法。
接收者(Receiver)角色:负责具体实施和执行一个请求。任何一个类都可以成为接收者,实施和执行请求的方法叫做行动方法。

【命令模式的优点】
命令模式的优点:
1、命令模式把请求一个操作的对象与知道怎么执行一个操作的对象分离开。
2、命令类与其他任何别的类一样,可以修改和推广。
3、可以把命令对象聚合在一起,合成为合成命令。
4、可以很容易的加入新的命令类。
命令模式的缺点:可能会导致某些系统有过多的具体命令类。

【命令模式适用场景】
1、抽象出待执行的动作以参数化对象。Command模式是回调机制的一个面向对象的替代品。
2、在不同的时刻指定、排列和执行请求。
3、支持取消操作。
4、支持修改日志。
5、用构建在原语操作上的高层操作构造一个系统。Command模式提供了对事务进行建模的方法。Command有一个公共的接口,使得你可以用同一种方式调用所有的事务。同时使用该模式也易于添加新事务以扩展系统。

【命令模式与其它模式】
合成模式(composite模式):Composite模式可被实现宏命令
原型模式(prototype模式):如果命令类带有clone(或在之前的文章中提到的copy方法)方法,命令就可以被复制。在命令模式支持多次取消操作时可能需要用到此模式,以复制当前状态的Command对象

【命令模式PHP示例】

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
<?php
/**
 * 命令模式 2010-08-21 sz
 * @author phppan.p#gmail.com  http://www.phppan.com                                                       
 * 哥学社成员(http://www.blog-brother.com/)
 * @package design pattern
 */
 
/**
 * 命令角色
 */
interface Command {
 
    /**
     * 执行方法
     */
    public function execute();
}
 
/**
 * 具体命令角色
 */
class ConcreteCommand implements Command {
 
    private $_receiver;
 
    public function __construct(Receiver $receiver) {
        $this->_receiver = $receiver;
    }
 
    /**
     * 执行方法
     */
    public function execute() {
        $this->_receiver->action();
    }
}
 
/**
 * 接收者角色
 */
class Receiver {
 
    /* 接收者名称 */
    private $_name;
 
    public function __construct($name) {
        $this->_name = $name;
    }
 
    /**
     * 行动方法
     */
    public function action() {
        echo $this->_name, ' do action.<br />';
    }
}
 
/**
 * 请求者角色
 */
class Invoker {
 
    private $_command;
 
    public function __construct(Command $command) {
        $this->_command = $command;
    }
 
    public function action() {
        $this->_command->execute();
    }
}
 
/**
 * 客户端
 */
class Client {
 
     /**
     * Main program.
     */
    public static function main() {
        $receiver = new Receiver('phpppan');
        $command = new ConcreteCommand($receiver);
        $invoker = new Invoker($command);
        $invoker->action();
    }
}
 
Client::main();
 
?>

【命令模式协作】
1、Client创建一个ConcreteCommand对象并指定它的Receiver对象
2、某Invoker对象存储该ConcreteCommand对象
3、该Invoker通过调用Command对象的execute操作来提交一个请求。若该命令是可撤消的,ConcreteCommand就在执行execute操作之前存储当前状态以用于取消命令。
4、ConcreteCommand对象对调用它的Receiver的一些操作以执行该请求。

【宏命令】
在这里,我们以一个简单的增加和粘贴功能为例,将这两个命令组成一个宏命令。
我们可以新建复制命令和粘贴命令,然后将其添加到宏命令中去。
如下所示代码:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
 
<?php
/**
 * 命令模式之宏命令 2010-08-22 00:10  sz
 * @author phppan.p#gmail.com  http://www.phppan.com                                                   
 * 哥学社成员(http://www.blog-brother.com/)
 * @package design pattern
 */
 
/**
 * 命令角色
 */
interface Command {
 
    /**
     * 执行方法
     */
    public function execute();
}
 
/**
 * 宏命令接口
 */
interface MacroCommand extends Command {
 
    /**
     *  宏命令聚集的管理方法,可以删除一个成员命令
     * @param Command $command
     */
    public function remove(Command $command);
 
    /**
     * 宏命令聚集的管理方法,可以增加一个成员命令
     * @param Command $command
     */
    public function add(Command $command);
 
}
 
 
class DemoMacroCommand implements MacroCommand {
 
    private $_commandList;
 
    public function __construct() {
        $this->_commandList = array();
    }
 
    public function remove(Command $command) {
        $key = array_search($command, $this->_commandList);
        if ($key === FALSE) {
            return FALSE;
        }
 
        unset($this->_commandList[$key]);
        return TRUE;
    }
 
    public function add(Command $command) {
        return array_push($this->_commandList, $command);
    }
 
    public function execute() {
        foreach ($this->_commandList as $command) {
            $command->execute();
        }
 
    }
 
}
 
/**
 * 具体拷贝命令角色
 */
class CopyCommand implements Command {
 
    private $_receiver;
 
    public function __construct(Receiver $receiver) {
        $this->_receiver = $receiver;
    }
 
    /**
     * 执行方法
     */
    public function execute() {
        $this->_receiver->copy();
    }
}
 
/**
 * 具体拷贝命令角色
 */
class PasteCommand implements Command {
 
    private $_receiver;
 
    public function __construct(Receiver $receiver) {
        $this->_receiver = $receiver;
    }
 
    /**
     * 执行方法
     */
    public function execute() {
        $this->_receiver->paste();
    }
}
 
/**
 * 接收者角色
 */
class Receiver {
 
    /* 接收者名称 */
    private $_name;
 
    public function __construct($name) {
        $this->_name = $name;
    }
 
    /**
     * 复制方法
     */
    public function copy() {
        echo $this->_name, ' do copy action.<br />';
    }
 
    /**
     * 粘贴方法
     */
    public function paste() {
        echo $this->_name, ' do paste action.<br />';
    }
}
 
/**
 * 请求者角色
 */
class Invoker {
 
    private $_command;
 
    public function __construct(Command $command) {
        $this->_command = $command;
    }
 
    public function action() {
        $this->_command->execute();
    }
}
 
/**
 * 客户端
 */
class Client {
 
     /**
     * Main program.
     */
    public static function main() {
        $receiver = new Receiver('phpppan');
        $pasteCommand = new PasteCommand($receiver);
        $copyCommand = new CopyCommand($receiver);
 
        $macroCommand = new DemoMacroCommand();
        $macroCommand->add($copyCommand);
        $macroCommand->add($pasteCommand);
 
        $invoker = new Invoker($macroCommand);
        $invoker->action();
 
        $macroCommand->remove($copyCommand);
        $invoker = new Invoker($macroCommand);
        $invoker->action();
    }
}
 
Client::main();
 
 
?>

个人觉得在命令的委派操作上,与访问者模式(Visitor模式)有相似之处。