如何建模PHP多对多关系

时间:2015-10-26 13:56:20

标签: php model many-to-many

我需要为我们的一个客户建立一个项目系统。 项目系统具有以下(给定)数据库结构:

| item
+--------------------------
| id tinyint(4) primary key
| name varchar(30)

| attr
+--------------------------
| id tinyint(4) primary key
| name varchar(30)

| itemAttr
+--------------------------
| itemId foreign key
| attrid foreign key
| value varchar(255)

我有类结构:

<?php

abstract class Item {
    private $id;

    private $name;  
}

class ShopItem extends Item {
    private $itemType;

    private $price;

    private $imageHref;

    private $description;   
}

因为它是多对多的关系,所以我可以让X行包含关于“item”的单个信息。

如何捆绑/分组行,以便将信息映射到模型?

我需要例如一页20个不同的“ShopItems”

更新

我想在一个查询中处理所有数据库操作(这就是我的任务所说的......) 所以会有如下结果:

| id | name     | attrId | value |
+----+----------+--------+-------+
| 1  | Item1    | 1      | 1     |
| 1  | Item1    | 2      | Text  |
| 1  | Item1    | 3      | 100   |

我有不同的搜索条件:

Item需要具有以下属性: ItemType(attrId 1) 说明(attrId 2) 价格(attrId 3)

否则我不想从数据库中取出这个项目

3 个答案:

答案 0 :(得分:0)

一个选项(有几个 - 像往常一样)是将它们存储在地图中并通过通用getter访问这些属性(使用属性名称作为第一个参数)或使用魔术函数访问它们。

<?php
abstract class Item {
    private $id;

    private $name;

    protected $attributes = array();

    /**
     * @param $name The attribute key/name
     * @return null|mixed returns NULL if the attribute was not set
     */
    public function getAttribute( $name ) {
        if( isset( $this->attributes[$name] ) ) {
            return $this->attributes[$name];
        }
        else {
            return null;
        }
    }
}

使用magic functions

<?php
abstract class Item {
    private $id;

    private $name;

    protected $attributes = array();

    /**
     * @param $name The attribute key/name
     * @return null|mixed returns NULL if the attribute was not set
     */
    public function __get( $name ) {
        if( isset( $this->attributes[$name] ) ) {
            return $this->attributes[$name];
        }
        else {
            /* Trigger an error for unknown properties */
            $trace = debug_backtrace();
            trigger_error(
                'Undefined attribute: ' . $name .
                ' in ' . $trace[0]['file'] .
                ' line ' . $trace[0]['line'],
                E_USER_NOTICE);
            return null;
        }
    }
}

答案 1 :(得分:0)

我个人会在Item类中添加一个属性数组作为成员。最佳实践可以在这里找到:PHP5. Two ways of declaring an array as a class member

在数据库理论中,您需要此数据透视表遵循规范化原则,其中禁止嵌套关系。但是你不能在课堂之间的Php中有这个要求。

答案 2 :(得分:0)

基本阶级关系:

class Item
{
    private $id;
    private $name;

    public $attrs = array();

    public function addAttr(Attr &$attr) { $this->attrs[] = $attr; $attr->items[] = $this; }
    public function getAttrs() { return $this->attrs; }

    public function __construct($id, $name)
    {
        $this->id = $id;
        $this->name = $name;
    }
}

class Attr
{
    private $id;
    private $name;

    public $items = array();

    public function addItem(Item &$item) { $this->items[] = $item; $item->attrs[] = $attr; }
    public function getItems() { return $this->items; }

    public function __construct($id, $name)
    {
        $this->id = $id;
        $this->name = $name;
    }
}

$item1 = new Item(1, "I1");
$item2 = new Item(2, "I2");

$attr1 = new Attr(1, "A1");
$attr2 = new Attr(2, "A2");

$item1->addAttr($attr1);
$item1->addAttr($attr2);

var_dump($item1->getAttrs());
var_dump($attr1->getItems());

我建议使用ORM库。