基于JavaScript实现前端数据多条件筛选功能


Posted in Javascript onAugust 19, 2020

有时候也会需要在前端进行数据筛选,增强交互体验。当数据可用的筛选条件较多时,把逻辑写死会给后期维护带来很大麻烦。下面是我自己写的一个简单的筛选器,筛选条件可以根据数据包含的字段动态设置。

仿照京东的筛选条件,这里就取价格区间和品牌作为测试。

基于JavaScript实现前端数据多条件筛选功能

代码

代码中主要使用js的过滤器Array.prototype.filter,该方法会对数组元素进行遍历检查,返回一个符合检查条件的新数组,不会改变原数组。

// filter()
var foo = [0,1,2,3,4,5,6,7,8,9];

var foo1 = foo.filter(
 function(item) {
 return item >= 5
 }
);

console.log(foo1); // [5, 6, 7, 8, 9]

有了这个方法,筛选数据方便了很多,下面先定义一个商品类。

// 定义商品类
function Product(name, brand, price) {
 this.name = name; // 名称
 this.brand = brand; // 品牌
 this.price = price; // 价格
}

创建一个过滤器对象,把所有过滤数据的方法放在里面。为了能自动适配不同的筛选条件,将筛选条件分为两个大类,一个是区间类型rangesFilter ,如:品牌、内存等;一个是选择类型choosesFilter,如:价格、屏幕尺寸等。

不同大类同时筛选时,进行的是与逻辑,每个大类在上一个大类筛选结果上进行筛选。比如我要筛选2000-5000块的华为手机,先调用rangesFilter筛选products并返回结果result1,然后用choosesFilter筛选result1并返回结果resulte2。

当然,如果还有其它大类,不一定是与逻辑,再另行处理。

// 商品筛选器
const ProductFilters = {
 /**
 * 区间类型筛选
 * @param {array<Product>} products
 * @param {array<{type: String, low: number, high: number}>} ranges
 */
 rangesFilter: function (products, ranges) { }

 /**
 * 选择类型筛选
 * @param {array<Product>} products
 * @param {array<{type: String, value: String}>} chooses
 */
 choosesFilter: function (products, chooses) { }
}

区间类型的筛选,代码如下。

// 区间类型条件结构
ranges: [
 {
  type: 'price', // 筛选类型/字段
  low: 3000, // 最小值
  high: 6000 // 最大值
 }
 ]
/**
 * @param {array<Product>} products
 * @param {array<{type: String, low: number, high: number}>} ranges
 */
 rangesFilter: function (products, ranges) {
 if (ranges.length === 0) {
  return products;
 } else {
  /**
  * 循环多个区间条件,
  * 每种区间类型应该只有一个,
  * 比如价格区间不会有1000-2000和4000-6000同时需要的情况
  */
  for (let range of ranges) {
  // 多个不同类型区间是与逻辑,可以直接赋值给自身
  products = products.filter(function (item) {
   return item[range.type] >= range.low && item[range.type] <= range.high;
  });
  }
  return products;
 }
 }

选择类型筛选:

// 选择类型条件结构
chooses: [
 {
  type: 'brand',
  value: '华为'
 },
 {
  type: 'brand',
  value: '苹果'
 }
 ]
/**
 * @param {array<Product>} products
 * @param {array<{type: String, value: String}>} chooses
 */
 choosesFilter: function (products, chooses) {
 let tmpProducts = [];
 if (chooses.length === 0) {
  tmpProducts = products;
 } else {
  /**
  * 选择类型条件是或逻辑,使用数组连接concat
  */
  for (let choice of chooses) {
  tmpProducts = tmpProducts.concat(products.filter(function (item) {
   return item[choice.type].indexOf(choice.value) !== -1;
  }));
  }
 }
 return tmpProducts;
 }

定义一个执行函数doFilter()。

function doFilter(products, conditions) {
 // 根据条件循环调用筛选器里的方法
 for (key in conditions) {
 // 判断是否有需要的过滤方法
 if (ProductFilters.hasOwnProperty(key + 'Filter') && typeof ProductFilters[key + 'Filter'] === 'function') {
  products = ProductFilters[key + 'Filter'](products, Conditions[key]);
 }
 }
 return products;
}
// 将两种大类的筛选条件放在同一个对象里
let Conditions = {
 ranges: [
 {
  type: 'price',
  low: 3000,
  high: 6000
 }
 ],
 chooses: [
 {
  type: 'brand',
  value: '华为'
 }
 ]
}

测试

创建10个商品数据,以及筛选条件

// 商品数组
const products = [
 new Product('华为荣耀9', '华为', 2299),
 new Product('华为P10', '华为', 3488),
 new Product('小米MIX2', '小米', 3599),
 new Product('小米6', '小米', 2499),
 new Product('小米Note3', '小米', 2499),
 new Product('iPhone7 32G', '苹果', 4588),
 new Product('iPhone7 Plus 128G', '苹果', 6388),
 new Product('iPhone8', '苹果', 5888),
 new Product('三星Galaxy S8', '三星', 5688),
 new Product('三星Galaxy S7 edge', '三星', 3399),
];
// 筛选条件
let Conditions = {
 ranges: [
 {
  type: 'price',
  low: 3000,
  high: 6000
 }
 ],
 chooses: [
 {
  type: 'brand',
  value: '华为'
 },
 {
  type: 'brand',
  value: '苹果'
 }
 ]
}

