실생활의 문제는 다음과 같은 데이터 모델로 추상화될 수 있습니다.
이 숫자의 합이 지정된 값이 되도록 배열에서 여러 숫자를 선택하세요.
대부분의 독자들은 온라인 쇼핑 경험이 있을 것입니다. 온라인 쇼핑에는 일반적으로 주문을 모으는 기능이 있습니다. 독자가 70위안짜리 제품을 구매했지만 무료 배송을 받으려면 구매 금액이 100위안을 초과해야 합니다. 일부 제품을 추천해 드립니다. 비용은 거의 100위안입니다.
시스템에서는 추천할 제품을 어떻게 결정하나요? 이것은 실제로 방금 언급한 모델입니다. 인기 있는 제품의 가격을 배열에 넣은 다음 알고리즘을 사용하여 배열의 어느 가격이 30위안이 되는지 알아낼 수 있습니다.
더 이상 고민하지 않고 Xiaocai가 알고리즘 구현의 JavaScript 버전을 여러분과 공유할 것입니다.
알고리즘 코드:
function getCombBySum(array,sum,tolerance,targetCount){ var util = { /* get combination from array arr: target array num: combination item length return: one array that contain combination arrays */ getCombination: function(arr, num) { var r=[]; (function f(t,a,n) { if (n==0) { return r.push(t); } for (var i=0,l=a.length; i<=l-n; i++) { f(t.concat(a[i]), a.slice(i+1), n-1); } })([],arr,num); return r; }, //take array index to a array getArrayIndex: function(array) { var i = 0, r = []; for(i = 0;i<array.length;i++){ r.push(i); } return r; } },logic = { //sort the array,then get what's we need init: function(array,sum) { //clone array var _array = array.concat(), r = [], i = 0; //sort by asc _array.sort(function(a,b){ return a - b; }); //get all number when it's less than or equal sum for(i = 0;i<_array.length;i++){ if(_array[i]<=sum){ r.push(_array[i]); }else{ break; } } return r; }, //important function core: function(array,sum,arrayIndex,count,r){ var i = 0, k = 0, combArray = [], _sum = 0, _cca = [], _cache = []; if(count == _returnMark){ return; } //get current count combination combArray = util.getCombination(arrayIndex,count); for(i = 0;i<combArray.length;i++){ _cca = combArray[i]; _sum = 0; _cache = []; //calculate the sum from combination for(k = 0;k<_cca.length;k++){ _sum += array[_cca[k]]; _cache.push(array[_cca[k]]); } if(Math.abs(_sum-sum) <= _tolerance){ r.push(_cache); } } logic.core(array,sum,arrayIndex,count-1,r); } }, r = [], _array = [], _targetCount = 0, _tolerance = 0, _returnMark = 0; //check data _targetCount = targetCount || _targetCount; _tolerance = tolerance || _tolerance; _array = logic.init(array,sum); if(_targetCount){ _returnMark = _targetCount-1; } logic.core(_array,sum,util.getArrayIndex(_array),(_targetCount || _array.length),r); return r; }
전화 안내:
배열: 데이터 소스 배열. 필수의.
sum: 합계가 추가되었습니다. 필수의.
관용: 관용. 이 매개변수를 지정하지 않으면 합계는 합계 매개변수와 같아야 합니다. 이 매개변수를 지정하면 결과가 허용 범위 내에서 변동될 수 있습니다. 선택 과목.
targetCount: 피연산자 수. 이 매개변수를 지정하지 않으면 가능한 모든 상황이 결과에 포함됩니다. 이 매개변수를 지정하면 고정된 숫자의 추가를 필터링할 수 있습니다. 3으로 지정하면 결과에 3개의 숫자만 추가됩니다. 선택 과목.
반환 값: 반환되는 것은 배열 구조 내의 배열입니다. 내부 배열의 요소는 피연산자이고 외부 배열의 요소는 모두 가능한 결과입니다.