Swift4 range与NSRange互转,字符串查找

extension String {
    /// range转换为NSRange
    func nsRange(from range: Range<String.Index>) -> NSRange {
        return NSRange(range, in: self)
    }
}

使用示例

let languages = "Java,Swift,Objective-C"
let one = "Swift"
let range = languages.range(of: one)
let nsRange = "".nsRange(from: range!)
print(nsRange) // {5, 5}
extension String {
    /// NSRange转化为range
    func range(from nsRange: NSRange) -> Range<String.Index>? {
        guard
            let from16 = utf16.index(utf16.startIndex, offsetBy: nsRange.location, limitedBy: utf16.endIndex),
            let to16 = utf16.index(from16, offsetBy: nsRange.length, limitedBy: utf16.endIndex),
            let from = String.Index(from16, within: self),
            let to = String.Index(to16, within: self)
            else { return nil }
          return from ..< to
    }
}

字符串其他用法示例

1.在字符串中查找另一字符串首次出现的位置(或最后一次出现位置)

extension String {
    ///(如果backwards参数设置为true,则返回最后出现的位置)
    func positionOf(sub:String, backwards:Bool = false)->Int {
        // 如果没有找到就返回-1
        var pos = -1
        if let range = range(of:sub, options: backwards ? .backwards : .literal ) {
            if !range.isEmpty {
                pos = self.distance(from:startIndex, to:range.lowerBound)
            }
        }
        return pos
    }
}

使用示例

let str1 = "欢迎访问hangge.com。hangge.com做最好的开发者知识平台"
let str2 = "hangge"

let position1 = str1.positionOf(sub: str2)
print("子字符串第一次出现的位置是:\(position1)")
// 子字符串第一次出现的位置是:4
let position2 = str1.positionOf(sub: str2, backwards: true)
print("子字符串最后一次出现的位置是:\(position2)")
// 子字符串最后一次出现的位置是:15

2.使用下标截取字符串

extension String {
    /// 使用下标截取字符串 例: "示例字符串"[0..<2] 结果是 "示例"
    subscript (r: Range<Int>) -> String {
        get {
            if (r.lowerBound > count) || (r.upperBound > count) { return "截取超出范围" }
            let startIndex = self.index(self.startIndex, offsetBy: r.lowerBound)
            let endIndex = self.index(self.startIndex, offsetBy: r.upperBound)
            return String(self[startIndex..<endIndex])
        }
    }
}
// 示例
let str = "示例字符串"[0..<2]
print(str) // 示例

3.字符串截取第一个到第任意位置

extension String {
    /// 截取第一个到第任意位置
    ///
    /// - Parameter end: 结束的位值
    /// - Returns: 截取后的字符串
    func stringCut(end: Int) ->String{
        
        if !(end < self.count) { return "截取超出范围" }
        let sInde = index(startIndex, offsetBy: end)
        return String(self[...sInde])
    }
}
// 使用示例
let str = "示例字符串".stringCut(end: 2)
print(str) // 示例字

4.截取第任意位置到结束

extension String {
    /// 截取第任意位置到结束
    ///
    /// - Parameter end:
    /// - Returns: 截取后的字符串
    func stringCutToEnd(start: Int) -> String {
        if !(start < count) { return "截取超出范围" }
        let sRang = index(startIndex, offsetBy: start)
        //return substring(with: sRang)
        return String(self[sRang...])
    }
}
// 使用示例
let str = "示例字符串".stringCutToEnd(start: 3)
print(str) // 符串

5.字符串任意位置插入

extension String {
    /// 字符串任意位置插入
    ///
    /// - Parameters:
    ///   - content: 插入内容
    ///   - locat: 插入的位置
    /// - Returns: 添加后的字符串
    func stringInsert(content: String,locat: Int) -> String {
        if !(locat < count) { return "截取超出范围" }
        let str1 = stringCut(end: locat)
        let str2 = stringCutToEnd(start: locat+1)
        return str1 + content + str2
    }
}

// 示例
let str = "示例字符串".stringInsert(content: ",", locat: 1)
print(str) // 示例,字符串

6.字符串包含,前缀,后缀

let languages = "Java,Swift,Objective-C"
let flag1 = languages.contains("Java") // true
let flag2 = languages.hasPrefix("Swift") // false
let flag3 = languages.hasPrefix("Java") // true
let flag4 = languages.hasSuffix("Objective-C")// true

7.字符串大小写转换,首字符大写转换

let languages = "Java,Swift,Objective-C,js"
// 全部转换成大写
let languages_up = languages.uppercased() // JAVA,SWIFT,OBJECTIVE-C
// 全部转换成小写
let languages_lower = languages.lowercased() // java,swift,objective-c
// 首字母大写
let languages_first = languages.capitalized // Java,Swift,Objective-C,Js

8.字符串是否为空

let stringA = ""
if stringA.isEmpty {
    print( "stringA 是空的" )
} else {
    print( "stringA 不是空的" )
}

9.剔除字符串首尾空格

var stringA = " Swift Java"
stringA = stringA.trimmingCharacters(in: CharacterSet.whitespacesAndNewlines)

10.字符串遍历

let abc: String = "abc"
for c in abc {
    print(c)
}

11.字符串翻转

let abc: String = "abc"
print(String(abc.reversed()))// cba

12.reduce函数

let abc: String = "abc"
let result = abc.reduce("1") { (result, c) -> String in
    print(result)
    print(c)
    return result + String(c)
}
print(result) // 1abc

13.map函数应用

let abc: String = "abc"
let arr = abc.map {
    "\($0)" + "-hello"
}
print(arr) // ["a-hello", "b-hello", "c-hello"]

14.filter过滤函数应用

let abc: String = "abcdb"
let filtered = abc.filter { $0 == "b" }
print(filtered) // bb

字符串的翻转,遍历,map函数,reduce函数,filter函数用法与数组类似,猜测应该是遵守了Collection 协议,因此具备这些方法调用的能力

15.Swift4 字符串换行特殊符号"""

  • Swift 3 中写很长的字符串只能写在一行,字符串中间有换行只能通过添加 \n 字符来代表换行。
func tellJoke(name: String, character: Character) {
    let punchline = name.filter { $0 != character }
    let n = name.count - punchline.count
    let joke = """
        Q: Why does \(name) have \(n) \(character)'s in their name?
        A: I don't know, why does \(name) have \(n) \(character)'s in their name?
        Q: Because otherwise they'd be called \(punchline).
        """
    print(joke)
}

16.One-sided Slicing语法糖 ... 可以对字符串进行单侧边界取子串

let values = "abcdefg"
let startSlicingIndex = values.index(values.startIndex, offsetBy: 3)
let subvalues = values[startSlicingIndex...] // defg
let subvalues2 = values[...startSlicingIndex] // abcd

参考
最全的 Swift 4 新特性解析
Swift - 在字符串中查找另一字符串首次出现的位置(或最后一次出现位置)

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

推荐阅读更多精彩内容