掌握这9段Swift代码,让你教面试官重新做人
1 将数组中每个元素的值乘以 2第一个例子中没什么干货,我们都知道只要使用 let arr = (1...20).map{$0*2} print(arr)//[2,4,6,8,10,12,14,16,18,20,22,24,26,28,30,32,34,36,38,40] 2 求一组数字的和 这个问题可以通过使用 print((1...20).reduce(0,+))//210 3 证明字符串中含有某个单词有三种方法:其中第三种方法的split函数如何使用看这里
let words = ["Swift","iOS","cocoa","OSX","tvOS"] let tweet = "This is an example tweet larking about Swift" print(!words.filter({tweet.contains($0)}).isEmpty) //true print(words.contains(where: tweet.contains))// true let result = tweet.characters .split(separator: " ") .lazy .map(String.init) .contains(where: Set(words).contains) print(result)// true 4 读取一个文件 和其他语言不同,Swift 不能使用内建的函数读取文件,并把每一行存放到数组中。不过我们可以结合 let path = Bundle.main.path(forResource: "test",ofType: "txt") let lines = try? String(contentsOfFile: path!).characters.split{$0 == "n"}.map(String.init) if let lin = lines { print(lin) } 5 祝你生日快乐 这段代码会将“祝你生日快乐”这首歌的歌词输出到控制台中,它在一段区间内简单的使用了 let name = "uraimo" (1...4).forEach { print("Happy Birthday " + (($0 == 3) ? "dear (name)":"to You")) } Happy Birthday to You Happy Birthday to You Happy Birthday dear uraimo Happy Birthday to You 6 数组过滤 假设我们需要使用一个给定的过滤函数将一个序列(sequence)分割为两部分。很多语言除了有常规的 所以,我们可以通过拓展 extension Sequence { typealias Element = Self.Iterator.Element func partitionBy(fu: (Element)->Bool)->([Element],[Element]){ var first=[Element]() var second=[Element]() for el in self { if fu(el) { first.append(el) }else{ second.append(el) } } return (first,second) } } let part = [82,58,76,49,88,90].partitionBy{$0 < 60} print(part) // ([58,49],[82,90])实际上,这不是单行代码,而且使用了命令式的解法。我们可以使用 filter
对它略作改进
extension Sequence { func anotherPartitionBy(fu: (Self.Iterator.Element)->Bool)->([Self.Iterator.Element],[Self.Iterator.Element]){ return (self.filter(fu),self.filter({!fu($0)})) } }
let part2 = [82,90].anotherPartitionBy{$0 < 60} print(part2) // ([58,90]) 这种解法略好一些,但是他遍历了序列两次。而且为了用单行代码实现,我们删除了闭合函数,这会导致很多重复的内容(过滤函数和数组会在两处被用到)。 能不能只用单个数据流就对原来的序列进行转换,把两个部分分别存入一个元组中呢?答案是是可以的,使用 let part3 = [82,90].reduce( ([],[]),{ (a:([Int],[Int]),n:Int) -> ([Int],[Int]) in (n<60) ? (a.0+[n],a.1) : (a.0,a.1+[n]) }) print(part3) // ([58,90]) 这里我们创建了一个用于保存结果的元组,它包含两个部分。然后依次取出原来序列中的元素,根据过滤结果将它放到第一个或第二个部分中。 我们终于用真正的单行代码解决了这个问题。不过有一点需要注意,我们使用
7 找到数组中最小(或最大)的元素 我们有多种方式求出 sequence 中的最大和最小值,其中一种方式是使用 let aaa = [10,-22,753,55,137,-1,-279,1034,77] //Find the minimum of an array of Ints print(aaa.sorted().first ?? 0)//-279 print(aaa.reduce(Int.max,min))//-279 print(aaa.min() ?? 0) //-279 //Find the maximum of an array of Ints print(aaa.sorted().last ?? 0)//1034 print(aaa.reduce(Int.min,max))//1034 print(aaa.max() ?? 0)//1034 8 埃拉托色尼选筛法(就是求小于N的所有质数)古老而优秀的埃拉托色尼选筛法被用于找到所有小于给定的上限 n 的质数。 首先将所有小于 n 的整数都放入一个序列(sequence)中,这个算法会移除每个数字的倍数,直到剩下的所有数字都是质数。为了加快执行速度,我们其实不必检查每一个数字的倍数,当检查到 n 的平方根时就可以停止。 基于以上定义,最初的实现可能是这样的:
let n = 50 var primes = Set(2...n) (2...Int(sqrt(Double(n)))).forEach { let _ = primes.subtract(stride(from: 2*$0,through: n,by: $0)) } print(primes.sorted()) 结果是: [2,3,5,7,11,13,17,19,23,29,31,37,41,43,47]
在外层的区间里,我们遍历每一个需要检查的数字。对于每一个数字,我们使用 不过正如你所见,为了真正的删除掉这些倍数,我们使用了一个外部的可变集合,这会带来副作用。 我们总是应该尝试消除副作用,所以我们先计算所有的子序列,然后调用
let n = 50 var sameprimes = Set(2...n) sameprimes.subtract((2...Int(sqrt(Double(n)))).flatMap{ stride(from: 2*$0,by: $0) }) print(sameprimes.sorted())结果是: [2,47]
9 福利:使用析构交换元组中的值和其他具有元组类型的语言一样,Swift 的元组可以被用来交换两个变量的值,代码很简洁:
var a1 = 1,b1 = 2 (a1,b1) = (b1,a1) print(a1,b1)// 2 1 (编辑:李大同) 【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容! |