集合Set
【接口参照了c# HashSet】
UnionWith: 合集
IntersectWith: 交集
ExceptWith: 差集
SymmetricExceptWith: 相当于异或, 相同的排除, 不同的留下
IsSubsetOf: 是否为子集
IsSupersetOf: 是否为超集
IsProperSupersetOf: 是否为真超集
IsProperSubsetOf: 是否为真子集
IsOverlaps: 是否存在重叠, 类似交集
IsEquals: 是否相同
local Set = {} Set.__cname = "util.Set" Set.__index = Set function Set.new(tb) local obj = {} setmetatable(obj, Set) obj:ctor(tb) return obj end function Set:ctor(tb) if nil ~= tb then local distinctCount = 0 for k, v in pairs(tb) do local flag = self.setTb[v] if nil == flag then self.setTb[v] = 1 distinctCount = distinctCount + 1 end end self.count = distinctCount else self.setTb = {} self.count = 0 end end function Set:Clear() if 0 == self.count then return end self.setTb = {} self.count = 0 end function Set:GetCount() return self.count end function Set:Add(v) if nil == v then return false end if nil ~= self.setTb[v] then return false end self.setTb[v] = 1 self.count = self.count + 1 return true end function Set:Remove(v) if nil == v or 0 == self.count then return false end local flag = self.setTb[v] if nil ~= flag then self.setTb[v] = nil self.count = self.count - 1 return true end return false end function Set:Contains(v) if nil == v or 0 == self.count then return false end return nil ~= self.setTb[v] end ---差集 function Set:ExceptWith(other) -- 减掉other的所有元素 assert("util.Set" == other.__cname) if self.count < 0 then return end if self == other then self:Clear() return end for k, v_flag in pairs(other.setTb) do self:Remove(k) end end ---交集 function Set:IntersectWith(other) -- other有, 自己也有的保留 assert("util.Set" == other.__cname) if 0 == self.count then return end if self == other then return end if other.count < 1 then self:Clear() return end for k, v_flag in pairs(other.setTb) do if 1 == self.setTb[k] then self.setTb[k] = 2 --other有自己也有的做标记 end end --未被标记的删除 for k, v_flag in pairs(self.setTb) do if 2 ~= v_flag then self:Remove(k) end end end ---并集 function Set:UnionWith(other) -- 加上other的所有元素 assert("util.Set" == other.__cname) for k, v_flag in pairs(other.setTb) do self:Add(k) end end ---是否为子集 function Set:IsSubsetOf(other) -- 自己的元素other都有 assert("util.Set" == other.__cname) if 0 == self.count then return true end --空集是任何集合的子集 local sameCount = 0 for k, v_flag in pairs(other.setTb) do if nil ~= self.setTb[k] then sameCount = sameCount + 1 end end return self.count == sameCount end ---是否为真子集 function Set:IsProperSubsetOf(other) -- 自己的元素other都有, 且other有额外的元素 assert("util.Set" == other.__cname) if 0 == self.count then if other:GetCount() > 0 then return true end end local sameCount = 0 local differentCount = 0 for k, v_flag in pairs(other.setTb) do if nil ~= self.setTb[k] then sameCount = sameCount + 1 else differentCount = differentCount + 1 end end return self.count == sameCount and differentCount > 0 end ---是否为超集 function Set:IsSupersetOf(other) -- other的元素自己都有 assert("util.Set" == other.__cname) if 0 == self.count then local otherCount = other:GetCount() if otherCount < 1 then return true end if otherCount > 0 then return false end end for k, v_flag in pairs(other.setTb) do if nil == self.setTb[k] then --只要other的元素自己没有, 则为false return false end end return true end ---是否为真超集 function Set:IsProperSupersetOf(other) -- other的所有元素, 自己都有, 且自己还有额外的元素 assert("util.Set" == other.__cname) if 0 == self.count then return false end local otherCount = other:GetCount() if otherCount < 1 then return true end for k, v_flag in pairs(other.setTb) do if nil == self.setTb[k] then --other中有元素自己没有, 则为false return false end end return self.count > otherCount end ---存在重叠(交集) function Set:IsOverlaps(other) --other的元素我有一个就行 assert("util.Set" == other.__cname) if 0 == self.count then return false end for k, v_flag in pairs(other.setTb) do if self.setTb[k] then return true end end return false end ---两个Set是否相同 function Set:IsEquals(other) assert("util.Set" == other.__cname) if self.count ~= other.count then return false end for k, v_flag in pairs(other.setTb) do if not self:Contains(k) then return false end end return true end function Set:__tostring() if 0 == self.count then return "" end local strTb = {} for k, v_flag in pairs(self.setTb) do table.insert(strTb, tostring(k)) end return table.concat(strTb, ",") end function Set:GetIterator() local function iterator(tb, key) local k = next(self.setTb, key) return k end return iterator end return Set
【关于:子集、真子集】
比如全集S为{1,2,3},
它的子集为{1}、{2}、{3}、{1,2}、{1,3}、{2,3}、{1,2,3}、{};
而真子集为{1}、{2}、{3}、{1,2}、{1,3}、{2,3}、{}, 不包括全集S本身.
非空真子集为{1}、{2}、{3}、{1,2}、{1,3}、{2,3}, 不包括S及空集{}.
【参考】
HashSet<T> 类 (System.Collections.Generic) | Microsoft Docs