首页 - 日志 - 维基 - 读书 - 跑步 - 关于

Swift学习笔记(1)

之前也有一篇学习笔记,后来发现如果这样学习下去,明年这个时候都很难出师(老师=互联网上海量的资料及乐于分享知识的各位大牛)。意识到这个问题是因为这几天我在阅读一本书《禅与摩托车维修艺术》及看完 iOS开发和七七八八 上的字符串学习笔记。原来我对语言的认识只停留在教材文字的表面,而文字背后的东西却不得而知。编程是一门艺术,不是语法的堆砌,如果没有了解语言的内涵及工作原理,那么写出来的代码不是生涩难懂毫无美感就是效率低下。所以,从决定学习iOS编程到现在两个月的时间过去了,我选择推倒一切,从零开始。之前的那篇笔记我没有删除,但做了标注。

另外:从这篇笔记开始采用Todo的模式来组织文字,做笔记的同时通过GTD的方式来管理及统计学习的过程,这在orgmode中实现是轻而易举的事情。

TODO 字符串[String]

表1  [2015-12-13 Sun 11:15]
       
nil 1:56    
TODO 字符串[String] 1:56    
  TODO 待解决的问题   0:04  
    DONE 上下标的问题     0:04
  知识点   1:52  

TODO 待解决的问题

DONE 上下标的问题

  • State "DONE" from "TODO" [2015-12-10 Thu 10:36]

字符串“xiaoguo”的上标为0,下标为7,而字符串长度也为7,那最后一个下标所指向的是什么呢?如果是 \n ,那又该如何验证呢?

let str = "xiaoguo"
let i = str.endIndex
print(str[i])
// fatal error: Can't form a Character from an empty String
// 这里说明是一个空字符串

原因如下:使用startIndex属性可以获取一个String的第一个Character的索引。使用endIndex属性可以获取最后一个Character的后一个位置的索引。因此,endIndex属性不能作为一个字符串的有效下标。如果String是空串,startIndex和endIndex是相等的。

DONE Index类型实际上是什么

  • State "DONE" from "TODO" [2015-12-10 Thu 09:17]

通过startIndex和endIndex获得的上下标不是Int类型,而是Index类型,这个Index类型到底是个什么东东?
通过String定义可以看出属性Index是个结构体,具体代码如下:

extension String : CollectionType {
    struct Index : BidirectionalIndexType, Comparable, Reflectable {
        func successor() -> String.Index
        func predecessor() -> String.Index
        func getMirror() -> MirrorType
    }
    var startIndex: String.Index { get }
    var endIndex: String.Index { get }
    subscript (i: String.Index) -> Character { get }
    func generate() -> IndexingGenerator<String>
}

TODO 作业,从包含多个‘hi’的字符串中提取所有的‘hi’,返回一个包含range范围的数组

DONE 实现字符串的反转,“abc” -> “cba”

var stringReverse = "abcdefghijklmnopqrstuvwxyz"
var characterArray = [Character]()
for c in stringReverse.characters {
    characterArray.append(c)
}
// $0 指累加器(accumulator),$1 指遍历数组得到的一个元素
stringReverse = String(characterArray.reduce([Character](), combine: {[$1] + $0}))
print(stringReverse)

知识点

  • Swift 中 String 是 struct
  • Swfit里面的String很有意思,它并不是由很多个Character组成的,而是在其上面又封装了一些东西。另外因为要兼容不同的编码,每个组成字符所占的内存也不一样(例如中文和英文的区别),所以它的下标并不是一个Int型,也不能通过下标来直接定位、获取字符。
  • 字符串最常用的两个参数:下标(Index)和范围(Range),几乎所有API都要用到它们。
  • 删除字符串中的某个字符或者连续的几个字符,需要通过获得Index和Range来进行。

字符串中检索某个单词方法:rangeOfString

var str = "Hello Apple.Hello Swift"  
str.rangeOfString("Hello")//正向检索;  
str.rangeOfString("Hello", options: NSStringCompareOptions.BackwardsSearch)//反向检索;  

str.rangeOfString("swift")//大小写完全匹配  
str.rangeOfString("swift", options: NSStringCompareOptions.CaseInsensitiveSearch)//忽略大小写  

返回值是一个Range范围,这里有两个‘Hello’,无论是正向还是反向检索都只能返回一个range。

截取子串

var str = "Hello Apple.Hello Swift"  
var toIndex = advance(str.startIndex, 4)  
str.substringToIndex(toIndex)//截取从开始到第4个位置的字符串;  

var fromIndex = advance(str.startIndex, 7)  
str.substringFromIndex(fromIndex)//截取从第7个位置开始到最后的字符串;  

str.substringWithRange(Range<String.Index>(start: toIndex, end: fromIndex))//截取从第4个位置到第7个位置的字符串;

截取之后,原来的字符串不变。

替换字符串

思路,得到所有需要替换的字符串,把每个字符串的range保存进数组,然后挨个替换。


本页最后更新时间:2015-12-21 Mon 13:32.
小过的布拉格 - Copyright©2013-2021 - @xiaoguo - Powered by Emacs 29.1 (Org mode 9.6.6)
行路难,行路难, 多歧路,今安在。长风破浪会有时,直挂云帆济沧海。