商品表怎么建才够用又不冗余
核心是抓住「商品」本身的关键属性,别一上来就加库存、分类、图片字段堆砌。先确保
id(主键)、
name(名称)、
price(售价)、
status(上下架状态,用 TINYINT 或 ENUM)这四个字段存在。分类别硬编码进商品表,改用外键关联独立的
categories表;图片路径统一存为字符串(如
image_url),别存二进制;库存如果涉及多仓库或秒杀,就单独拆出
inventory表,初期单仓直接放商品表里加
stock字段也行。
分类和商品一对多关系怎么写外键
必须显式定义外键约束,否则数据一致性靠人肉维护迟早出错。建分类表时主键用
id,商品表里加字段
category_id,然后执行:
ALTER TABLE products ADD CONSTRAINT fk_category FOREIGN KEY (category_id) REFERENCES categories(id) ON DELETE SET NULL;
注意三点:
•
categories.id必须是索引(通常是主键,自动有)
•
products.category_id自己也要手动加索引,否则 JOIN 慢
•
ON DELETE SET NULL比
CASCADE更安全,删分类不会误删商品
查商品+分类名一条 SQL 怎么写不翻车
用 LEFT JOIN 而不是 INNER JOIN,避免没分类的商品被漏掉:
SELECT p.id, p.name, p.price, c.name AS category_name FROM products p LEFT JOIN categories c ON p.category_id = c.id WHERE p.status = 1;
常见错误:
• 忘记给
c.name起别名,导致 PHP/Python 取字段时和
p.name冲突
• 在 WHERE 里写
c.name IS NOT NULL,把 LEFT JOIN 变相变成 INNER JOIN
• 没加
p.status = 1条件,查出一堆已下架商品
批量插入商品时主键冲突或乱序怎么办
用
INSERT IGNORE或
ON DUPLICATE KEY UPDATE,别用普通 INSERT 然后靠代码捕获异常再处理:
INSERT INTO products (name, price, category_id) VALUES ('iPhone 15', 5999, 1), ('MacBook Air', 8999, 2) ON DUPLICATE KEY UPDATE price = VALUES(price);
关键点:
• 表必须有唯一约束(比如
UNIQUE KEY(name)或联合唯一)才能触发重复逻辑
•
VALUES(price)指的是本次 INSERT 语句中对应位置的值,不是原记录值
• 如果主键是自增 ID,重复时不会更新 ID,只更新指定字段 实际跑起来你会发现,最麻烦的不是建表,而是前端传参格式和后端校验没对齐——比如价格传了字符串 "5999.00" 进来,MySQL 存成 5999,但展示时又要求保留两位小数,这种细节比外键还容易漏。