调用函数

let result = doFilter(products, Conditions);
console.log(result);

输出

基于JavaScript实现前端数据多条件筛选功能

代码的扩展性和可维护性都很好,只要保证筛选条件中的type字段在商品数据中一致都可以筛选,比如将筛选条件改为

let Conditions = {
 ranges: [
 {
  type: 'price',
  low: 3000,
  high: 6000
 }
 ],
 chooses: [
 {
  type: 'name',
  value: 'iPhone'
 }
 ]
}

输出

基于JavaScript实现前端数据多条件筛选功能

搜索匹配等一些地方也需要优化,是否区分大小写、是完全匹配还是模糊匹配等。

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
IE6弹出“已终止操作”的解决办法
Nov 27 Javascript
javascript遍历控件实例详细解析
Jan 10 Javascript
js document.write()使用介绍
Feb 21 Javascript
js兼容火狐获取图片宽和高的方法
May 21 Javascript
JavaScript DOM 学习总结(五)
Nov 24 Javascript
JS实现环形进度条(从0到100%)效果
Jul 05 Javascript
老生常谈javascript变量的命名规范和注释
Sep 29 Javascript
Javascript Promise用法详解
May 10 Javascript
对angular2中的ngfor和ngif指令嵌套实例讲解
Sep 12 Javascript
layui点击数据表格添加或删除一行的例子
Sep 12 Javascript
node.js使用mongoose操作数据库实现购物车的增、删、改、查功能示例
Dec 23 Javascript
JS实现拖拽元素时与另一元素碰撞检测
Aug 27 Javascript
javascript 开发之网页兼容各种浏览器
Sep 28 #Javascript
JavaScript中重名的函数与对象示例详析
Sep 28 #Javascript
js 开发之autocomplete=&quot;off&quot;在chrom中失效的解决办法
Sep 28 #Javascript
微信小程序下拉刷新界面的实现
Sep 28 #Javascript
详解Vuex中mapState的具体用法
Sep 28 #Javascript
Node.js学习之地址解析模块URL的使用详解
Sep 28 #Javascript
javascript基于牛顿迭代法实现求浮点数的平方根【递归原理】
Sep 28 #Javascript
You might like
PHP4引用文件语句的对比
2006/10/09 PHP
说说PHP的autoLoad自动加载机制
2012/09/27 PHP
php按百分比生成缩略图的代码分享
2014/05/10 PHP
使用CodeIgniter的类库做图片上传
2014/06/12 PHP
PHP文件读写操作相关函数总结
2014/11/18 PHP
php将字符串全部转换成大写或者小写的方法
2015/03/17 PHP
Mac版PhpStorm之XAMPP整合apache服务器配置的图文教程详解
2016/10/13 PHP
uploadify 3.0 详细使用说明
2012/06/18 Javascript
jQuery ajax dataType值为text json探索分享
2013/09/23 Javascript
JS执行删除前的判断代码
2014/02/18 Javascript
jQuery打印指定区域Html页面并自动分页
2014/07/04 Javascript
AngularJS + Node.js + MongoDB开发的基于高德地图位置的通讯录
2015/01/02 Javascript
微信JSSDK上传图片
2015/08/23 Javascript
jQuery图片轮播(二)利用构造函数和原型创建对象以实现继承
2016/12/06 Javascript
JS实现获取来自百度,Google,soso,sogou关键词的方法
2016/12/21 Javascript
jQuery Form表单取值的方法
2017/01/11 Javascript
js面向对象编程总结
2017/02/16 Javascript
使用pkg打包Node.js应用的方法步骤
2018/10/19 Javascript
Vue 中可以定义组件模版的几种方式
2019/08/06 Javascript
快速对接payjq的个人微信支付接口过程解析
2019/08/15 Javascript
[43:32]Winstrike vs VGJ.S 2018国际邀请赛淘汰赛BO3 第一场 8.23
2018/08/24 DOTA
Python使用pymysql小技巧
2017/06/04 Python
numpy排序与集合运算用法示例
2017/12/15 Python
pycharm恢复默认设置或者是替换pycharm的解释器实例
2018/10/29 Python
python命名空间(namespace)简单介绍
2019/08/10 Python
HTML5+CSS3实现机器猫
2016/10/17 HTML / CSS
初中生学习生活的自我评价
2013/11/20 职场文书
建筑专业毕业生推荐信
2013/11/21 职场文书
高中军训广播稿
2014/01/14 职场文书
自我工作评价范文
2015/03/06 职场文书
公司行政管理制度范本
2015/08/05 职场文书
中国梦党课学习心得体会
2016/01/05 职场文书
Python机器学习算法之决策树算法的实现与优缺点
2021/05/13 Python
vue实现可拖拽的dialog弹框
2021/05/13 Vue.js
Golang生成Excel文档的方法步骤
2021/06/09 Golang
python游戏开发之pygame实现接球小游戏
2022/04/22 Python