您的位置:首页 > 编程语言 > PHP开发

如何使用抽象类和接口类? (JAVA、PHP通用)

2010-08-10 15:09 549 查看
 


在我才接触php的时候,也觉得这个东西没有什么用,在后来的逐渐接触大系统以后,才发现其实这些东西还是有一定的作用的,下面我就简单的说说。
1.php 接口类:interface
其实他们的作用很简单,当有很多人一起开发一个项目时,可能都会去调用别人写的一些类,那你就会问,我怎么知道他的某个功能的实现方法是怎么命名的呢,这个时候php接口类就起到作用了,当我们定义了一个接口类时,它里面的方式是下面的子类必须实现的,比如
interface Shop

{

public function buy($gid);

public function sell($gid);

public function view($gid);

}

我声明一个shop接口类,定义了三个方法:买(buy),卖(sell),看(view),那么继承此类的所有子类都必须实现这3个方法少一个都不行,如果子类没有实现这些话,就无法运行。实际上接口类说白了,就是一个类的模板,一个类的规定,如果你属于这类,你就必须遵循我的规定,少一个都不行,但是具体你怎么去做,我不管,那是你的事,如:
class BaseShop implements Shop

{

public function buy($gid)

{

echo '你购买了ID为 :' . $gid . '的商品';

}
public function sell($gid)

{

echo '你购卖ID为 :' . $gid . '的商品';

}
public function view($gid)

{

echo '你浏览了ID为 :' . $gid . '的商品';

}

}

你想想,在一个多人合作的大项目里面,有了接口类是多么的方便,这样你就不用去问别人,你的某某功能的方法名是什么了,当然如果你们喜欢这样我也没有办法。
结论 : 接口类就是一个类的领导者,指明方向,子类必须完成它指定方法。

2.php 抽象类 : abstract
其实抽象类和接口类有一部分很像,记得在哪里看见这样一句话,抽象类就把类像的部分抽出来,这句看上去很搞笑,其实它说出了抽象类的真理,抽象类的作用是,当你发现你的很多类里面用很多方法你不断的在重复写,那你就可以考虑使用抽象类了,你可能会说“我不是可以重写一个类每个公共类我个实例化一个这个公共类,调用相同的方法就可以了”,这里是可以,实际上抽象类做的工作也就是这个,不过他省去了你实例化的这个步骤,让你就像直接调用本类方法一样方便,而且你还可以重载这个方法。如:
abstract class BaseShop {

public function buy($gid)

{

echo '你购买了ID为 :' . $gid . '的商品';

}
public function sell($gid)

{

echo '你购卖ID为 :' . $gid . '的商品';

}
public function view($gid)

{

echo '你浏览了ID为 :' . $gid . '的商品';

}

}
class BallShop extends BaseShop

{

var $itme_id = null;
public function __construct()

{

$this->itme_id = 2314;

}
public function open()

{

$this->sell($this->itme_id);

}

}

这里是一个例子,想上面一样我定义了一个商店类,抽所了它所有像的部分,买(buy),卖(sell),看(view),并且抽象类里都实现了这些方法,那么继承它的子类就自动获得了这些方法,子类就做它自己独特的东西,介绍代码的重复,提高复用性。
结论: 抽象类就是一个类的服务提供商,拥有众多服务,你不用必须用,当需要的时候你来用就可以,如果你觉得不提供服务不满意,你还可以自己来做。

抽象类和接口是OO里比较难理解的概念,也是比较容易混淆的。

抽象类和接口都不能直接实例化。在抽象类里可以实现一些功能,但在接口里面则不能实现功能。

LZ的例子不好,我给你换个例子:(这里我只是从<<权威编程>>里copy一些例子,因为我也懒,呵呵。) 复制内容到剪贴板

代码:

抽象类:

abstract class Shape

{
function setCenter($x, $y)

{
$this->x = $x;

$this->y = $y;
}
abstract function draw();
protected $x, $y;
}

接口:

interface Loggable

{
function logString();
}


