JS基础--集合

集合

集合(set)是一种包含不同元素的数据结构

集合特性

  • 集合中的成员是无序的
  • 集合中不允许相同成员存在

在很多编程语言中,并不把集合当成一种数据类型。当你想要创建一个数据结构,用来保存一些独一无二的元素时,比如一段文本中用到 的单词,集合就变得非常有用

相关概念
  • 空集: 不包含任何成员的集合称为空集
  • 全集: 则是包含一切可能成员的集合
  • 集合相等: 如果两个集合的成员完全相同,则称两个集合相等
  • 子集: 如果一个集合中所有的成员都属于另外一个集合,则前一集合称为后一集合的子集
对集合的操作
  • 并集: 将两个集合中的成员进行合并,得到一个新集合
  • 交集: 两个集合中共同存在的成员组成一个新的集合
  • 补集: 属于一个集合而不属于另一个集合的成员组成的集合
Set类
function Set() {
    this.dataStore = [];
    this.add = add;
    this.remove = remove;
    this.size = size;
    this.union = union;
    this.intersect = intersect;
    this.subset = subset;
    this.difference = difference;
    this.show = show;
}
  • show()
function show() {
    return this.dataStore;
}
  • add 方法
function add(data) {
    if (this.dataStore.indexOf(data) < 0) {
           this.dataStore.push(data);
           return true;
        } else {
           return false;
    } 
}

思路:先要确保数 组中不存在该数据。我们使用 indexOf() 检查新加入的元素在数组中是否存在。如果找到, 该方法返回该元素在数组中的位置;如果没有找到,该方法返回 -1。如果数组中还未包含该 元素,add() 方法会将新加元素保存到数组中并返回 true;否则,返回 false。

  • remove 方法
function remove(data) {
    var pos = this.dataStore.indexOf(data);
        if (pos > -1) {
           this.dataStore.splice(pos,1);
           return true;
        } else {
           return false;
    } 
}
  • union() 并集操作

思路:首先将第一个集合里的成员悉数加入一个临时集合,然后检 查第二个集合中的成员,看它们是否也同时属于第一个集合。如果属于,则跳过该成员, 否则就将该成员加入临时集合

在定义 union() 方法前,先需要定义一个辅助方法 contains(),该方法检查一个成员是否 属于该集合

function contains(data) {
    if (this.dataStore.indexOf(data) > -1) {
       return true;
        } else {
       return false;
    } 
}


function union(set) {
     var tempSet = new Set();
     for (var i = 0; i < this.dataStore.length; ++i) {
          tempSet.add(this.dataStore[i]);
     }
     for (var i = 0; i < set.dataStore.length; ++i) {
          if (!tempSet.contains(set.dataStore[i])) {
             tempSet.dataStore.push(set.dataStore[i]);
          }
     }
     return tempSet;
}
  • intersect() 交集

每当发现第一 个集合的成员也属于第二个集合时,便将该成员加入一个新集合,这个新集合即为方法的 返回值

function intersect(set) {
       var tempSet = new Set();
       for (var i = 0; i < this.dataStore.length; ++i) {
          if (set.contains(this.dataStore[i])) {
             tempSet.add(this.dataStore[i]);
          } 
       }
       return tempSet;
}
  • subset()

在判断每个元素是否属于待比较集合前,该方法先使用 size() 方法对比两个集合的大小

function size() {
        return this.dataStore.length;
}

思路:

subset() 方法首先要确定该集合的长度是否小于待比较集合。如果该集合比待比较集合还要大,那么该集合肯定不会是待比较集合的一个子集。 当该集合的长度小于待比较集合时,再判断该集合内的成员是否都属于待比较集合。如果有任意一个成员不属于待比较集合,则返回 false,程序终止。如果一直比较完该集合的 最后一个元素,所有元素都属于待比较集合,那么该集合就是待比较集合的一个子集,该方法返回true。

function subset(set) {
    if (this.size() > set.size()) {
	return false;
    } else {
       for each (var member in this.dataStore) {
          if (!set.contains(member)) {
             return false;
          } 
       }
    }
    return true;
}

  • difference() 返回一个新集合
function difference(set) {
    var tempSet = new Set();
    for (var i = 0; i < this.dataStore.length; ++i) {
       if (!set.contains(this.dataStore[i])) {
          tempSet.add(this.dataStore[i]);
       } 
    }
    return tempSet;
}