笛卡尔积算法的sku
1.笛卡尔积在形式上比较容易理解,但作为按钮操作DOM的时候,我的思路大体还可以,有些偏差。看到这种矩行方阵,首先联想到二维数组,事实上这种方法完全可以实现,但是在性能和编码速度上都有弊端。
2.以下是代码
1 <!DOCTYPE html> 2 <html> 3 <head> 4 <meta charset="UTF-8"> 5 <title></title> 6 <style> 7 input{ 8 width: 50px; 9 height: 35px; 10 } 11 .checked{ 12 background: orange; 13 } 14 </style> 15 </head> 16 <body> 17 <div class="container"> 18 <div class="row"> 19 <input type="button" value="红" /> 20 <input type="button" value="黄" /> 21 <input type="button" value="蓝"/> 22 <input type="button" value="白"/> 23 <input type="button" value="军绿"/> 24 25 </div> 26 27 <div class="row"> 28 <input type="button" value="xl"/> 29 <input type="button" value="xxl"/> 30 <input type="button" value="xxxl"/> 31 </div> 32 33 <div class="row"> 34 <input type="button" value="纯棉"/> 35 <input type="button" value="牛仔"/> 36 <input type="button" value="针织"/> 37 </div> 38 39 <div class="row"> 40 <input type="button" value="A"/> 41 <input type="button" value="B"/> 42 <input type="button" value="C"/> 43 <input type="button" value="D"/> 44 <input type="button" value="E"/> 45 <input type="button" value="F"/> 46 <input type="button" value="H"/> 47 </div> 48 </div> 49 50 <div class="box"> 51 52 </div> 53 <script src="jquery-3.2.1.min.js"></script> 54 <script type="text/javascript"> 55 (function(){ 56 //两个数组的笛卡尔积 57 var Dicar = function(a,b){ 58 var ret=[]; 59 for(var i=0;i<a.length;i++){ 60 for(var j=0;j<b.length;j++){ 61 ret.push(multi(a[i],b[j])); 62 } 63 } 64 return ret; 65 } 66 var multi = function(a,b){ 67 if(!(a instanceof Array)) 68 a = [a]; 69 var ret = Array.call(null,a); 70 ret.push(b); 71 return ret; 72 } 73 //递归求笛卡尔最后结果 74 multiDicar = function(data){ 75 var len = data.length; 76 if(len == 0) { 77 return []; 78 }else if(len == 1){ 79 return data[0]; 80 }else{ 81 var r=data[0]; 82 for(var i=1;i<len;i++){ 83 var s = Dicar(r,data[i]) 84 if(s.length>0){ 85 r=s; 86 } 87 } 88 return r; 89 } 90 } 91 })(); 92 93 94 //给按钮添加选中取消标志 95 $(".container .row input").on("click",function(){ 96 $(this).toggleClass("checked"); 97 }); 98 99 100 (function(){ 101 //获取矩阵按钮 102 function getBtn(ele){ 103 var arr=[]; 104 var contain = $(ele); 105 for(let i=0;i<contain.length;i++){ 106 arr.push($.makeArray(contain[i].children)); 107 } 108 return arr; 109 } 110 //生成二维数组 111 var data = getBtn(".container .row"); 112 113 //判断点击的元素是否在二维数组中 114 function getIndex(ele,map){ 115 var res=[]; 116 for(let i=0;i<map.length;i++){ 117 for(let j=0;j<map[i].length;j++){ 118 if(map[i][j] == ele){ 119 res = [i,j]; 120 } 121 } 122 } 123 return res; 124 } 125 126 //生成结果二维数组 127 var checked=[]; 128 for(let i = 0;i<data.length;i++){ 129 checked[i] = []; 130 } 131 132 //处理结果二维数组中的断层 133 //如果有中间一行没数据,就截断阵列 134 function deal(checked){ 135 if(checked[0].length == 0){ 136 return [[]] 137 } 138 for(let i=0;i<checked.length;i++){ 139 if(checked[i].length == 0){ 140 return checked.slice(0,i); 141 } 142 } 143 return checked; 144 } 145 146 //删除数组的元素 147 function removeByValue(arr, val) { 148 for(var i=0; i<arr.length; i++) { 149 if(arr[i] == val) { 150 arr.splice(i, 1); 151 break; 152 } 153 } 154 } 155 156 //绑定点击事件 157 $(".container .row input").on("click",function(){ 158 $(".box").empty(); 159 var _this=$(this); 160 //判断在哪行那列 161 var res = getIndex(_this[0],data); 162 163 //判断是否是取消 164 //如果数据已经存在,就把它删除 ,bug在于按钮的文字不能重复 165 if(($.inArray(_this.val(),checked[res[0]])) !==-1){ 166 removeByValue(checked[res[0]],_this.val()); 167 }else{ 168 checked[res[0]].push(_this.val()); 169 } 170 //做笛卡尔积的结果 171 var r = multiDicar(deal(checked)); 172 for(var i=0;i<r.length;i++){ 173 $(".box").append("("+r[i]+")"+"<br>") 174 } 175 }) 176 })(); 177 </script> 178 </body> 179 </html>