4. 数据模型设计:材料价格信息的数据结构
材料价格信息的数据结构是联动体系的数据基石。一个设计良好的数据结构,需要同时满足采集端(供应商报价、市场询价)的录入效率,以及消耗端(定额库匹配、造价计算)的查询精度。本节围绕核心字段展开设计,并给出标准化的数据模型。
4.1 核心字段定义与业务含义
材料价格信息表(t_material_price)包含以下 7 个核心字段,每个字段均对应明确的业务规则:
| 字段名称 | 数据类型 | 主键/约束 | 业务说明 |
|---|---|---|---|
| 材料编码 | VARCHAR(32) | PK, NOT NULL | 全局唯一标识,与定额库消耗量编码体系对齐 |
| 名称 | VARCHAR(120) | NOT NULL | 国标/行业标准名称,禁止使用俗称 |
| 规格 | VARCHAR(200) | NOT NULL | 包含型号、技术参数、等级,如“HRB400 Φ25” |
| 单位 | VARCHAR(10) | NOT NULL | 统一使用计量单位(t、m³、m、㎡、个) |
| 含税价 | DECIMAL(12,2) | DEFAULT 0.00 | 含增值税专用发票价格,元为单位 |
| 除税价 | DECIMAL(12,2) | DEFAULT 0.00 | 扣除增值税后的裸价,用于计价取费 |
| 供应商 | VARCHAR(100) | NOT NULL | 报价单位全称,支持多源比价 |
| 日期 | DATE | NOT NULL | 价格采集/报价生效日期,用于时间序列分析 |
设计要点:材料编码必须与定额库中的“材料编码”字段保持完全一致,这是实现“价格→消耗量”联动的唯一外键桥梁。建议采用“大类码+中类码+顺序码”的层级编码规则(如 010101001),避免使用自增ID。
4.2 数据模型 E-R 关系与物理表结构
材料价格信息表与定额消耗量表之间通过材料编码建立一对多关系。一个材料编码在定额库中可能对应多条消耗量记录(不同定额子目),但在价格表中,同一编码+同一供应商+同一日期只允许一条记录。
核心关联逻辑:
通过该关联,定额库中的每一条消耗量记录都能实时获取最新的含税价/除税价,实现动态调价。
t_quota_consumption.material_code = t_material_price.material_code通过该关联,定额库中的每一条消耗量记录都能实时获取最新的含税价/除税价,实现动态调价。
4.3 物理建表 SQL(MySQL 语法)
以下为材料价格信息表的完整建表语句,包含索引设计和注释:
-- 材料价格信息表
CREATE TABLE t_material_price (
material_code VARCHAR(32) NOT NULL COMMENT '材料编码(主键,与定额库对齐)',
name VARCHAR(120) NOT NULL COMMENT '材料名称(国标)',
specification VARCHAR(200) NOT NULL COMMENT '规格型号',
unit VARCHAR(10) NOT NULL COMMENT '计量单位',
price_tax_included DECIMAL(12,2) DEFAULT 0.00 COMMENT '含税价(元)',
price_tax_excluded DECIMAL(12,2) DEFAULT 0.00 COMMENT '除税价(元)',
supplier VARCHAR(100) NOT NULL COMMENT '供应商名称',
price_date DATE NOT NULL COMMENT '价格生效日期',
created_at DATETIME DEFAULT CURRENT_TIMESTAMP COMMENT '记录创建时间',
updated_at DATETIME DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP COMMENT '最后更新时间',
PRIMARY KEY (material_code, supplier, price_date),
INDEX idx_name (name),
INDEX idx_price_date (price_date)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='材料价格信息采集表';
注意:主键采用联合主键(material_code + supplier + price_date),确保同一供应商在同一天对同一材料只能有一条报价记录。如果业务允许同一供应商一天多次调价,建议增加自增ID作为逻辑主键,并将原联合字段改为唯一索引。
4.4 字段设计中的关键避坑点
- 编码长度预留:材料编码建议使用 VARCHAR(32),避免因编码规则扩展(如增加项目代号)导致截断。
- 含税价与除税价分离:不要只存含税价然后通过税率计算除税价。不同供应商、不同材料的税率可能不同(13%、9%、3%),且历史税率可能调整,必须分别存储原始值。
- 日期精度:使用 DATE 类型而非 DATETIME,因为价格通常以“天”为粒度生效。如果存在日内多次调价,可扩展为 DATETIME 并增加批次号。
- 供应商去重:供应商字段应关联供应商信息表(t_supplier),通过 supplier_id 外键关联,避免同一供应商名称录入不一致(如“XX建材有限公司” vs “XX建材”)。
4.5 数据模型扩展建议(进阶)
在实际生产环境中,建议在上述核心字段基础上增加以下辅助字段,以提升数据治理能力:
| 扩展字段 | 数据类型 | 说明 |
|---|---|---|
| 税率 (%) | DECIMAL(5,2) | 增值税税率,用于校验含税价与除税价的换算关系 |
| 价格来源 | VARCHAR(20) | 枚举值:供应商报价/信息价/市场询价/历史参考 |
| 数据状态 | TINYINT | 0=待审核,1=已生效,2=已作废 |
| 备注 | VARCHAR(500) | 价格异常说明、运输方式、付款条件等 |
最佳实践:建议将材料价格信息表设计为增量追加模式,即每次采集都新增一条记录,而非覆盖旧数据。这样既能保留完整的价格历史轨迹,又便于后续进行时间序列分析、价格趋势预测以及审计追溯。