计算属性实现电商规格选择的核心是解耦“用户选了什么”和“哪些还能选”,通过selectedspecs与skus两个响应式字段驱动availablesizes、availablecolors等计算属性动态禁用,再经matchedsku、iscompletelyselected、isinstock构成判断链验证有效性,大规模场景可引入邻接矩阵优化性能。

用计算属性实现电商规格选择,核心是把“用户选了什么”和“哪些还能选”这两件事彻底解耦——不靠事件手动更新状态,而是让 Vue 自动推导依赖关系。关键不在“算得快”,而在“逻辑清晰、响应及时、禁用准确”。
结构先行:两个响应式字段撑起整个逻辑
所有计算都基于两个稳定输入:
-
selectedSpecs:对象,记录当前已选的规格键值对,例如
{ color: '红色', size: 'L' } -
skus:数组,每个元素是完整 SKU 对象,含
specs(规格映射)、stock、price、id等字段
这两个字段必须是响应式的(Vue 2 的 data 或 Vue 3 的 ref/reactive),后续所有计算属性都只读取它们,不修改、不缓存中间态。
动态禁用:用计算属性替代暴力遍历
用户点一个颜色后,尺码列表要立刻过滤出仍有库存的组合。传统做法是每次点击都 filter + map + Set 全量 SKU,性能差且易错。正确方式是交给计算属性:
-
availableSizes():返回当前已选颜色下,所有有库存的尺码值去重列表 -
availableColors():同理,基于已选尺码反向推导可选颜色 - 每个计算属性只关注一个维度,彼此独立,但自动响应
selectedSpecs和skus的变化
这样既避免重复逻辑,又天然支持任意规格维度增减(加个“版本”字段?只需新增一个 availableVersions())。
组合有效性判断:三个计算属性串成判断链
用户点完所有规格,需立刻反馈能否下单。这个判断也应由计算属性完成:
-
matchedSku:遍历skus,找specs完全匹配selectedSpecs的项,返回第一个或null -
isCompletelySelected:检查selectedSpecs是否覆盖全部规格维度(如商品定义了颜色、尺码、版本三者必填) -
isInStock:仅当matchedSku存在且matchedSku.stock > 0时为true
这三个值可直接绑定按钮 :disabled、价格文案、库存提示,无需额外 watch 或方法调用。
高性能进阶:邻接矩阵替代笛卡尔积遍历
当规格维度多、SKU 数量大(如服装:5色×8码×3版型=120+ 组合),纯 filter 性能会明显下降。此时可引入邻接矩阵优化:
- 预处理阶段,将所有规格值(如“红色”“L”“经典版”)扁平化为顶点,构建
n × n邻接矩阵 - 矩阵中
matrix[i][j] === 1表示第 i 个值与第 j 个值可共存于某个有库存的 SKU 中 - 点击某规格值时,用
selected.every(s => matrix[vertexIndex[s]][vertexIndex[curr]] === 1)判断当前值是否可选
查询时间复杂度从 O(n²) 降至 O(m),m 是当前已选项数量,大幅提升交互流畅度。









