Swift4.0新特性之String、Array和Dictionary

Swift4.0新特性之String、Array和Dictionary


Swift 4是苹果计划在2017年秋季推出的最新版本,值得关注的是其提供了与Swift 3代码很好的兼容性,并最大限度的保持了ABI稳定性.

String

字符串已经像之前的2.0版一样, 改为了Collection类型 。此变化消除了字符串对字符数组的依赖

0.创建空字符串的两种方式,可用isEmpty判断是否为空

let SwiftString = "Hello"
var emptyString = ""               // empty string literal
var anotherEmptyString = String()

1.字符和字符串

1.1 遍历字符串

for char in SwiftString {
    print(char)
}

1.2通过 Character类型创建单个字符

let char : Character = "H"

1.3 String值可以通过传入 Character来构造:

let charArr : [Character] = ["H", "e", "l", "l", "o"]
print(String(char)) // H
print(String(charArr)) // Hello

1.4 拼接字符串

//方式一:
let addString = String(charArr) + String(char) //HelloH
//方式二:
var addString2 = "Why"
addString2 += String(charArr) //"WhyHello"

2.字符串个数

let count1 = SwiftString.count //5(类型: String.CharacterView.IndexDistance)
let count2 = SwiftString.characters.count // 5(Int型)
count1: 

3.是否为空

let isStr = SwiftString.isEmpty //false

4.去掉某一个或几个字符

let text1 = SwiftString.dropFirst()//"ello"
let text2 = SwiftString.dropLast()//"Hell"
let text3 = SwiftString.dropFirst(2)//"llo"
let text4 = SwiftString.dropLast(2)//"Hel"
//注:以上皆为String.SubSequence类型
let text5 = String(text1) //"ello"---text5为String类型

5.倒叙

let text6 = String(SwiftString.reversed()) //"olleH"

6.字符串分割数组

let swiftString2 = "one two three"
let StrArr = swiftString2.split(separator: " ") //["one", "two", "three"]
//let StrArr: [String.SubSequence]

7.删除不符合ASCII编码的字符

let swiftString3 = "quanjun 🐷,"
let qj = swiftString3.filter { (char) -> Bool in
    return char.unicodeScalars.reduce(true, { $0 && $1.isASCII })
}
print(qj)  //"quanjun ,"

8. 字符串索引

  • Swift 的字符串不能通过整数值索引
  • 使用 index(before:) 和 index(after:) 方法来访问给定索引的前后。要访问给定索引更远的索引,你可以使用 index(_:offsetBy:) 方法而不是多次调用这两个方法。
  • Swift 4添加了Substring类型,用于引用String的子序列。
  • String和Substring都实现了StringProtocol,两者几乎具有相同的功能:

8.1 startIndex和endIndex

let greeting = "Guten Tag!"
//startIndex属性来访问 String中第一个 Character的位置
print(greeting[greeting.startIndex])
print(greeting[greeting.index(after: greeting.startIndex)])
//endIndex属性就是 String中最后一个字符后的位置。endIndex属性并不是字符串下标脚本的合法实际参数
//greeting[greeting.endIndex] //会报错
print(greeting[greeting.index(before: greeting.endIndex)])
//注: 如果 String为空,则 startIndex与 endIndex相等

let index = greeting.index(greeting.startIndex, offsetBy: 2)
print(greeting[index])
let indesString = greeting[greeting.startIndex...index]  //"Gut"
//注:indesString : Substring类型
print(String(indesString)) //"Gut"

8.2使用 characters属性的 indices属性来创建所有能够用来访问字符串中独立字符的索引范围 Range。

for index in greeting.characters.indices {
    print("\(greeting[index]) ", terminator: "")//不换行输出
}

9.多行字符串

  • 注:你可以在多行字面量中使用单个双引号 " 。要在多行字符串中包含 """ ,你必须用反斜杠( \ )转义至少其中一个双引号
let rowsString = """
                我是一只小鸭子
                咿呀咿呀哟
                \"""
                """
print(rowsString)

Array

  • Swift 的 Array类型被桥接到了基础框架的 NSArray类上。
  • Swift 数组的类型完整写法是 Array<Element>, Element是数组允许存入的值的类型。你同样可以简写数组的类型为 [Element]。

1. 创建确定大小且元素都设定为相同默认值的数组。

/*Array*/
//默认值(叫做 repeating)和新数组元素的数量(叫做 count)
var array1 = Array(repeating: 1, count: 2)
var array2 = Array(repeating: 3, count: 2)

2. 连接两个数组来创建数组(类型必须一致)

var array3 = array1 + array2
print(array3) //[1, 1, 3, 3]

3. 数组个数

print(array3.count)  //5

4. 判断数组个数是否为0

print(array3.isEmpty)  //false
print(array3.count == 0)  //false

5. 添加

array3.append(4) //[1, 1, 3, 3, 4]
array3 += [5]  //[1, 1, 3, 3, 4, 5]
array3 += [6, 5]  //[1, 1, 3, 3, 4, 5, 6, 5]

6. 取值

print(array3[0]) // 1
array3[1] = 9 // [1, 9, 3, 3, 4, 5, 6, 5]

//用下标改变一个范围的值,就算替换与范围长度不同的值的合集也行
array3[2...4] = [0, 8] //[1, 9, 0, 8, 5, 6, 5]

7.遍历

for item in array3 {
    print(item)
}
//元组输出
for (index, item) in array3.enumerated() {
    print("\(index)---\(item)")
}
//倒叙输出
for item in array3.reversed() {
    print(item)
}

//forEach遍历,如同for-in
let arr = [1, 9, 3, 3, 4, 5, 6, 5]
arr.forEach { (x) in
    print(x)
}

8. 删除和插入

