如何为事务和主表选择主键?

时间:2014-06-03 18:39:26

标签: sql-server database foreign-keys primary-key entity-relationship

设计数据库时,例如假设我有名为SalaryTransEmployeeMasterAttendanceTrans的表。假设它的标准化为第3范式,表格字段如下...(仅显示相关的3个表格)

SalaryTrans (salary_id[pk], employee_id[fk], month, ..., net_salary )

EmployeeMaster (employee_id[pk], name, ...)

AttendanceTrans (attendance_id[pk], employee_id[fk], in_time, out_time, date)

注:

salary_idattendance_id是整数自动增量字段。

employee_id是一个类似“OA123”的字符串。

[pk] - 主键

[fk] - 外键

问题:

  1. 我是否正确选择了主键?
  2. 我是否应该为integer使用EmployeeMaster自动增量ID字段(使employee_id成为唯一但非主键)?
  3. 例如,在表SalaryTrans中,如果我将主键更改为[employee_id + month](因为此复合键将是唯一的,因为没有员工每个月可以获得两次工资)
  4. 对最佳做法和标准的任何建议?

1 个答案:

答案 0 :(得分:1)

这取决于表的目的。 SalaryTrans可以具有employee_ID的复合键,包括月份和年份。除非是为了减轻开发人员的负担,否则看起来很难获得Salary_ID字段。即使两个人有相同的工资,employeeID在桌面上的事实否定了两个不同的员工可以链接到同一记录的事实,因此salary_ID实际上不会是其他表的FK。所以复合键看起来很好。说我在X公司工作了10年。我10年的每一年的工资是否相同?我希望不是......

EmployeeMaster似乎有理由拥有一个名为employee_Id的PK。在这种情况下,字符串的工作方式与数字一样,只要它是唯一的而不是空的。我不认为添加自动编号会增加任何特殊内容。一个 SLIGHT 的性能提升,因为整数的处理速度比字符串快,但除非你是亚马逊,谷歌或重载网站,否则我现在怀疑它是否足够重要。

当出现晚上10点到早上6点之间的“日期”存储时,你会遇到出勤问题吗?此外,当人们没有键入或关闭时会发生什么...相当长或短时间。或者如果有人认真地投入25小时会发生什么?记录日期/时间和日期/时间会更好吗?

除此之外,这将有效......它可以。我没有看到任何无法在这里扩展的东西。我无法从这个设计中看到无法缩小的根本错误。我可能会做出一些不同的选择。

关于提出的问题:

好的,如果我将employee_id与月/年作为SalaryTrans表的主键,您是否建议删除自动编号字段salary_id或仅将其保留为唯一键?

我个人会删除它;但是,如果您计划在多个事务中经常使用这样的表而没有要引用的公共对象,那么添加保留主键和自动编号会使这些事务的开发变得更加困难。就个人而言,我更喜欢使用现有的领域;但我知道一些现有工具更喜欢1个关键列。如果您正在使用此类工具,请保留它。

通常在每张桌子上都有这样的字段是否有利? 仅当用于开发的工具要求密钥为1字段时。随着继任计划和其他人继承设计,它将使表格更容易理解。但是,请确保此字段不会由用户以任何方式维护或呈现或呈现。自然键对用户最有意义,因此我们应该向他们展示。代理键更易于系统开发/维护,因此开发人员可以/应该使用。然而,为了减少技术发言并简化与客户的沟通,我发现在开发中坚持使用自然键可以使管理要求更加轻松;虽然它使开发变得复杂一些。我个人宁愿让自己的工作更加努力,以减轻与客户群的沟通。

还请告诉我如何为AttendanceTrans表选择复合主键? employee_id + in_time_date会同时作为员工同时登录两次吗?或ID字段(自动编号)会比这更好吗?

Employee_ID + In_Time_date可以正常工作,也可以永不复制。