如何归一化 table

How to normalize table

我想我应该先解释一下系统实际做了什么,以便更好地理解。

该系统是一个工资单查看器网站,其中上传者(hr 人员)以 excel 格式上传一堆工资单,这些条目将保存到数据库中。工资单查看器然后获取当前登录用户的 emp_id 并显示他们所有的 earnings, deductions, info 和他们的总数 earnings(all earnings are added), total deductions(all deductions are added) and netpay(total earning-total deduction).

我的问题是我的教授说我需要 "normalize" table 但我想知道我怎么可能将其标准化,因为我认为这是 "normalized"得到。但是,我确实尝试创建两个 erds,但我有几个问题:

  1. 当系统的重点只是读取上传者提供的内容时,为什么我要拆分收入和扣除额?
  2. 我的教授建议我得到对所有员工都相同的扣除额,但没有这样的事情,我能想到的最接近的是保险,它也在根据依赖性和其他影响因素而变化它。
  3. 如果我确实尝试创建 3 号,那么在费率发生变化时就会出现问题(即 2 月的保险 1 = 100 美元在 3 月变为 200 美元)。由于工资单查看器依赖于此 table,这意味着如果用户查看他 2 月份的工资单,他的保险也将是 200 美元。
  4. 我创建这个数据库是为了符合系统的要求,即上传者上传工资单的电子表格,难道这还不足以证明我的 erd 合理吗?也许如果这是一个工资单系统,我可以设置其他 tables 而不是影响工资单的输出但是基于系统,输出已经完成,hr 只需要将它们上传到数据库。

我的第一个 ERD:

我的第二个 ERD:

(我这样做是为了尝试规范化它,但出于系统的要求,我认为这不合适)

我猜你的教授不希望你有 30 个扣除字段。就像...当您设置 table 并发现自己在做:

object_typa_1 | object_typa_2 | object_typa_3 | object_typa_4 | object_typeb_1 | object_typeb_2 ..

并将值存储在各自的字段中。相反,你应该规范化,以防有一天你必须添加 deduction31 你不必做一个 ALTER TABLE 和 schluff 围绕你所有的 SQL 来适应。

改为:

Object Table:
type | number | value

你的情况:

employees:
emp_id | password | name | ...

payslips:
id | emp_id | other payslip attributes | ...


payslip_items:
payslip_id | type  | number | value

在 payslip_items table 中,您为每张工资单添加了多条记录。您在 type 字段中告诉它该项目是收入还是扣除。您说的是 number 字段中的收入或扣除额……可能不是最好的名字,但作为例子很好。然后 value 字段中 earning/deduction 的值。所以实际上你的 payslip_items table 每张工资单将有 34 条记录(30 条扣除和 4 条收入)...

你想这样做的原因是,在现实世界中,一旦你为 client/business 合作伙伴推出这个东西,他们就会想在工资单上添加新的扣除或收入(保证)。此架构之所以有效,是因为您不必更改 TABLE 并弄乱所有处理 payslip_items 的 sql。它会根据您的需要变大变小。

据我所知,你看起来很接近,你只需要将扣除和收入表的关系更改为一对多,并删除所有多余的 "earning" 和 "deduction" 列,留下以下内容:

通过这种方式,您可以根据需要拥有与工资单关联的任意多的收入记录和扣除记录。

我认为下面的 table 结构可以解决您的问题。

CREATE TABLE `Emp` (
    `id` int NOT NULL,
    `name` varchar(100) NOT NULL,
    `password` varchar(255) NOT NULL,
    `user_type` varchar NOT NULL,
    PRIMARY KEY (`id`)
);

CREATE TABLE `payslip_map` (
    `id` INT NOT NULL AUTO_INCREMENT,
    `emp_id` INT NOT NULL,
    `payslip_id` INT NOT NULL,
    PRIMARY KEY (`id`)
);

CREATE TABLE `payslips` (
    `id` INT NOT NULL,
    `particular_id` INT NOT NULL,
    `amt` FLOAT NOT NULL
);

CREATE TABLE `particulars` (
    `id` INT NOT NULL AUTO_INCREMENT,
    `particulars` varchar(80) NOT NULL UNIQUE,
    `is_earning` BOOLEAN NOT NULL,
    PRIMARY KEY (`id`)
);

ALTER TABLE `payslip_map` ADD CONSTRAINT `payslip_map_fk0` FOREIGN KEY (`emp_id`) REFERENCES `Emp`(`id`);

ALTER TABLE `payslip_map` ADD CONSTRAINT `payslip_map_fk1` FOREIGN KEY (`payslip_id`) REFERENCES `payslips`(`id`);

ALTER TABLE `payslips` ADD CONSTRAINT `payslips_fk0` FOREIGN KEY (`particular_id`) REFERENCES `particulars`(`id`);

视觉呈现