array3.remove(at: 1)  //[1, 0, 8, 5, 6, 5]
array3.removeFirst()  //[0, 8, 5, 6, 5]
array3.removeLast()   //[0, 8, 5, 6]
array3.removeFirst(2) //[5,6]
array3.removeLast(1)  //[5]
array3.removeAll()    //[]

9. 获取元素在数组中的索引

let arr = ["1", "2", "4", "3", "6", "2"]
//获取最后一个元素索引
let index0 = arr.endIndex           //6

//获取第一个元素索引
let index1 = arr.startIndex         //0

//获取指定某元素索引
let index2 = arr.index(of: "3")     //3

//当数组中有多个相同元素时, 返回指定元素的第一个的索引
let index3 = arr.index(of: "2")     //1

//返回指定某索引的后一个索引, 等同于4+1
let index4 = arr.index(after: 4)    //5

//返回指定某索引的前一个索引, 等同于4-1
let index5 = arr.index(before: 8)   //7

//根据元素内的某属性获取索引
let strArr = [("a", "1"), ("b", "2"), ("s", "3")]
let index = strArr.index(where: { $0.0 == "b" })
//返回值是一个可选值: Optional(1)

Dictionary and Set

  • 至于Collection类型,Set和Dictionary并不那么最直观的
  • Swift 的 Dictionary桥接到了基础框架的 NSDictionary类。

1.首先列表可以是从一系列键值对(元组)创建一个字典:

//Dictionary
let keyNames = ["a", "b", "c", "d", "e"]
let valueNames = [1, 2, 4, 5, 6]

//public init<S>(uniqueKeysWithValues keysAndValues: S) where S : Sequence, S.Element == (Key, Value)
//对于该方法的具体解释,可以点进去看一下官方的讲解
let nameDic = Dictionary(uniqueKeysWithValues: zip(keyNames, valueNames))
print(nameDic)
//["b": 2, "e": 6, "a": 1, "d": 5, "c": 4]

2.在初始化Dictionary时, 你现在可以使用你喜欢的方式来处理重复的键,同时避免覆盖键值对,且不会出现任何问题:

let keyNames2 = ["a", "b", "c", "a", "b"]

//public init<S>(_ keysAndValues: S, uniquingKeysWith combine: (Value, Value) throws -> Value) rethrows where S : Sequence, S.Element == (Key, Value)
//对于该方法的具体解释,可以点进去看一下官方的讲解
let nameDic2 = Dictionary(zip(keyNames2, repeatElement(1, count: keyNames2.count)), uniquingKeysWith: +)
print(nameDic2)
//["b": 2, "a": 2, "c": 1]

3.Dictionary 和 Set现在都可以将结果 通过filter函数 过滤到原始类型的新对象中:

let nameDic3 = nameDic.filter({ $0.value < 5 })
print(nameDic3)
//["b": 2, "a": 1, "c": 4]

4.Dictionary为直接映射其值提供了一种非常有用的方法::

//将value值Int转化为字符串
let nameDic4 = nameDic3.mapValues({ "\($0)" })
print(nameDic4)
//["b": "2", "a": "1", "c": "4"]

5.在Dictionary上访问某个值时,常见的做法是使用nil-coalescing operator给出默认值

let nameDic5 = nameDic4["d", default : "unknown"]

6.我们可以从Sequence"中初始化Dictionary,并将其分组为bucket::

//注: 当通过特定模式对数据进行分组时,这相当方便。
let name2 = ["Proxima", "Centauri A", "Centauri B", "Barnard", "Wolf"]
let nameDic6 = Dictionary(grouping: name2, by: { $0.first! })
print(nameDic6)
//["B": ["Barnard"], "W": ["Wolf"], "P": ["Proxima"], "C": ["Centauri A", "Centauri B"]]

涉及Zip的用法,详见Swift语法之Zip详解

7.预留空间

  • Sequence和Dictionary现在都具有明确保留容量的能力
  • 在这些类型上,Reallocation可能是一项代价高昂的任务。
  • 如果你知道需要存储的数据量时, 使用reserveCapacity(_:)可以提高性能且便捷
var name3 : [String : Int] = [ : ]
print(name3.capacity) // 0
name3.reserveCapacity(10) //储备 10元素的能力
print(name3.capacity) // 12


欢迎您扫一扫下面的微信公众号,订阅我的博客!

微信公众号
最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 159,290评论 4 363
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 67,399评论 1 294
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 109,021评论 0 243
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 44,034评论 0 207
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 52,412评论 3 287
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 40,651评论 1 219
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 31,902评论 2 313
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 30,605评论 0 199
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 34,339评论 1 246
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 30,586评论 2 246
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 32,076评论 1 261
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 28,400评论 2 253
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 33,060评论 3 236
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 26,083评论 0 8
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 26,851评论 0 195
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 35,685评论 2 274
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 35,595评论 2 270

推荐阅读更多精彩内容

  • importUIKit classViewController:UITabBarController{ enumD...
    明哥_Young阅读 3,673评论 1 10
  • 53.计算字符 在字符串中获取字符值的数量, 可以使用字符串字符属性中的计数属性: let unusualMena...
    无沣阅读 1,002评论 0 4
  • 一直想要将自己写的工具类做成一个三方库分享出去让更多的人可以快速开发,今天刚学会用cocoapods支持管理我的三...
    勇不言弃92阅读 223评论 0 0
  • APP创建完成之后,我们需要真机调试,以下介绍真机调试证书的创建。 在开始之前我们先检查一下 Apple Worl...
    Luyc_Han阅读 2,855评论 0 2
  • 糖尿病是一组以高血糖为特征的代谢性疾病。患有糖尿病的患者在平时就需要特别注意饮食,稍有不注意的地方就很容易引发高血...
    Michelle0Q0阅读 279评论 1 0