• 结合element-ui表格自动生成sku规格列表


    最近在写一个根据输入的规格,属性值动态生成sku表格,实现的效果大致如图,这是在vue项目里,结合element-UI表格写的,写好了就整理了一下,把代码贴上来,方便以后使用,不过代码里还是有一些重复的东西没整理,因为急着完成功能,也没太注意代码整洁,以后有时间再整理一下

    读取规格列表的功能是,如果你这次存了一个表格给后台,查看详情时,后台返回给你,你需要把它渲染到页面上用的,我这里写的比较复杂,因为用v-model绑定input,取值的时候要用对象取法,所以存进去的时候也是用的对象存放

    如果你只是要实现动态生成规格表的话,有这段代码就行了,可以生成3*2*2的组合

    /**
    * 递归生成规格列表
    * @param {*} skuarr 存储每一种排列组合的数组
    * @param {*} i 要用list数据的第几项作为基数,i为几,最后的结果就是以list[i]的数据开头,一般以第一项的值放在组合的第一位,如果要以其他属性开头,方法需要变动一下,有兴趣可以自己研究
    * @param {*} list 要生成排列的原始数据
    */
    var arr = []
    function func(skuarr=[], i, list){  
    for (let j=0; j<list[i].length; j++) {  
            if (i<list.length-1) {     // 演示一下第一次执行函数的结果
               skuarr[i] = list[i][j]  // skuarr[0] = ['黑色']  i=0, j=0
               func(skuarr, i+1, list)    // 执行递归 skuarr[1] = ['s']  i=1, j=0
             } else {
          // 拓展运算符合并数组 arr.push([...skuarr,list[i][j]]) // arr[0] = ['黑色','s','好'] i=2不符合if条件,执行else j=0 } }
    return arr }
    const list = [
      ['黑色','红色','白色'],
      ['S','M'],
      ['好','差']
    ]
    console.log(func([],0,list))
    // 打印的结果
    1. 0:(3) ["黑色", "S", "好"]
    2. 1:(3) ["黑色", "S", "差"]
    3. 2:(3) ["黑色", "M", "好"]
    4. 3:(3) ["黑色", "M", "差"]
    5. 4:(3) ["红色", "S", "好"]
    6. 5:(3) ["红色", "S", "差"]
    7. 6:(3) ["红色", "M", "好"]
    8. 7:(3) ["红色", "M", "差"]
    9. 8:(3) ["白色", "S", "好"]
    10. 9:(3) ["白色", "S", "差"]
    11. 10:(3) ["白色", "M", "好"]
    12. 11:(3) ["白色", "M", "差"]
     

    最近用数组的reduce方法时,想到了另一种实现笛卡尔积的方法,补充进来

    handleData () {
          // 测试的数据
          let arrs = [['红','黄', '蓝'], ['大', '中', '小']] // 如果你的数据类型是其他形式,需要转换成二维数组的格式再进行
    
          /**
           * 思路: 以第一项为基础,循环合并之后的每一项再循环的值
           * @param {*} acc 累计的值
           * @param {*} cur 当前遍历项
           * @param {*} index 当前遍历索引
           */ 
          let result = arrs.reduce((acc, cur, index) => {
            // 从第二项开始合并值
            if (index > 0) {
              let saveArr = []
              acc.forEach(item => {
                cur.forEach(subItem => {
                  saveArr.push(`${item},${subItem}`)
                })
              })
              acc = saveArr
            }
            return acc
          }, arrs[0]) // 把数组的第一项传入作为初始值
          console.log(result) //["红,大", "红,中", "红,小", "黄,大", "黄,中", "黄,小", "蓝,大", "蓝,中", "蓝,小"]
        }

    整个页面的代码,写得比较乱,见谅

    <template>
        <div>
            <div class="stand">
                <ul>
                    <li class="attr" v-for="(item,index) in standData" :key="index">
                        <span @click="remove(index)">删除:</span>
                        <el-input class="title" v-model="item.title" placeholder="请输入属性">:</el-input>
                        <div class="putt" v-if="item.attrs.length" v-for="(subitem,i) in item.attrs" :key="i">
                            <el-input v-model="subitem.attr" placeholder="请输入值"></el-input>
                            <div class="close" @click="closeAtrr(index,i)">×</div>
                        </div>
                        <div class="append" @click="addAtrr(index)">+</div>
                    </li>
                </ul>
                <div class="add">
                    <el-button type="primary" @click="addStand">添加规格</el-button>
                    <el-button type="primary" @click="getTable">生成规格列表</el-button>
                    <el-button type="primary" @click="read">读取规格列表</el-button>
    
                </div>
                
            </div>
            <div class="table">
                <el-table  v-if="isTable"
                :data="tableData"
                border
                style=" 100%">
                <el-table-column
                    prop="date"
                    label="属性"
                    width="180">
                </el-table-column>
                <el-table-column
                    prop="name"
                    label="价格1"
                    width="180">
                </el-table-column>
                <el-table-column
                    prop="address"
                    label="价格2">
                </el-table-column>
                </el-table>
            </div>
        </div>
    </template>
    <style>
        .table,.stand {
            padding: 40px;
        }
        .table {
            height: 500px;
        }
        .add {
            margin-top: 20px;
        }
        .attr {
            margin-bottom: 10px;
        }
        .el-input {
             auto;
            
        }
        .putt {
            display: inline-block;
            position: relative;
            margin-right: 10px;  
        }
        .append {
             40px;
            height: 40px;
            background-color: aqua;
            line-height: 40px;
            text-align: center;
            display: inline-block;
            font-size: 28px;
            cursor: pointer;
            vertical-align: middle;
        }
        .title {
            background-color: bisque;
            margin-right: 10px;
        }
        .close {
            position: absolute;
             15px;
            height: 15px;
            background-color: burlywood;
            border-radius: 50%;
            line-height: 15px;
            text-align: center;
            right: -5px;
            top: -5px;
        }
    </style>
    
    <script>
        export default {
          data() {
            return {
              tableData: [],
              input: '',
              isTable: false,
              standData: [],
              list: [],
              group: []
            }
          },
          created() {
              
          },
          methods: {
              // 添加规格行
              addStand (i) {
                //  限制规格种类不超过4种
                  if (this.standData.length>3) {
                      this.$message('不能超过四行')
                  } else {
                    this.standData.push({title: '', attrs: []})
                  }
              },
              // 添加规格表格
              getTable () {
                  this.isTable = true
                  this.tableData = []
                  this.group = []
                  this.list = []
                //   console.log(this.standData);
                  const num = this.standData.length
                  this.standData.forEach(item => {
                      this.list.push(item.attrs)
                  });
                //   console.log(this.list);
                 var arr = [] 
                 var that = this 
                 function func(skuarr=[], i){  
                    for (let j=0; j<that.list[i].length; j++) {  
                        if (i<that.list.length-1) {  
                            skuarr[i] = that.list[i][j].attr  
                            func(skuarr, i+1)  
                        } else {  
                            arr.push([...skuarr,that.list[i][j].attr])  
                        }  
                    }  
                    return arr  
                 }  
                 let newList = func([], 0)
                let b
                     newList.forEach(item => {
                         b = ''
                         for (let i = 0; i < num; i++) {
                            let a = this.standData[i].title
                            a = a + ':' + item[i]
                            b = b + a + ';'
                         }
                         this.group.push(b)
                     })
                 console.log(this.group)
                 let table = []
                 for (let j = 0; j < this.group.length; j++) {
                     table.push({
                         date: this.group[j],
                         name: '',
                         address: ''
                     })
                 }
                 this.tableData = table
              },
              
              // 删除规格行
              remove (i) {
                  this.standData.splice(i,1)
              },
              // 添加属性值
              addAtrr (i) {
                //  限制属性值不超过5个
                if (this.standData[i].attrs.length>4) {
                    this.$message('不能超过5个')
                 } else {
            // 存的时候是存的对象
    this.standData[i].attrs.push({attr: ''}) } }, // 删除属性值 closeAtrr (a, b) { // console.log(a, b); this.standData[a].attrs.splice(b,1) }, // 读取规格属性数组 read () {
          // 如果后台返回的数据是这样的 const arr
    = [ '颜色:红色;尺码:M;品质:好;', '颜色:红色;尺码:S;品质:好;', '颜色:白色;尺码:M;品质:好;', '颜色:白色;尺码:S;品质:好;' ] const a = arr[0].split(';') const num =a.length-1 let ss = [] for (let tt = 0; tt < num; tt++){ ss.push([]) } arr.forEach(item => { for (let tt = 0; tt < num; tt++){ ss[tt].push(item.split(';')[tt].split(':')[1]) } }) ss = ss.map(item => { return Array.from(new Set(item)) }) for (let s = 0; s < ss.length; s++) { for (let t = 0; t < ss[s].length; t++) { ss[s][t] = {attr:ss[s][t]} } } for (let i = 0; i < num; i++) { this.standData.push({'title': a[i].split(':')[0],attrs: ss[i]}) } console.log(this.standData); } } } </script>
  • 相关阅读:
    190. Reverse Bits
    150. Evaluate Reverse Polish Notation
    【UML】状态图与活动图
    【UML】类图与对象图
    【UML】用例图
    【运维】Dell R710如何开启VT服务
    【运维】Dell R710如何做Raid0与Raid5
    【运维】略谈Raid级别
    【VMware vSphere】VMware vSphere简单了解
    【Linux】在Linux上安装VNC
  • 原文地址:https://www.cnblogs.com/steamed-twisted-roll/p/9315502.html
Copyright © 2020-2023  润新知