我为一个网站设计了一个反馈系统,它有大约20个问题,但是这些问题可能每年都会发生变化,并试图考虑最好的设计。
最简单的方法是将每个问题映射到列中,但这需要每年创建一个新表,并更改根本不合理的应用程序代码。
第二个选项是将列与含义分开,并有一个应用含义的第二个表,即。

Table1: (row per survey)  Table2: (row per questionnaire type)
QuestionID                AnswerID
Question1                 QuestionID
Question2                 Answer1
...                       ....
Question20                Answer20

我能想到的第三个选择是完全分离每一个方面,比如:
Table1:       Table2:     Table3:       Table4:
QuestionID    AnswerID    MatchTableID  SetID
QuestionValue AnswerValue QuestionID    FeedbackSet
                          AnswerID      QuestionID

这给它带来了可伸缩性的好处,但是对于一年最多改变一次的几百条记录来说,这可能是过度的,我不确定这是否有点像实体属性值设计。
我非常感谢您对这里被认为是最佳实践和被认为是可接受实践的任何意见。

最佳答案

您可能只想保持它的简单性,并采用经典的关系设置。
模型:

class Question < ActiveRecord::Base
  has_many :replies
  has_many :answers
  belongs_to :questionnaire
end

class Answer < ActiveRecord::Base
  belongs_to :question
  has_many :replies
end

# A collection of questions
class Questionnaire < ActiveRecord::Base
  has_many :questions
  has_many :replies, through: :questions
end

# A user reply to a question
# acts as a many to many join table
class Reply < ActiveRecord::Base
  belongs_to :question
  belongs_to :answer
end

架构:
ActiveRecord::Schema.define(version: 20160215124045) do

  create_table "answers", force: :cascade do |t|
    t.text     "text"
    t.integer  "question_id"
    t.datetime "created_at",  null: false
    t.datetime "updated_at",  null: false
  end

  add_index "answers", ["question_id"], name: "index_answers_on_question_id"

  create_table "questionnaires", force: :cascade do |t|
    t.datetime "created_at", null: false
    t.datetime "updated_at", null: false
  end

  create_table "questions", force: :cascade do |t|
    t.text     "text"
    t.integer  "questionnaire_id"
    t.datetime "created_at",       null: false
    t.datetime "updated_at",       null: false
  end

  add_index "questions", ["questionnaire_id"], name: "index_questions_on_questionnaire_id"

  create_table "replies", force: :cascade do |t|
    t.integer  "question_id"
    t.integer  "answer_id"
    t.datetime "created_at",  null: false
    t.datetime "updated_at",  null: false
  end

  add_index "replies", ["answer_id"], name: "index_replies_on_answer_id"
  add_index "replies", ["question_id"], name: "index_replies_on_question_id"

end

是的,它有很多表,但是这给了你很大的灵活性,而不需要处理关键值表的麻烦。而且它的构建速度也比一些针对动态模式的黑客尝试快得多。
如果需要的话,它也很容易提取出指标。
这个例子有很多假设:
问题是多项选择题-不是写进去的。您可以通过将write-ins存储在replies表中来简单地调整它。
问题与问卷的关系是一对一的。使用联接表和habtm关系,如果需要能够重用多个问卷上的问题,则使用has_many through:

关于database - 何时分隔数据库列的含义(通用列),我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/35409428/

10-15 21:27