zoukankan      html  css  js  c++  java
  • swift5.x 集合(Set)的基本操作

    //
    //  ViewController3.swift
    //  swiftT
    //
    //  Created by wjwdive
    //  Copyright © 2020 wjwdive. All rights reserved.
    //
    
    import UIKit
    
    struct Person {
        var name: String
        var age: Int
    }
    //准守 Hashable 协议, 不实现该方法会报错:Type 'Person' does not conform to protocol 'Hashable'
    extension Person: Hashable {
        func hash(into hasher: inout Hasher) {
            hasher.combine(age)
            hasher.combine(name)
        }
    }
    
    extension Person: Equatable {
        static func ==(lhs: Self, rhs: Person) -> Bool {
            return lhs.name == rhs.name
        }
    }
    
    class ViewController3: UIViewController {
    
        override func viewDidLoad() {
            super.viewDidLoad()
            //创建Set
            let person: Set<Person> = [Person(name: "Jarvis", age: 18)]
            print(person)
            
            // 遍历Set
            //可以使用For-in 遍历 Set
            //因为Set 是无序的,如果需要顺序遍历Set,使用 sorted() 方法。
            
            //访问Set
           //Set.count
           //Set.isEmpty()
           
           //Set 添加元素
           //insert(_:)  添加一个元素到Set
           //update(with:) 如果已经有相等的元素,替换为新元素。如果Set 中没有,则插入
           
           //Set 移除元素
           //filter(_:) 返回一个新的Set, 新Set的元素是Set符合条件的元素
           //remove(_:) 从Set中移除一个s元素。如果元素是Set的成员就移除它,并且返回移除的值,如果集合中没有这个元素就返回你了
           //removeAll()   移除所有元素
           //removeFirst()  移除Set 的第一个元素,并不是第一个放入的元素,而是 hash后排序的第一个元素
           
            
            let course: Set = ["Math", "English", "History"]
            for c in course {
                print(c)
            }
            
            for cs in course.sorted() {
                print(cs)
            }
            
            var personsSet: Set<Person> = [Person(name: "Jarvis", age: 18), Person(name: "lisi", age: 18)]
            personsSet.update(with: Person(name:"Harvis", age: 20))
            //移除集合首部的元素
            personsSet.removeFirst()
            print("移除集合首部的元素 ", personsSet)
                
            print("filter : ", personsSet.filter({$0.age > 20}))
            
           
            //集合的计算
            //交,差(对称差集,所有属于A和B切不属于A和B的交集的元素),并,补(所有属于A但不属于B的元素)
            let a: Set<Character> = ["A", "B", "C"]
            let b: Set<Character> = ["B", "E", "F", "G"]
            print("a 交 b", a.intersection(b))
            print("a 并 b", a.union(b))
            print("a 对称差集 b", a.symmetricDifference(b))
            print("a 补 b", a.subtracting(b))
    
            print("a b, 有无相同元素", a.isDisjoint(with: b))
            
            //Set 的判断方法
            //isSubSet(of:) 判断是否是另一个Set或者Sequence的子集
            //isSuperSet(of:)   判断是否是另一个Set 或者 Sequence 的超集
            //isStrictSubset(of:) isStrictSuperset(of:)  判断是否是另一个Set的子集或者超集,但是又不等于另一个Set
            //isDisjoint(with:) 判断两个Set 是否有公共元素,如果没有返回True, 如果有返回false
            
            let smallSet: Set = [1, 2, 3]
            let bigSet: Set = [1, 2, 3, 4]
            print(smallSet.isSubset(of: bigSet))
            print(bigSet.isSuperset(of: smallSet))
            print(smallSet.isStrictSubset(of: bigSet))
            print(bigSet.isStrictSuperset(of: smallSet))
            print(smallSet.isDisjoint(with: bigSet))
            
            //实现自己的集合算法
            //给定一个集合,返回该集合的所有子集
            
            let sett: Set = ["A", "B", "C"]
            let subSets = getSubsets(sett)
               for subSet in subSets {
                    print(subSet)
                }
               
        }
        
        //求给定集合的所有子集, 1、位法, 局限:只能计算出集合中元素个数小于计算机位数的集合的所有子集,超出计算机位数,无法用该方法
        func getSubsets<T>(_ set: Set<T>) -> Array<Set<T>> {
            let count = 1 << set.count  // 左移count位, 2的 conut 次方个子集
            let elements = Array(set)   // 包含所有set元素的array
            var subsets = [Set<T>]()    // 可变数组,存储 set的子集
            for i in 0..<count {        // 针对每个子集的值 写入到待返回数组,每次的循环次数依次是 0, 1, 10, 11, 110,111,。。。 1代表对应数组位选中,0 代表不选中
                var subset = Set<T>()   // 用来保存子集的临时变量
                for j in 0..<elements.count {   // 针对已知集合中的每个元素,右移并和1做与操作,然后和1比较,结果为1 存入临时变量 subset, 否则不存入
                    if((i >> j) & 1) == 1{  // 把 i 依次移位,
                        subset.insert(elements[j])
                    }
                }
                subsets.append(subset)
            }
            return subsets
        }
        
       //求给定集合的左右子集, 2、递归法 每个元素构成子集的时候都有入选子集合不入选子集两种选择
        func getSubsetsRescue<T>(set: Set<T>) -> Array<Set<T>> {
            let elements = Array(set)
            return getSubsetPart(elements, index:elements.count - 1, count:elements.count )
        }
        
        
        func getSubsetPart<T>(_ elements: Array<T>, index: Int, count: Int) -> Array<Set<T>>{
            var subsets = Array<Set<T>>()
            //只有一个元素时
            if index == 0 {
                subsets.append(Set<T>())//添加空集到子集合数组
                var subset = Set<T>()
                subset.insert(elements[0])//构建只有一个元素的集合
                subsets.append(subset)//添加一个元素集合到子集合数组
                return subsets
            }
            
            //递归调用
            subsets = getSubsetPart(elements, index: index - 1, count: count)
            //
            for subset in subsets {
                var subsetWithCurrent = Set(subset)
                subsetWithCurrent.insert(elements[index])
                subsets.append(subsetWithCurrent)
            }
            return subsets
        }
    
        /*
        // MARK: - Navigation
    
        // In a storyboard-based application, you will often want to do a little preparation before navigation
        override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
            // Get the new view controller using segue.destination.
            // Pass the selected object to the new view controller.
        }
        */
    
    }
    
    
  • 相关阅读:
    c#备份MySQL数据库
    AjAX探究——JS调用实体类与赋值
    使用System.Timers.Timer类实现程序定时执行
    阿里云拨测:主动探测Web应用质量,助力提升用户体验
    亲历者说 | 完整记录一年多考拉海购的云原生之路
    核桃编程:前端可观测性建设之路
    深度 | 阿里云蒋江伟:什么是真正的云原生?
    从云网络时延看应用部署架构
    一文读懂 Serverless,将配置化思想复用到平台系统中
    如何编写有效的接口测试?
  • 原文地址:https://www.cnblogs.com/wjw-blog/p/12915219.html
Copyright © 2011-2022 走看看