Chang Crazy's Blog

升级自己的操作系统


  • 首页

  • 归档

  • 标签

  • 分类

  • 日程表

  • 关于

  • 搜索

principles(原则)

2016-06-15

建立自己的原则系统, 把一些好的概念与方法论,应用到自己的生活中方方面,形成自己的“原则”。

进取型人格宣言

  1. 学习其实是一种生活方式,学习本身就是最好的洗脑方式。
  2. 只要我投入时间精力,长期来看,没有什么是我学不会的。
  3. 我学会的东西越多,我再学新的东西就只能越来越快。
    阅读全文 »

数据库设计

2016-01-28

数据库的基本概念

基本概念就一页PPT,让大家就一些数据库方面的概念达成一致。

  1. “单库”。

  2. “分片”,也就是水平切分,它是用来解决数据量大的问题。有一些数据库支持auto sharding,自动分片,例如mongoDB,后来发现auto sharding不太可控,不知道什么时候会进行数据迁移,数据迁移过程中会有大粒度的锁,读写被阻塞,业务会有抖动和毛刺,这些是业务不能接受的。

阅读全文 »

【转】赶集Mysql军规

2016-01-28

写在前面:

++ 总是在灾难发生后,才想起容灾的重要性;总是在吃过亏后,才记得曾经有人提醒过。++

核心军规

  1. 不在数据库做运算:cpu计算务必移至业务层
  2. 控制单表数据量:单表记录控制在1000w
  3. 控制列数量:字段数控制在20以内
  4. 平衡范式与冗余:为提高效率牺牲范式设计,冗余数据
  5. 拒绝3B:拒绝大sql,大事物,大批量
阅读全文 »

如何高效生成趋势有序的全局唯一ID?

2015-12-04

生成一个记录标识的需求,例如:

  1. 消息标识:message-id
  2. 订单标识:order-id
  3. 帖子标识:tiezi-id

这个记录标识往往就是数据库中的唯一主键,数据库上会建立聚集索引(cluster index),即在物理存储上以这个字段排序。

阅读全文 »

nodejs 基础

2015-11-14

Node.js 是单进程单线程应用程序,但是通过事件和回调支持并发,所以性能非常高。Node.js 的每一个 API 都是异步的,并作为一个独立线程运行,使用异步函数调用,并处理并发。Node.js 基本上所有的事件机制都是用设计模式中观察者模式实现。Node.js 单线程类似进入一个while(true)的事件循环,直到没有事件观察者退出,每个异步事件都生成一个事件观察者,如果有事件发生就调用该回调函数。

阅读全文 »

如何快乐的去工作

2015-10-15

如何快乐的去工作

简化工作的高效法则

我们创造了那么多条条框框,中间部门和协调人员,对每个员工进行问责制,之后考核量化kpi,有增加了很多了复杂度。当我责怪一个人的时候,而不是责怪清晰度、问责制、衡量方法的时候,我们在无效之后有增加了很多。

阅读全文 »

门面模式(command pattern)

2015-09-29

命令模式就是将一组对象的相似行为,进行了抽象,将调用者与被调用者之间进行解耦,提高了应用的灵活性。命令模式将调用的目标对象的一些异构性给封装起来,通过统一的方式来为调用者提供服务。

CommandInterface.php

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<?php

namespace DesignPatterns\Behavioral\Command;

/**
* CommandInterface
*/
interface CommandInterface
{
/**
* 在命令模式中这是最重要的方法,
* Receiver在构造函数中传入.
*/
public function execute();
}

HelloCommand.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
<?php

namespace DesignPatterns\Behavioral\Command;

/**
* 这是一个调用Receiver的print方法的命令实现类,
* 但是对于调用者而言,只知道调用命令类的execute方法
*/
class HelloCommand implements CommandInterface
{
/**
* @var Receiver
*/
protected $output;

/**
* 每一个具体的命令基于不同的Receiver
* 它们可以是一个、多个,甚至完全没有Receiver
*
* @param Receiver $console
*/
public function __construct(Receiver $console)
{
$this->output = $console;
}

/**
* 执行并输出 "Hello World"
*/
public function execute()
{
// 没有Receiver的时候完全通过命令类来实现功能
$this->output->write('Hello World');
}
}

