对于NSString肯定会经常用到,谈谈最近在项目中遇到的一个奇特的现象。如下:
我们知道文件系统的命名都是用的字符串,比如你给文件取名“a.pdf”,然后保存文件后,那个文件的名字就真的是 "a.pdf"吗?
假如有一个文件夹 folderName,他里面包含一个文件 fileName.........然后我们得到一个包含许多文件名的数组
NSFileManager* fileManager = [NSFileManagerdefaultManager];
NSError* error;
NSArray* fileList = [fileManager contentsOfDirectoryAtPath:folderName error:&error];
此时你
if(![fileList containsObject: fileName]) {
NSLog(@"error!");
}
那这个error一定不会出现吗?? 不一定吧!!!!
最近在项目中我们就遇到了这样的事情, debug是查看的这个文件一定是存在的,但 [fileList containsObject: fileName] 判断就是错误,
你也许会说是不是苹果的函数 containsObject 有问题了,
但如果你将字符串标准化了,就不会出现问题了,
怎样标准化??
CFStringNormalize((CFMutableStringRef)fileName, kCFStringNormalizationFormD);
苹果上也提过,当字符串设计到文件名时,这就要注意标准化了
上面函数的解释:
/*!
@function CFStringNormalize
Normalizes the string into the specified form as described in
Unicode Technical Report #15.
@param theString The string which is to be normalized. If this
parameter is not a valid mutable CFString, the behavior is
undefined.
@param theForm The form into which the string is to be normalized.
If this parameter is not a valid CFStringNormalizationForm value,
the behavior is undefined.
*/
CF_EXPORTvoid CFStringNormalize(CFMutableStringRef theString, CFStringNormalizationForm theForm);
第二个参数的解释:
/*!
@typedef CFStringNormalizationForm
This is the type of Unicode normalization forms as described in
Unicode Technical Report #15. To normalize for use with file
system calls, use CFStringGetFileSystemRepresentation().
*/
typedef CF_ENUM(CFIndex, CFStringNormalizationForm) {
kCFStringNormalizationFormD = 0, // Canonical Decomposition
kCFStringNormalizationFormKD, // Compatibility Decomposition
kCFStringNormalizationFormC, // Canonical Decomposition followed by Canonical Composition
kCFStringNormalizationFormKC // Compatibility Decomposition followed by Canonical Composition
};
所以,但判断fileList是否包含某个对象时最好这样写
if(![fileList containsObject: copyfileName]) {
CFStringNormalize((CFMutableStringRef)copyfileName, kCFStringNormalizationFormD);
if(![fileList containsObject: copyfileName]) {
NSLog(@"error!");
}
}
........