这里很清楚的显示了在抽象类里,我们贯彻了设原用到点setCenter()的方法,这样,当子类继承它时,就不用再重复写这个设原点的方法了。那么为什么draw的方法要设定成抽象方法呢?这是因为不同的子类要用不同的实现方法。那么我们干脆不要这个什么抽象方法,而在子类里再实现不是更好吗?哈哈,你忘了很多程序员都自称是懒人吗?在抽象类里先定义一个抽象方法,就是告诉你,在子类里面一定要用到这个方法,如果你忘了,漏了,那是不行的。但是因为每个做法不一样,所以我抽象类这里就不把它先做好了。
接口的作用与抽象类相似的地方在于:所有方法都是抽象的,也就是说,如果你要继承这个接口,那么所有的这些方法,你都要在子类里实现,一个不能漏,一个不能忘。
子类继承的例子: 复制内容到剪贴板

代码:

抽象类的继承:

class Square extends Shape

{
function draw()
{
// Here goes the code which draws the Square

...
}
}
class Circle extends Shape

{

function draw()
{

// Here goes the code which draws the Circle

...
}
}

接口的继承:

class Person implements Loggable

{
private $name, $address, $idNumber, $age;
function logString()

{
return "class Person: name = $this->name, ID = $this >idNumber/n";
}
}
class Product implements Loggable

{
private $name, $price, $expiryDate;
function logString()

{
return "class Product: name = $this->name, price = $this >price/n";
}
}


LZ说:没实际功能为什么还要继承?

因为这是OO设计上的要求。实际应用时的例子不会这么简单。在OO设计时,会把一些通用的方法放在一个类里,但考虑到子类继承时的差异性,又不能把它事先实现,就只好用到这个抽象类或接口了。
LZ说:但是不如一个类离开了父类车,不是照样可以完成自己的功能?

当然你可以在子类里实现所有的功能,甚至于不要父类,但这样做,与过程编程没什么两样,也就谈不上什么OO思想了。
先顶结构后开发实现代码提高系统的可扩展和快速变动系统架构

LZ说:一般的类继承后可以覆盖父亲的方法,但是抽象类完全没有功能,难道就是为了好看?

因为你举的例子不好,所以抽象类完全没有功能。但就算抽象类完全没有功能,像接口一样,那也不是为了好看,你以为懒人会吃饱了撑着没事干要找活干吗?道理上面讲过了。
LZ说:麻烦解答下我帖子上关于接口的问题?

原理上面讲过了。
LZ说:想了很久,只是觉得,抽象类和接口都是为了方便读代码的人,或者说是写代码的规范?

错!!!道理上面讲过了。
紫幻凌说:我也一直疑惑为什么要弄个抽象类?普通的父类不也能好好的被继承?为什么一定要抽象呢?

道理讲完了,还疑惑吗?
LZ说:问题是什么时候用。。。想不出什么时候用?

什么时候用抽象类,什么时候用接口,这个嘛,嘿嘿,谁用谁知道!(你以为是卖广告啊?!)
在讲之前,大家要记住OO的一个原则:一个类只能extends一个父类,但可以贯彻多个接口。

比如说

class Square extends Shape implements B, C, ... {

...

}

有时候,我们需要设计一个物品,比如shape,这个shape有不同的形状,有不同的颜色,可作不同的运动,等等。当然我们可以把这些都放在一个类里面,但这样,如前面说的,只是过程编程,不是OO编程。你会说,像上面例子一样,做一个抽象类,然后在子类里实现所有的功能。好象不错,进步了。这样子类里面要实现形状,颜色,运动等功能,OK吗?记住,OO里面还有一条原则,为了最大程度的做到代码重用,一个类里最好只实现一个功能,也就是说,一个类做形状,一个类做颜色,一个类做运动
。这样如果其他的类要用到颜色的功能时,我们就可以重用这个颜色类,同理,这样我们可以很容易的重用运动类,形状类,等等。
但这样问题出来了,现在我们要用到上面所有的功能,但又分散在三个类里面,怎么办?

这时我们就要用到抽象类和接口了。选定一个跟shape关联最大的一项–形状,把它做成抽象类,
其他两样,把它们做成接口,然后在子类里面extends一个抽象类,再implements两个接口就行了。如:

class Square extends Shape implements 颜色, 运动, ... {

...

}
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息