Receiver.php

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
<?php

namespace DesignPatterns\Behavioral\Command;

/**
* Receiver类
*/
class Receiver
{
/**
* @param string $str
*/
public function write($str)
{
echo $str;
}
}

Invoker.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
<?php

namespace DesignPatterns\Behavioral\Command;

/**
* Invoker类
*/
class Invoker
{
/**
* @var CommandInterface
*/
protected $command;

/**
* 在调用者中我们通常可以找到这种订阅命令的方法
*
* @param CommandInterface $cmd
*/
public function setCommand(CommandInterface $cmd)
{
$this->command = $cmd;
}

/**
* 执行命令
*/
public function run()
{
$this->command->execute();
}
}

测试代码 Tests/CommandTest.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

<?php

namespace DesignPatterns\Behavioral\Command\Tests;

use DesignPatterns\Behavioral\Command\Invoker;
use DesignPatterns\Behavioral\Command\Receiver;
use DesignPatterns\Behavioral\Command\HelloCommand;

/**
* CommandTest在命令模式中扮演客户端角色
*/
class CommandTest extends \PHPUnit_Framework_TestCase
{

/**
* @var Invoker
*/
protected $invoker;

/**
* @var Receiver
*/
protected $receiver;

protected function setUp()
{
$this->invoker = new Invoker();
$this->receiver = new Receiver();
}

public function testInvocation()
{
$this->invoker->setCommand(new HelloCommand($this->receiver));
$this->expectOutputString('Hello World');
$this->invoker->run();
}
}

代理模式(proxy pattern)

2015-09-29

代理模式(Proxy)为其他对象提供一种代理以控制对这个对象的访问。使用代理模式创建代理对象,让代理对象控制目标对象的访问(目标对象可以是远程的对象、创建开销大的对象或需要安全控制的对象),并且可以在不改变目标对象的情况下添加一些额外的功能。

在某些情况下,一个客户不想或者不能直接引用另一个对象,而代理对象可以在客户端和目标对象之间起到中介的作用,并且可以通过代理对象去掉客户不能看到的内容和服务或者添加客户需要的额外服务。

代理模式在很多情况下都非常有用,特别是你想强行控制一个对象的时候,比如延迟加载、监视状态变更的方法等等。

与类似接口的区别:

  • 适配器模式 —— 适配器模式为它所适配的对象提供了一个不同的接口,而代理提供了与它的实体相同的接口。
  • 装饰器模式 —— 两者目的不同:装饰器为对象添加一个或多个功能,而代理则控制对对象的访问。
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

// record.php

namespace DesignPatterns\Structural\Proxy;

/**
* Record类
*/
class Record
{
/**
* @var array|null
*/
protected $data;

/**
* @param null $data
*/
public function __construct($data = null)
{
$this->data = (array) $data;
}

/**
* magic setter
*
* @param string $name
* @param mixed $value
*
* @return void
*/
public function __set($name, $value)
{
$this->data[(string) $name] = $value;
}

/**
* magic getter
*
* @param string $name
*
* @return mixed|null
*/
public function __get($name)
{
if (array_key_exists($name, $this->data)) {
return $this->data[(string) $name];
} else {
return null;
}
}
}


// RecordProxy.php

namespace DesignPatterns\Structural\Proxy;

/**
* RecordProxy类
*/
class RecordProxy extends Record
{
/**
* @var bool
*/
protected $isDirty = false;

/**
* @var bool
*/
protected $isInitialized = false;

/**
* @param array $data
*/
public function __construct($data)
{
parent::__construct($data);
//当记录有数据时,将其标记为初始化.
//由于记录将保持我们的业务逻辑,我们不想在那里实现这个行为,而不是在一个新的代理类
//扩展记录类

if (null !== $data) {
$this->isInitialized = true;
$this->isDirty = true;
}
}

/**
* magic setter
*
* @param string $name
* @param mixed $value
*
* @return void
*/
public function __set($name, $value)
{
$this->isDirty = true;
parent::__set($name, $value);
}
}


//测试代码

namespace DesignPatterns\Structural\Proxy\Tests;

use DesignPatterns\Structural\Proxy\Record;
use DesignPatterns\Structural\Proxy\RecordProxy;

