你们的数据库设计问题。我有一个表格(比如纸张类型),它有几个数据入口点。这种形式已经改变,预计会随着岁月而改变。它正在变成一个计算机应用程序,以便除其他外,我们可以放弃浪费纸张。 (还有一些小问题,比如将一个中央存储中的所有数据都可以查询,等等。)我想将所有表单数据存储在一个数据库中,并且对于这些更改是非常不可知的。
最初,我只是考虑每个字段都是一个字符串 - 我有一个像这样的表:
FormId int (FK)
FieldName nvarchar(64)
FieldValue nvarchar(128)
......类似的东西。它实际上是3NFy,因为FieldName在另一个表中,与一个人工密钥相关联,因此字段名称不会在整个地方重复。
但是,我想将其扩展为数字和下拉数据。我可以将数字数据存储为字符串,但这似乎是一个非常糟糕的想法。与下降相同。
我可以停止使用表,并实际使用主表单表上的列(上面引用的FormId的列),但这意味着为每个新项添加一个列,而旧表单只是null 。 (而且,除非我存储它,否则我不知道该列何时被创建。使用上面的字符串表,它是隐含的。)
我可以将上面的表格扩展为:
FormId int (FK)
FieldName nvarchar(64)
FieldValueType int -- enum as to which of the columns below are valid (or just let nulls imply that)
FieldValue nvarchar(128)
FieldValueInt int
Combos必须在OTLT(一个真正的查找表)中,我有所保留,但也许这里需要它?
有关StackOverflow的任何建议吗?我正在使用MSSQL,但这确实是一个更普遍的问题。
答案 0 :(得分:2)
使用Null。适当的数据库设计是一个复杂的主题;你可以做好参考并对整个事情做一些研究(我收集this是一本关于这个主题的好书)。一般来说,从单个表开始封装表单中的所有字段,然后将其放入规范化过程中,听起来就好了。是的,使用空值并且不要使用int来枚举哪些列设置为有效值;这正是空的原因。
答案 1 :(得分:2)
每种数据类型都可以有一个单独的表。
即。要获取整个表单,您需要使用表单ID进行N路连接,其中N是您支持的不同数据类型的数量(+可能是额外的,具体取决于您想要的信息 - 例如,下拉值可能会存储在另一个表中/你的fieldname lookup / etc.)
但设计应该也可能取决于你打算如何使用数据,你没有说过。而且还取决于这些形式的变化速度有多快。 。
答案 2 :(得分:1)
通过创建包含表单描述的表,您实际上是在定义元数据结构。那令人生畏。您需要大量正确的表描述所需的基础结构。我认为数据库系统的供应商在完成所有这些工作上花费了很多精力。
起初我想 - 这个好主意!构建自己的兼容性感知表描述系统!
但后来我想 - 我自己这样做太傻了。必须有一个能够做到这一点的数据库系统。
所以我得出结论,不是数据库专家,在新表单版本中为“新字段”定义正确的默认值。处理业务逻辑中的兼容性问题。
答案 3 :(得分:1)
我强烈建议不要像你描述的那样使用“通用表”。
您实际上是在重新构建关系数据库,这不是一个好主意:查询和更新对您的结构非常痛苦,如果您需要,您将无法使用更高级的功能,如外键和触发器它们。
只需创建一个包含数据字段列的表,如果表单没有字段,则将其设为null。
或者,甚至可能更好,有一个“基表”(每种形式的字段),并为更新的表单提供名称/版本号,并为此版本添加的新列提供一个新表,然后使用用于将这些新表连接到基表的合成PK。
即:
base table: id(numeric,PK), name, birthday, town
addresstable1: street, number, postal code, country, base_table_id (foreign key)
addresstable2: po box no, po box code, base_table_id (FK)
等等。
这样可以避免加载空字段;您的表格不是那么宽(总是可取的),并且您的记录是隐式版本的,因为具有属于基表中记录的记录的表列表会告诉您原始表单具有哪些字段,因此表单的格式是什么最初用的。