我应该将美国州存储为数组还是创建表格列?

时间:2013-08-27 18:06:14

标签: ruby ruby-on-rails-3 postgresql

我有一个应用程序,通过Product模型和表格存储产品数据。每个产品都有特定的状态可用性(多个状态),我将来需要过滤和/或搜索。我希望找到能告诉我存储这些数据最有效方法的人。在我看来,我有两种选择。

第一个是在我的表中简单地创建50个列,标题为每个州名并包含一个布尔值。然后,我可以按= "avail in California" if product.ca进行过滤。虽然这确实有效,但看起来有点麻烦,特别是在搜索多个状态可用时。

第二个选项是简单地有一列(“状态”)存储可用状态数组,然后按= "avail in California" if product.states.include? "CA"过滤。出于两个原因,这似乎是更好的解决方案。第一,它只允许更清洁的数据库表。其次,更重要的是,我可以通过简单地将用户的输入保存为变量(user_input)然后= "avail in California" if product.states.include? user_input来允许我的用户进行搜索。这个解决方案确实需要更多的工作,但是在DB中保存产品时,因为我不能简单地检查一个布尔值。

我认为备选方案2最有意义,但我希望就为什么或为什么不提供一些建议。我发现了一些类似的问题,但它们似乎并没有解释哪种解决方案会更好,只是如何解决这些问题。

我该怎么办?

2 个答案:

答案 0 :(得分:3)

除非你有充分的理由不这样做,否则你应该正常化,我在你的概述中没有看到。

要标准化,您应该有以下表格:

  1. product表,每个产品一条记录
  2. state表,每州一条记录
  3. product_state表,每个处于州的产品的一个条目
  4. product_state架构如下所示:

    (product_state_id PK, product_id FK, state_id FK)
    UNIQUE INDEX(product_id,state_id);
    

    这允许您将产品置于零个或多个状态。

答案 1 :(得分:0)

我认为,既然你在销售产品,你就会收税。州,县,市有不同的税。一些国家也有国家税。

因此,您需要将这些实体抽象为通用父级(通常称为GeopoliticalArea),以便您可以在任何子类型中指定单个外键(例如,来自税率表)。

create table geopolitical_area (
  id bigint primary key,
  type text not null
);

create table country (
  id bigint primary key references geopolitical_area(id),
  name text not null unique
);

-- represents states/provinces:
create table region (
  id bigint primary key references geopolitical_area(id),
  name text not null,
  country_id bigint references country(id),
  unique (name, country_id)
);
insert into geopolitical_area values 
(1, 'Country'),
(2, 'Region');

insert into country values 
(1, 'United States of America');

insert into region values 
(2, 'Alabama', 1);