与大量不同表格的多对多关系

时间:2011-12-09 01:30:20

标签: mysql database doctrine-orm

我在开发一个数据库架构时遇到问题。目前,我的应用程序有一个用户表和另一个事件表。我可以轻松地设置多对多关系(使用第三个表)来保存有关哪些用户参加哪些事件的信息。

我的问题是,事件只是我的应用的一个功能。目标是让用户可以参与大量不同的程序,每个程序都需要自己的表。然而,我仍然需要能够调出用户注册的所有内容的列表。

现在,我正在考虑从每个事件表向用户提供单向关系。然后我需要创建一个自定义函数(在我的网站ORM中),它独立地查询每个表并组装一个完整的列表。我觉得这会很慢,所以我也很想创建一个单独的表,只列出用户注册的所有程序,并在那里存储我的应用程序运行所需的信息。这将在我的数据库中重复信息,并且通常听起来不是“干净”,但可能会更快。

有关处理此类关系的最佳方式的任何建议吗?

P.S。如果重要,我正在使用Doctrine2& Symfony2为我的网站供电。

3 个答案:

答案 0 :(得分:5)

在我的一个Web应用程序中,我使用了这种构造来存储任何以整数作为主键的表的注释:

CREATE TABLE Comments (
    Table VARCHAR(24) NOT NULL,
    RowID BIGINT NOT NULL,
    Comments VARCHAR(2000) NOT NULL,
    PRIMARY KEY (TABLE, RowID, COMMENTS)
);

就我而言(DB2,在Comments表中少于1000万行),它表现良好。 所以,将它应用到你的案例中:

CREATE TABLE Registration (
    Table VARCHAR(24) NOT NULL,
    RowID BIGINT NOT NULL,
    User <datatype> NOT NULL,
    Signup TIMESTAMP NOT NULL,
    PRIMARY KEY (TABLE, RowID, User)
);

因此,'Table'列标识包含程序的表(例如,'Events'表)。 'RowID'是该表中的主键(例如'Events'表中的条目的PK)。为了表现良好,这需要在所有目标表中使用相同数据类型的主键。

NoSQL解决方案很酷,但上面的模式适用于普通的旧关系数据库。

答案 1 :(得分:2)

这些要求他们拥有自己的桌子的事件类型有什么独特之处?

如果对象本质上是不同的,那么只使用所有事件共有的东西,使对象尽可能简单:...

public Event
{
    public Guid Id;
    public string Title;
    public DateTime Date;
    public string Type;
    public string TypeSpecificData; // serialized JSON/XML
}

// Not derived from Event, but built from it.
public SpecialEventType
{
    public Guid Id;
    // ... and the other common props from Event

    // some kind of special prop parsed from the Event's serialized data
    public string SpecialField; 
}

然后可以使用“类型特定数据”来存储有关不常见事件的详细信息(通常需要列或新表)...执行类似于序列化XML或JSON的操作

将表MTM映射到Users表,并按基本事件属性及其类型进行查询。

然后,您的代码负责使用其Type属性和与之关联的一些预定义XML架构来解析数据。

非常简单,让您的数据库保持干净,快速,最大限度地减少往返次数。这里的权衡是你没有能力向DB查询特定事件类型的细节......但对于具有成熟ORM层的大型扩展应用程序,性能权衡是值得的...

例如,现在您为特定类型的事件查询数据一次,从中构建伪派生类型,然后使用LINQ“查询”它们。

答案 2 :(得分:1)

除非您有大量类型的事件,否则从几个表中查询用户注册的事件不应该比从所有事件的一个长表中查询相同的事情慢得多。

我会采用这种方法,每个表或集合都有一个user_id字段,该字段映射回Users表。您不需要在ORM中真正创建单独的函数。如果每个事件类型都继承自事件类,那么您只需按user_id查找所有事件。