MySql中的规范化和表

MySql中的规范化和表,mysql,sql,sql-server,database,database-design,Mysql,Sql,Sql Server,Database,Database Design,我知道下面的问题可能是基于观点的,但是因为我正在创建我的第一个DBMS,所以我需要建议 我有一个包含以下列的订阅表: IDSubscription_PK, Date_Subscription, Cost_Subscription. 订阅费用根据订阅月份的不同而不同,例如->3个月:30美元,6个月:60美元等等,从1个月到12个月不等 知道我在追求第三范式,您是否建议我创建两个单独的表,如下所示: Subscription -> IDSubscription_PK, Date_Subsc

我知道下面的问题可能是基于观点的,但是因为我正在创建我的第一个DBMS,所以我需要建议

我有一个包含以下列的订阅表:

IDSubscription_PK, Date_Subscription, Cost_Subscription.
订阅费用根据订阅月份的不同而不同,例如->3个月:30美元,6个月:60美元等等,从1个月到12个月不等

知道我在追求第三范式,您是否建议我创建两个单独的表,如下所示:

Subscription -> IDSubscription_PK, Date_Subscription, Months_Subscription
Costs -> Months_Subscription, Cost
因此,我将:

SUBSCRIPTION_TABLE                |    COST_TABLE
IDSub.   Date.        Months.     |. Months.  Cost
2992.   2019/07/12.    1          |.  1.       10
9178.   2020/01/11.    10         |.  2.       20
1827.   2020/03/21.    7          |.  ...     ....
1928.   2020/11/10.    1          |.  12.      120
或者,改为单个,如下所示:

Subscription -> IDSubscription_PK, Date_Subscription, Date_end_Subscription, cost
因此:

SUBSCRIPTION_TABLE              
IDSub.   Date.        EndOfSub    Cost 
2992.   2019/07/12.   2019/08/12   10
9178.   2020/01/11.   2020/11/11   100    
1827.   2020/03/21.   2020/10/21   70   
1928.   2020/11/10.   2020/12/10   10       
我建议你加上成本表。为什么?

如果没有它,您将不得不对订阅表执行某种SELECT DISTINCT操作,以获取价目表。如果一些订户有独特的交易,这可能会产生垃圾。通常,如果您必须选择DISTINCT或类似的方法来获取所需的信息,这是非规范化的标志

更好的是,我建议用计划表代替成本表

它将包含这些类型的条目

plan_id   months  cost  description
   1        1      10   Monthly plan
   2        1       5   Monthly plan, student discount
   3       12     100   Yearly plan
   4       12      35   Yearly plan, student discount
这使您能够灵活地根据业务需要以表驱动而非逻辑驱动的方式更改价格

然后,您的订阅表将如下所示

subscription_id  plan_id subscriber_id renewal_date 
   1                1       101         2020-05-05
   2                4       103         2021-04-05
而且,很容易获得您的价目表:从计划中选择*

专业提示:避免在表和列的名称中混合使用大小写。当服务器托管在不同的操作系统上时,MySQL的区分大小写规则是不同的,您不希望现在或将来处理该问题。全小写:没问题


专业提示:通常为表中的实体命名表,如计划或订阅。然后,命名表plan\u id或subscription\u id或任意id的自动递增主键。当您在其他一些表中使用与FK相同的id时,请为其使用相同的任意id名称。这使将来必须阅读和维护SQL的人的生活更加轻松。

无论订阅表的详细信息如何,都需要将实际成本放入用户表中。明天,你可以改变价格。因此,您不应该让用户表指向订阅表

或者


订阅表可以有一个应用的天数范围。更改价格时,将向该表添加新行。新订阅或续订将链接到新行。但是这一模式实施起来很混乱;我更喜欢另一种方法。

在您的第一个想法中,什么类型和数据将包含月订阅?介于1和12之间的整数@Alejan请参见:很清楚,谢谢!我有两个问题:在subscription表中,subscription\u id代表什么?因为我看到了两个相等的数字和第二个:为什么计划表比我在示例中列出的成本表更受欢迎,因为没有学生折扣之类的东西,我会有12个不同的计划1个月,2个月…12个月。两个相同的订阅id值是我的错误。固定的谢谢你指出这一点。计划表不要求您拥有多个订阅计划,但它允许您拥有多个订阅计划。我认为用几个月作为成本指标没有多大意义。这根本不是很灵活。这是我运行一个真正的订阅服务的经验,每年收入约100万美元。因此,我可以创建两个表:CUSTOMER和PLAN,第三个表是关联实体,其主键是PlanID、CustomerID和Date?此外,日期应该是PK,因为同一客户可以多次订阅同一计划,所以也应该有日期作为标识符。您认为这是一个好的解决方案吗?或者,第三个表可能有一个特定的PK,例如,subscription ID,PlanID和customer ID作为外键。这个解决方案还是上一个?