class ProxyTest extends \PHPUnit_Framework_TestCase
{
public function testSetAttribute(){
$data = [];
$proxy = new RecordProxy($data);
$proxy->xyz = false;
$this->assertTrue($proxy->xyz===false);
}
}

依赖注入(dependency injection pattern)

2015-09-28

依赖注入模式需要在调用者外部完成容器创建以及容器中接口与实现类的运行时绑定工作,在 Laravel 中该容器就是服务容器,而接口与实现类的运行时绑定则在服务提供者中完成。此外,除了在调用者的构造函数中进行依赖注入外,还可以通过在调用者的方法中进行依赖注入。

三种常见注入方式:

  1. 构造注入
  2. setter注入
  3. 接口注入
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
interface Shape
{
public function getCircum();

public function getArea();
}

//矩形

class Rectangle implements Shape
{

private $width, $height;

public function __construct($width, $height)
{
$this->width = $width;
$this->height = $height;
}

public function getCircum()
{

return ($this->width + $this->height) * 2;
}

public function getArea()
{

return $this->width * $this->height;
}
}

class Circle implements Shape
{

private $radii;

public function __construct($radii)
{
$this->radii = $radii;
}

public function getCircum()
{
// TODO: Implement getCircum() method.
return 2 * M_PI * $this->radii;

}

public function getArea()
{
// TODO: Implement getArea() method.
return M_PI * pow($this->radii, 2);
}
}

构造注入

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23

class DependencyInjection
{
public $shape;

public function __construct(Shape $shape)
{
$this->shape = $shape;
}
}


// 调用示例:

$rectangle = new Rectangle(4, 2);
$r_di = new DependencyInjection($rectangle);
echo $r_di->shape->getCircum();
echo $r_di->shape->getArea();

$circle = new Circle(3);
$c_di = new DependencyInjection($circle);
echo $c_di->shape->getCircum();
echo $c_di->shape->getArea();

setter 注入

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19

class DependencyInjectionSetter
{

public $shape;

public function setter(Shape $shape)
{

$this->shape = $shape;
}
}

//调用示例:

$rectangle = new Rectangle(4, 2);
$setter_di = new DependencyInjectionSetter();
$setter_di->setter($rectangle);
echo $setter_di->shape->getCircum();

interface 注入

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
interface ServiceSetter
{
public function setService(Shape $shape);
}

class ServiceClient implements ServiceSetter
{

public $shape;

public function setService(Shape $shape)
{
// TODO: Implement setService() method.
$this->shape = $shape;
}
}

//调用示例:

$sc = new ServiceClient();
$sc->setService($rectangle);
echo $sc->shape->getArea();

工厂模式(factory pattern)

2015-09-27
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
interface Shape
{
public function getCircum();

public function getArea();
}

//矩形

class Rectangle implements Shape
{

private $width, $height;

public function __construct($width, $height)
{
$this->width = $width;
$this->height = $height;
}

public function getCircum()
{

return ($this->width + $this->height) * 2;
}

public function getArea()
{

return $this->width * $this->height;
}
}

class Circle implements Shape
{

private $radii;

public function __construct($radii)
{
$this->radii = $radii;
}

public function getCircum()
{
// TODO: Implement getCircum() method.
return 2 * M_PI * $this->radii;

}

public function getArea()
{
// TODO: Implement getArea() method.
return M_PI * pow($this->radii, 2);
}
}



// 创建工厂
class Factory
{

public static function create()
{
//判断穿过来的参数个数
switch (func_num_args()) {
case 1:
return new Circle(func_get_arg(0));
break;
case 2:
return new Rectangle(func_get_arg(0), func_get_arg(1));
break;
}

}
}


$rectangle = Factory::create(4,2);
echo $rectangle->getCircum()." ";
echo $rectangle->getArea()." ";

$circle = Factory::create(3);
echo $circle->getCircum()." ";
echo $circle->getArea();
1…4567
changyuan

changyuan

不断升级自己的操作系统

69 日志
1 分类
26 标签
GitHub Twitter Weibo Zhihu
Links
  • Weibo
  • GitHub
© 2023 changyuan
载入天数... 载入时分秒...