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

仿照京东的筛选条件,这里就取价格区间和品牌作为测试。进行商品按条件筛选主要是利用Arrary.prototype.filter对数组元素进行遍历检查,返回一个符合检查条件的新数组,不会改变原数组。

首先定义一个商品类:

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

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

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

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

  1. // 商品筛选器
  2. const ProductFilters = {
  3. /**
  4. * 区间类型筛选
  5. * @param {array<Product>} products
  6. * @param {array<{type: String, low: number, high: number}>} ranges
  7. */
  8. rangesFilter: function (products, ranges) { }
  9.  
  10. /**
  11. * 选择类型筛选
  12. * @param {array<Product>} products
  13. * @param {array<{type: String, value: String}>} chooses
  14. */
  15. choosesFilter: function (products, chooses) { }
  16. }

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

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

选择类型筛选:

  1. // 选择类型条件结构
  2. chooses: [
  3. {
  4. type: 'brand',
  5. value: '华为'
  6. },
  7. {
  8. type: 'brand',
  9. value: '苹果'
  10. }
  11. ]
  1. /**
  2. * @param {array<Product>} products
  3. * @param {array<{type: String, value: String}>} chooses
  4. */
  5. choosesFilter: function (products, chooses) {
  6. let tmpProducts = [];
  7. if (chooses.length === 0) {
  8. tmpProducts = products;
  9. } else {
  10. /**
  11. * 选择类型条件是或逻辑,使用数组连接concat
  12. */
  13. for (let choice of chooses) {
  14. tmpProducts = tmpProducts.concat(products.filter(function (item) {
  15. return item[choice.type].indexOf(choice.value) !== -1;
  16. }));
  17. }
  18. }
  19. return tmpProducts;
  20. }

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

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

测试

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

  1. // 商品数组
  2. const products = [
  3. new Product('华为荣耀9', '华为', 2299),
  4. new Product('华为P10', '华为', 3488),
  5. new Product('小米MIX2', '小米', 3599),
  6. new Product('小米6', '小米', 2499),
  7. new Product('小米Note3', '小米', 2499),
  8. new Product('iPhone7 32G', '苹果', 4588),
  9. new Product('iPhone7 Plus 128G', '苹果', 6388),
  10. new Product('iPhone8', '苹果', 5888),
  11. new Product('三星Galaxy S8', '三星', 5688),
  12. new Product('三星Galaxy S7 edge', '三星', 3399),
  13. ];
  14. // 筛选条件
  15. let Conditions = {
  16. ranges: [
  17. {
  18. type: 'price',
  19. low: 3000,
  20. high: 6000
  21. }
  22. ],
  23. chooses: [
  24. {
  25. type: 'brand',
  26. value: '华为'
  27. },
  28. {
  29. type: 'brand',
  30. value: '苹果'
  31. }
  32. ]
  33. }  

调用函数:

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

参考

JS前端数据多条件筛选(商品搜索)的更多相关文章

  1. HTML多条件筛选商品

    今天同事接到一个类似于JD的按条件筛选商品的功能,同事把这个锅出色的甩给了我,俺就勉为其难的解决了这个问题. 首先我们来理清一下思路: 1.条件切换时,tab选项卡肯定要跟着切换,而且只是一个大类条件 ...

  2. JS前端数据格式化

    当我们从后台取了数据,但是我们希望在前台统一显示格式时,我们可能需要格式化数据. 今天正好总结一下前端JS格式化数据的几个方法: 1. toFixed() 方法   可把 Number 四舍五入为指定 ...

  3. js 树结构数据遍历条件判断

    代码: /** * 树结构数据条件过滤 * js 指定删除数组(树结构数据) */ function filter (data, id) { var newData = data.filter(x = ...

  4. js前端数据验证JS工具

    var regexEnum = { intege : "^-?[1-9]\\d*$", // 整数 intege1 : "^[1-9]\\d*$", // 正整 ...

  5. 求解:php商品条件筛选功能你是怎么做出来的?

    求解:php商品条件筛选功能你是怎么做出来的? 2013-09-25 13:43 chenhang607 | 浏览 2756 次 资源共享 求思路或者方法,最好能有些代码 2013-09-25 14: ...

  6. php商品条件筛选功能你是怎么做出来的?

    php商品条件筛选功能你是怎么做出来的? php按条件筛选商品的功能,还是比较简单的.其实就是根据不同的条件组成SQL查询条件,从数据库里查出不同的商品出来.举个例子:用户可以按价格范围.按品牌.按商 ...

  7. js前端 多条件筛选查询

    一.前言 在做项目中,遇到多条件筛选案例.实现完成以后,我将我做的代码分享在这里,希望可以帮助到其他朋友. 二.效果截图 三.实现代码 首先我先类型.类别.职位分成三块来处理,如果传到服务器端的话,就 ...

  8. c#中如何不通过后台直接用js筛选gridview中的数据条件筛选查询?

    js: //条件筛选 var showstate = true; function imagechange() { if (showstate) { $('#_toggle').hide(500, f ...

  9. Js处理数据——前端分页工具

    这几天有小伙伴讨论起了分页的相关问题,这里我也简单讲下前端如何简单便捷的利用Js(库)写出优雅,好用的分页工具. 分页是个很简单又超多接触的技术点,粗略来讲分如下两种: 真分页--每次根据页码.页大小 ...

随机推荐

  1. English trip -- VC(情景课)8 D Reading

    Listen and read. Shop Smart [smɑːt]  Employee of the Month: Sara['særə] (萨拉) Lopez(洛佩斯) Congratulati ...

  2. 实训10a--用数据值填充下拉列表

    1.新建mvc4项目,选择基本模板. (1)点击“开始->所有程序->Microsoft Visual Studio 2012->Visual Studio 2012”菜单,打开Vi ...

  3. 『OpenCV3』简单图片处理

    cv2和numpy深度契合,其图片读入后就是numpy.array,只不过dtype比较不常用而已,支持全部数组方法 数组既图片 import numpy as np import cv2 img = ...

  4. hdu-2227-dp+bit

    Find the nondecreasing subsequences Time Limit: 10000/5000 MS (Java/Others)    Memory Limit: 32768/3 ...

  5. h1042 N!大数乘int

    计算10000以内某个数的阶乘,即大数乘以int,考虑到一个int存一个数位过于繁琐且浪费空间,采用万进制 一个int存四个位数,但注意除了最高位,其他位不够四位数时要加上前导0凑够四位: 例1234 ...

  6. STL_string

    将string对象利用c风格的形式输出函数:  c_str() 栗子:      string s;      printf("%s\n",s.c_str());

  7. sql 数据库显示 正在恢复

    问题原因:Sql Server 一直显示正在恢复.有事务未恢复或者还原数据库造成 处理办法: 步骤一:数据库上右键->任务->分离 步骤二:数据库上右键->任务->脱机 数据库 ...

  8. spark submit 入门

    spark dirver本质是一个spark集群的驱动程序,你要调用spark集群的计算功能,必须要通过它! from pyspark import SparkConf, SparkContext c ...

  9. 循环大法——一次性理清forEach/for-in/for/$each

    国寿的这个项目写得我基础都忘完了 近期会把vue和基础都并行复习.学习 forEach 适用于调用数组的每个元素,并将元素传递给回调函数,但是空数组是不会执行回调函数的.forEach适用于集合中的对 ...

  10. JVM笔记(一) Java内存区域

    Java 内存区域 总概 java虚拟机在执行java程序的过程中,会把它管理的内存划分为几个不同的数据区域.每当运行一个java程序时,就会启动一个虚拟机. 具体的区域如图所示: 同时,方法区 与 ...