JavaScript实现从数组中选出和等于固定值的n个数


Posted in Javascript onSeptember 03, 2014

现实生活中的问题,可能会抽象为这样一种数据模型:

从一个数组中挑选出几个数,让这几个数相加的和为指定的值。

大多数读者应该有过网购的经历,网购一般会有个凑单功能,假如读者买了70元的商品,但是必须满100元才能包邮,这时系统会自动推荐一些商品,加起来差不多就100块钱了。

系统如何确定推荐哪些商品呢?这其实就是刚刚提到的模型,我们可以把热销商品的价格放到一个数组中,然后利用算法,找出数组中哪些价格的和为30元。

废话少说,小菜给大家分享一个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;
}

调用说明:

array: 数据源数组。必选。

sum: 相加的和。必选。

tolerance: 容差。如果不指定此参数,则相加的和必须等于sum参数,指定此参数可以使结果在容差范围内浮动。可选。

targetCount: 操作数数量。如果不指定此参数,则结果包含所有可能的情况,指定此参数可以筛选出固定数量的数相加,假如指定为3,那么结果只包含三个数相加的情况。可选。

返回值:返回的是数组套数组结构,内层数组中的元素是操作数,外层数组中的元素是所有可能的结果。

Javascript 相关文章推荐
javascript下arguments,caller,callee,call,apply示例及理解
Dec 24 Javascript
JQuery学习笔录 简单的JQuery
Apr 09 Javascript
js判断iframe内的网页是否滚动到底部触发事件
Mar 18 Javascript
微信小程序  wx.request合法域名配置详解
Nov 23 Javascript
微信小程序 欢迎界面开发的实例详解
Nov 30 Javascript
详解vue-cli + webpack 多页面实例应用
Apr 25 Javascript
解决html input验证只能输入数字,不能输入其他的问题
Jul 21 Javascript
详解Vue中一种简易路由传参办法
Sep 15 Javascript
详解ES6之async+await 同步/异步方案
Sep 19 Javascript
深入理解基于vue-cli的webpack打包优化实践及探索
Oct 14 Javascript
详解Vue中的MVVM原理和实现方法
Jul 15 Javascript
JavaScript常用进制转换及位运算实例解析
Oct 14 Javascript
JavaScript实现找出数组中最长的连续数字序列
Sep 03 #Javascript
js实现的类似于asp数据字典的数据类型代码实例
Sep 03 #Javascript
jQuery表格列宽可拖拽改变且兼容firfox
Sep 03 #Javascript
Egret引擎开发指南之视觉编程
Sep 03 #Javascript
Egret引擎开发指南之发布项目
Sep 03 #Javascript
Egret引擎开发指南之运行项目
Sep 03 #Javascript
JavaScript实现找出字符串中第一个不重复的字符
Sep 03 #Javascript
You might like
php 分页类 扩展代码
2009/06/11 PHP
CodeIgniter扩展核心类实例详解
2016/01/20 PHP
Zend Framework教程之模型Model用法简单实例
2016/03/04 PHP
phpcmsv9.0任意文件上传漏洞解析
2020/10/20 PHP
JScript 脚本实现文件下载 一般用于下载木马
2009/10/29 Javascript
IE8的JavaScript点击事件(onclick)不兼容的解决方法
2013/11/22 Javascript
JavaScript代码编写中各种各样的坑和填坑方法
2014/06/06 Javascript
基于JavaScript实现单选框下拉菜单添加文件效果
2016/06/26 Javascript
js无法获取到html标签的属性的解决方法
2016/07/26 Javascript
js实现String.Fomat的实例代码
2016/09/02 Javascript
详解能在多种前端框架下使用的表格控件
2017/01/11 Javascript
JavaScript 数组的进化与性能分析
2017/09/18 Javascript
vue实现文章内容过长点击阅读全文功能的实例
2017/12/28 Javascript
Node.js使用MySQL连接池的方法实例
2018/02/11 Javascript
JS实现图片旋转动画效果封装与使用示例
2018/07/09 Javascript
实例详解ztree在vue项目中使用并且带有搜索功能
2018/08/24 Javascript
微信小程序实现的绘制table表格功能示例
2019/04/26 Javascript
JavaScript动态检测密码强度原理及实现方法详解
2019/06/11 Javascript
vue中echarts的用法及与elementui-select的协同绑定操作
2020/11/17 Vue.js
[05:41]2014DOTA2西雅图国际邀请赛 小组赛7月10日TOPPLAY
2014/07/10 DOTA
[16:19]教你分分钟做大人——风暴之灵
2015/03/11 DOTA
[23:18]Spirit vs Liquid Supermajor小组赛A组 BO3 第二场 6.2
2018/06/03 DOTA
python数据结构链表之单向链表(实例讲解)
2017/07/25 Python
如何关掉pycharm中的python console(图解)
2019/10/31 Python
Python如何使用字符打印照片
2020/01/03 Python
pyqt5数据库使用详细教程(打包解决方案)
2020/03/25 Python
HTML5头部标签的一些常用信息小结
2016/10/23 HTML / CSS
HTML5 canvas实现的静态循环滚动播放弹幕
2021/01/05 HTML / CSS
《童年的发现》教学反思
2014/02/14 职场文书
中班开学寄语
2014/04/04 职场文书
医院安全生产月活动总结
2014/07/05 职场文书
交通安全横幅标语
2014/10/07 职场文书
2014年招商引资工作总结
2014/11/22 职场文书
初中英语教师个人工作总结2015
2015/07/21 职场文书
2016年优秀少先队员事迹材料
2016/02/26 职场文书
如何设计高效合理的MySQL查询语句
2021/05/26 MySQL