【问题标题】:Database structure for "customer" table having many orders per customer and many items per order“客户”表的数据库结构,每个客户有很多订单,每个订单有很多商品
【发布时间】:2013-07-16 16:29:20
【问题描述】:

我正在尝试创建一个数据库,其中每个客户都有几个订单(每天都有新订单),每个订单都有几个项目。我计划创建一个客户表并为每个订单创建一个表,并用“项目”表填充该表。我认为这种方法过于复杂和繁琐,因为订单数量可以达到数千,我认为拥有数千张表是不可维护的。你认为什么是合适的结构?非常感谢任何帮助。

对不起,如果这是一个愚蠢的问题,我正在学习编程。这是我第一次尝试数据库设计。

【问题讨论】:

  • 如果您是初学者,您可能应该首先尝试设置ERM。其他一切都应该从中派生出来。
  • 把表格想象成你存储相似类型事物的地方,订单属于一个表格,因为每个订单都会保存相同类型的信息。如果你发现自己认为你会有多个具有相同结构的表,你应该停下来想想你的设计。有很多很好的资源和示例,寻找'sample order database'或'sample db schema'。
  • @GoatCO 感谢您提供关于不该做什么的提示!是的,我真的认为每个订单都有一张桌子的想法非常糟糕,但这是我想到的最好的想法之一。

标签: sql database sqlite


【解决方案1】:

您需要四个表,如下所示:

客户

包含客户列表。每个客户一行。将包含所有客户的信息 - 他们的联系方式等...

订单

包含订单列表。每个订单一行。每个订单都由客户下达,并有一个Customer_ID - 可用于链接回客户记录。如果与客户记录中的地址不同,还可以存储送货地址 - 或将地址存储在单独的表中。

订单项

包含订单项目列表。订单上的每个项目都有一行 - 因此每个订单可以在此表中生成多行。订购的每件商品都是您库存中的产品,因此每一行都有一个 product_id,它链接到 products 表。

产品

包含产品列表。每个产品一行。类似于客户表,但对于产品 - 包含所有产品详细信息。

这是您可以用来创建此结构的 SQL 代码 - 它将为自己创建一个名为 mydb 的数据库:

CREATE SCHEMA IF NOT EXISTS `mydb` DEFAULT CHARACTER SET utf8 COLLATE utf8_general_ci ;
USE `mydb` ;

-- -----------------------------------------------------
-- Table `mydb`.`Customers`
-- -----------------------------------------------------
CREATE  TABLE IF NOT EXISTS `mydb`.`Customers` (
  `ID` INT NOT NULL ,
  `Name` TEXT NOT NULL ,
  `PhoneNo` VARCHAR(45) NULL ,
  PRIMARY KEY (`ID`) )
ENGINE = InnoDB;


-- -----------------------------------------------------
-- Table `mydb`.`Orders`
-- -----------------------------------------------------
CREATE  TABLE IF NOT EXISTS `mydb`.`Orders` (
  `ID` INT NOT NULL ,
  `customer_id` INT NULL ,
  PRIMARY KEY (`ID`) ,
  INDEX `fk_Order_1_idx` (`customer_id` ASC) ,
  CONSTRAINT `fk_Order_1`
    FOREIGN KEY (`customer_id` )
    REFERENCES `mydb`.`Customers` (`ID` )
    ON DELETE NO ACTION
    ON UPDATE NO ACTION)
ENGINE = InnoDB;


-- -----------------------------------------------------
-- Table `mydb`.`Products`
-- -----------------------------------------------------
CREATE  TABLE IF NOT EXISTS `mydb`.`Products` (
  `ID` INT NOT NULL ,
  `Name` VARCHAR(45) NOT NULL ,
  `Description` TEXT NULL ,
  PRIMARY KEY (`ID`) )
ENGINE = InnoDB;


-- -----------------------------------------------------
-- Table `mydb`.`OrderItems`
-- -----------------------------------------------------
CREATE  TABLE IF NOT EXISTS `mydb`.`OrderItems` (
  `ID` INT NOT NULL ,
  `Order_ID` INT NOT NULL ,
  `Product_ID` INT NOT NULL ,
  `Quantity` INT NOT NULL ,
  PRIMARY KEY (`ID`) ,
  INDEX `fk_OrderItem_1_idx` (`Order_ID` ASC) ,
  INDEX `fk_OrderItem_2_idx` (`Product_ID` ASC) ,
  CONSTRAINT `fk_OrderItem_1`
    FOREIGN KEY (`Order_ID` )
    REFERENCES `mydb`.`Orders` (`ID` )
    ON DELETE NO ACTION
    ON UPDATE NO ACTION,
  CONSTRAINT `fk_OrderItem_2`
    FOREIGN KEY (`Product_ID` )
    REFERENCES `mydb`.`Products` (`ID` )
    ON DELETE NO ACTION
    ON UPDATE NO ACTION)
ENGINE = InnoDB;

USE `mydb` ;

【讨论】:

  • @HartCO 这和答案中的 Product 表不是一回事吗?
  • 请问是用什么工具来可视化这个的?
  • @Robin 是mysql自带的标准东西,不知道叫什么。这是一个可选下载,但可以从同一个地方获得。
  • @bteague 添加一个支付表就差不多了。一个名为payments 的表,其中包含IDcustomer_idorder_id(如果您想将付款与订单联系起来)、amount - 以及您想要收集的任何其他信息付款。
  • 想补充一点,Order 是一个保留字。因此,如果有人决定借用它并尝试与表交互,他们需要使用反引号,否则 mysql 将返回错误。例如desc Order 会失败,但desc `Order` 不会。
【解决方案2】:

为每个订单创建一个表是没有意义的。不要那样做。它不实用,不可维护。您将无法正常查询您的数据。对于初学者来说,你只需要四个这样的表

  • 客户
  • 订单
  • order_items
  • 产品(或物品)

这里是过于简单的SQLFiddle演示

【讨论】:

  • 一个问题(我对关系数据库了解不多):如果我们必须搜索特定客户的订单。我们必须扫描整个订单表吗?
  • 如果您在订单表中的客户列上有索引,则不需要。
  • 明白了。刚刚了解索引。
【解决方案3】:

我会有一个客户表以及订单和项目表。客户的主键是订单的外键。然后,项目将有一个与放置它的顺序相匹配的外键。

3张桌子应该没问题

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-07-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多