iOS-NSURL 与 NSURLComponents 解读

这里有一个直观的描述来解释什么是“一维数据类型”:number或string被格式化为多种多样的值,可以通过数学运算或某种转换方法可以算出它们的值。比如:十六进制的颜色值 #EE8262
的红绿蓝三原色的值通过掩码或移位运算得出;正则表达式可以通过少量字符中复杂的样本中进行匹配。
在所有的一维数据类型中,URI有着至高地位。单独就人类可阅读的字符串这一点来说,它存在并将永远存在于计算机中任何你能够想象到的对位置信息进行编码的数据中。
它最基础的表示法中,URI由一个scheme和一个hierarchical part组成,带有query和fragment(后两者非必需):
Text : [ ? ] [ # ]

很多像HTTP的协议中会定义有一定的规范结构,例如:username、password、port, 以及hierarchical part中的path:
foo
://
username
:
password
@
example.com
:
8042
/over/there/index
.
dtb
?
type=animal&name=narwhal

nose

scheme
username

password

hostname

port
path

extension

query

fragment

对网络编程的扎实理解植根于对于URL各个部分的完全的熟悉。作为软件开发工程师,这意味着在你的编程语言标准库中存在着对URI进行指挥功能的命令。
如果某门语言在标准库中没有URL模块,你要跑着离开这门语言(不能用走的!一定要跑!),这不是一门真正的编程语言。

在Foundation库中,NSURL
用来代表URL。
NSURL
可以通过 URLWithString:
类方法实例化。
Objective-CNSURL *url = [NSURL URLWithString:@"http://example.com"];

如果传入值不是合法URL,这个方法会返回一个 nil
值。
我们几周前提到过 NSString
也有一些关于path处理的残留功能,但这些功能对于处理 NSURL
实在是太麻烦了。把 NSString
转化为 NSURL
带来的额外转化成本让这件事并不那么方便,你总是要花时间在这个上面。如果一个值就是一个URL,那么它就应该被保存为 NSURL
,把这两种类型搞混是懒惰而鲁莽的API设计。
附加提示:@@
是创建 NSURL
的字面量的绝佳方法(例如:@@"http://example.com"
),怎么样,很方便吧?

NSURL
也有一个类方法 +URLWithString:relativeToURL:
可以根据一个base URL地址和关联字符串来构造URL。这个方法的行为由于其对子目录的/
符号的处理而变得非常混乱无序。
这里有一些这个方法用法的典型参考:
Objective-CNSURL *baseURL = [NSURL URLWithString:@"http://example.com/v1/"];[NSURL URLWithString:@"foo" relativeToURL:baseURL];// http://example.com/v1/foo[NSURL URLWithString:@"foo?bar=baz" relativeToURL:baseURL];// http://example.com/v1/foo?bar=baz[NSURL URLWithString:@"/foo" relativeToURL:baseURL];// http://example.com/foo[NSURL URLWithString:@"foo/" relativeToURL:baseURL];// http://example.com/v1/foo[NSURL URLWithString:@"/foo/" relativeToURL:baseURL];// http://example.com/foo/[NSURL URLWithString:@"http://example2.com/" relativeToURL:baseURL];// http://example2.com/

URL Components
NSURL
根据RFC 2396的定义提供accessor方法用于获取URL每一部分的值:
– absoluteString
– absoluteURL
– baseURL
– fileSystemRepresentation
– fragment
– host
–lastPathComponent
– parameterString
– password
– path
– pathComponents
– pathExtension
–port
– query
– relativePath
– relativeString
– resourceSpecifier
– scheme
– standardizedURL
– user

NSURL
官方文档中的文档和样例是让你熟悉各种URL组成部分的绝佳参考。
虽然可以通过URL来存储用户名和密码,但建议用 NSURLCredential
装载用户名和密码,用keychain来存储它们更适合。

NSURLComponents
苹果在 iOS 7 和 OS X Mavericks 中悄悄添加了 NSURLComponents
,这样就可以完美替代 NSMutableURL
了。但文档还不是很完善,所以这个类仍然是近期Foundation新增类中隐晦的一块。
创建 NSURLComponents
实例和创建 NSURL
实例的方法差不多,通过一个 NSString
和一个非必需的base URL参数创建(+componentsWithString:
& +componentsWithURL:resolvingAgainstBaseURL:
)。也可以用 alloc init
创建一个空的容器,和NSDateComponents
差不多。
NSURL
和 NSURLComponents
的不同之处在于,URL component属性是 readwrite
的。它提供了安全直接的方法来修改URL的各个部分:
scheme

user

password

host

port

path

query

fragment

如果尝试赋值一个非法的scheme或port,会抛出一个异常。

另外,NSURLComponents
也有 readwrite
属性对每个component进行[percent-encoded]。
percentEncodedUser

percentEncodedPassword

percentEncodedHost

percentEncodedPath

percentEncodedQuery

percentEncodedFragment

对这些percent encoding属性的get操作可能会造成retain增加。set操作会默认认为该component已经正确encode了。试图赋值一个非法的percent encode值会抛出异常。虽然 ';' 是一个合法的路径字符,但建议还是percent-encoded一下来兼容NSURL(传递给-stringByAddingPercentEncodingWithAllowedCharacters:
URLPathAllowedCharacterSet
参数 会将所有的 ';' 字符percent-encode)。
Percent-Encoding
说起percent-encoding...
NSURL
对 CFURLRef
的转换是无缝的。底层的C API有 NSURL
的所有功能。包括CFURLCreateStringByAddingPercentEscapes
和CFURLCreateStringByReplacingPercentEscapesUsingEncoding
异常:
CFURLCreateStringByAddingPercentEscapes
:创建一个字符串的copy,用同义的percent-encoded字符代替原有的字符。

Objective-CCFStringRef CFURLCreateStringByAddingPercentEscapes ( CFAllocatorRef allocator, CFStringRef originalString, CFStringRef charactersToLeaveUnescaped, CFStringRef legalURLCharactersToBeEscaped, CFStringEncoding encoding);

CFURLCreateStringByReplacingPercentEscapesUsingEncoding
: 创建一个新字符串,用同义的percent-encoded字符代替原有的所有可替换字符。

Objective-CCFStringRef CFURLCreateStringByReplacingPercentEscapesUsingEncoding ( CFAllocatorRef allocator, CFStringRef origString, CFStringRef charsToLeaveEscaped, CFStringEncoding encoding);

Bookmark URL
最后一个话题是关于 bookmark URL 的,bookmard URL可以在应用多次启动间安全地引用文件。可以认为是一种对文件描述符的持久化。
一个bookmark是一个唯一的数据类型,包含一个描述文件位置的 NSData
对象。鉴于path和文件引用URL在多次启动间可能被破坏,bookmark就可以被用来重建某个文件的URL地址,即使文件被改名或移动了位置也可以。

你可以在苹果官方的文件系统编程指南的"Locating Files Using Bookmarks"部分中阅读更多关于bookmark URL的内容。
忘记喷射火箭背包,忘记会飞的汽车吧,看看我对未来的设想:所有的东西都有一个URL,以Markdown编码,用Git存储!如果你对宇宙资源定位器有兴趣的话,你会同意我的想法的!
像超文本一样,通用标识就是一个哲学概念,通用标识理念早于计算机时代被提出,也将长存于人类信息体系中。这些通用标示合在一起便可以代表我们信息时代的架构:一个用来把我们对于宇宙每一点了解都encode为一个网络中实体的框架,这很酷,很像我们的大脑中存在很多神经元一样。
我们处在物理计算的寒武纪大爆发险境边缘。用不了多久就会出现这样的情景:在Internet组成的世界中,我们生活中的每一部分都有一个URL,也都有一个电子化的大脑,都有数字化的精神和意识。虽然不能说是奇点迫近,但是,我们,就正在某些未知但难以置信的奇妙事物边缘,马上就要感受到它的来临。
世界总是这样的:互相交换猫咪照片的技术,总是蕴含着无比高深的哲学含义。

你可能感兴趣的:(iOS-NSURL 与 NSURLComponents 解读)