我正在通过编写自己的“简单”CMS系统来扩展我的PHP和一般编码知识。
我的数据库结构如下:
USERS --< WEBSITES --< PAGES
在我的逻辑中,我有三个类,一个User
,Website
和Page
类。 NOT INHERITED
User
类包含USER TABLE
加$_website
属性的所有属性,
Website
类具有WEBSITE TABLE
的所有属性以及Page
个对象的ARRAY
我决定使用它的方法是,在页面加载时,将创建这些类并填充数据库数据。
那么在html中我只需通过调用类来回显结果:
$USER -> name;
$USER -> website -> get_pages();
$USER -> website -> pages[0] -> get_header();
我意识到这些类可以继承,因此Page
继承Website
而Website
继承User
但如果我这样做,那么我将实例化Page
类,如:
$PAGES = array();
$PAGES[] = new Page( $constructor_data_to_construct_user_website_and_page );
现在如果我这样做,对象$PAGES[0]
将拥有与该页面有关的所有信息,以及与网站(第一个父母)有关的所有信息,
以及与用户(第二个父母)
如果我然后创建另一个Page
,我只是复制相同的User
和Website
详细信息 是
因此,如果我var_dump $PAGES[0]
id,请获取与USER,
WEBSITE
和PAGE
如果我要var_dump $PAGES[1]
id,请获取USERS
和WEBSITE
的所有相同信息,但只获取不同的Page
数据。
继承,导致不必要的用户和网站对象复制
因为我基本上可以这样做:
$PAGES[0] -> username // username is a property of the Users class
$PAGES[1] -> username
两者都会返回相同的值。
肯定这很糟糕,因为数据被不必要地复制了!这是正确的吗?
或者这个问题是垃圾,这不是inheritance
使用的情况吗?
答案 0 :(得分:3)
这正是不能使用继承的情况。
继承旨在模拟IS-A
关系。典型示例:Student
是一种Person
,因此Student
继承自Person
。
继承不是,不是, NOT 意味着建立HAS-A
关系。典型示例:Car
有一个Engine
,但Car
不是一种Engine
。
当我们有HAS-A
关系时(例如用户拥有网站),您几乎在所有情况下都应使用合成而不是继承:
class Website extends User {}
class Website {
private $users;
}
答案 1 :(得分:0)
当需要子类时,使用继承,该子类基本上是父类的特定类型。例如,动物的层次结构 - &gt;哺乳动物 - &gt;马是一种合理的遗传等级,因为马是特定类型的哺乳动物,哺乳动物是特定类型的动物。
在你的情况下,我不会使用继承。一个网站包含页面,但页面不是网站本身的扩展,而用户完全是一个完全不同的东西。做出决定时,通常使用“is-a”与“has-a”,如
页面是网站而网站有页面
在这种情况下,我认为后者(has-a)更具描述性。如果短语“is-a”更合适,那么它可能是继承的良好候选者。
答案 2 :(得分:0)
不,这不正确。只有当一个是另一个的子类型时才应该继承。
例如,如果您代表人员,您可能会有一个像Manager继承Employee的关系,因为Manager是特定类型的Employee。网站不是特定类型的用户,因此继承没有意义。
您正在寻找的是一种简单的关系(聚合),因为网站可能有很多页面,而用户可能有很多网站。
答案 3 :(得分:0)
如果您在其班级中将网站和用户字段声明为“静态”:
class Website extends User {
protected static $_xxx = '123';
}
class User {
protected static $_username = 'Fred';
}
然后它们将不会被复制,但它们将完全相同。
但是,在那个地方继承这是错误的 - 它是绑定的对象,但不是继承的。所以在这种情况下你不能使用继承 - 父类必须是子类的超集。