在SQL中构建基于月份的数据

时间:2018-05-07 00:37:16

标签: sql postgresql

我很想知道在SQL数据库中构建数据的最佳方法是什么,我需要跟踪某些字段以及它们每月的差异。

例如,如果我有一个用户表,我试图存储3个不同的值:名称,电子邮件,以及他们每个月登录的次数。最佳做法是为每个月创建一个新列,并在该列下存储他们在该月登录的次数吗?或者每个月创建一个新的行/表会更好吗?

我的直觉说创建新列是减少冗余的最佳方法,但是当表中的列数随时间变化时,我可以看到它变得有点笨拙。 (我也在想,如果我按列进行,它将保证有一个total_column,可以一次跟踪所有月份。)

谢谢!

3 个答案:

答案 0 :(得分:1)

在我看来,最好的方法是为每个用户存储每个登录信息。

使用查询在查询时按照您需要的方式汇总数据。

如果总结细节并不符合性能要求,那么您应该只考虑其他结构 - 对于月度报告来说,这似乎并不那么繁重。

无论您做什么,将计数存储在单独的中都不是正确的做法。每个月,您都需要在表格中添加另一列。

答案 1 :(得分:0)

我不是专家,但在我看来,最好将数据存储在一个单独的表中(在您的情况下)。这样,您可以轻松地操作数据,并且您不必在将来修改表设计。

PK:UserID& Date或新列(例如:具有自动增量的RowNo)

+--------+------------+-----------+
| UserID |    Date    | NoOfTimes |
+--------+------------+-----------+
|     01 | 2018.01.01 |         1 |
|     01 | 2018.01.02 |         3 |
|     01 | 2018.01.03 |         5 |
|     .. |            |           |
|     02 | 2018.01.01 |         2 |
|     02 | 2018.01.02 |         6 |
+--------+------------+-----------+

或者

PK:UserIDYear& Month或新列(例如:具有自动增量的RowNo)

+--------+------+-------+-----------+
| UserID | Year | Month | NoOfTimes |
+--------+------+-------+-----------+
|     01 | 2018 | Jan   |        10 |
|     01 | 2018 | feb   |        13 |
+--------+------+-------+-----------+

在创建表之前,请先查看数据库规范化。特别是第1(1NF),第2(2NF)和第3(3NF)归一化形式。

答案 2 :(得分:0)

这两种方法都有效,具体取决于查询模式和连接要求。

  

每个月一行

对于用户,当月份的数据可用时,将插入包含月份登录计数的行。每个用户每月将有1行。此设计将使month列更容易进行连接。但是,需要访问多行以获取该年度用户的数据。

-- column list
name
email
month
login_count

-- example entries
'user1', 'user1@email.com','jan',100
'user2', 'user2@email.com','jan',65
'user1', 'user1@email.com','feb',90
'user2', 'user2@email.com','feb',75
  

所有月份的一行

您无需动态添加列,因为预先知道月数。最初可以创建表以适应所有月份。默认情况下,所有month_login_count列都将初始化为0.然后,该行将在填充月份的登录计数时更新。每个用户将有1行。这种设计不适合month进行连接。但是,只需要访问一行即可获取该年度用户的数据。

-- column list
name
email
jan_login_count
feb_login_count
mar_login_count
apr_login_count
may_login_count
jun_login_count
jul_login_count
aug_login_count
sep_login_count
oct_login_count
nov_login_count
dec_login_count

-- example entries
'user1','user1@email.com',100,90,0,0,0,0,0,0,0,0,0,0
'user2','user2@email.com',65,75,0,0,0,0,0,0,0,0,0,0