最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

深入理解Swift中的Substring和String

 更新時間:2018年03月23日 08:29:00   作者:Greg Heo (@gregheo)  
這篇文章主要給大家深入的介紹了Swift中Substring和String的相關(guān)資料,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧。

前言

為文本字符串添加特性或者語法糖在各種編程語言中都很普遍。就拿大家都很熟悉的 C 語言舉例,C 字符串本質(zhì)是一個字符數(shù)組(characters array),但是每次輸入字符串的時候不用輸入 ['h','e','l','l','o'] ,直接打 hello 就可以了,因?yàn)檫@個操作編譯器幫你做了。

更高級的語言比如 Swift 處理字符串就不僅僅是當(dāng)做字符數(shù)組了,String 是一個完整的類型,并且有各種特性。我們先來看一下 String 的一個特性:substring。

簡單的看一下 String

首先粗略的了解一下字符串的實(shí)現(xiàn)。下面的代碼來自標(biāo)準(zhǔn)庫中 String.swift :

public struct String {
 public var _core: _StringCore
}

當(dāng)然也有一些其他初始化設(shè)置,不過在聲明里只有這一個存儲屬性!秘密一定都在 StringCore.swift 里:

public struct _StringCore {
 public var _baseAddress: UnsafeMutableRawPointer?
 var _countAndFlags: UInt
 public var _owner: AnyObject?
}

在這個類型里還有很多其他東西,不過我們還是只關(guān)注存儲屬性:

  • Base address — 一個指向內(nèi)部存儲的指針
  • Count — 字符串長度,UInt 類型,在一個 64 位的系統(tǒng)中,意味著有 62(64 - 2) 位的空間可以表示長度。這是一個非常大的數(shù)字。所以字符串的長度不太可能溢出。
  • Flags — 兩個 bits 用來做標(biāo)志。第一位表示是否被 _StringBuffer 持有;第二位表示編碼格式是 ASCII 還是 UTF-16。

_StringCore 的真實(shí)情況比這里提到的要復(fù)雜的多,但是通過上面的內(nèi)容可以讓我們更容易理解字符串的一些信息:字符串的內(nèi)部存儲和存儲的大小(underlying storage and size)。

Substring

Swift 中要怎么創(chuàng)建一個 substring?最簡單的方式就是通過下標(biāo)從 string 取一段:

let str = "Hello Swift!"
let slice = str[str.startIndex..
<str index="" str="" startindex="" nbsp="" offsetby:="" 5="" hello=""></str>

雖然很簡單,但是代碼看起來不太優(yōu)雅。

String 的索引不是直觀的整型,所以截取時的位置索引需要利用 startIndex 和 index(_:offsetBy:)獲取。如果是從字符串開始位置截取,可以省略掉 startIndex :

let withPartialRange = str[..
<str index="" str="" startindex="" nbsp="" offsetby:="" 5="" still="" hello=""></str>

或者用 collection 中的這個方法:

let slice = str.prefix(5)
// still "Hello"

要記住字符串也是 collection ,所以你可以用集合下的方法,比如 prefix(),suffix(), dropFirst() 等。

Substring 的內(nèi)部原理

substring 一個神奇的地方是他們重用了父 string 的內(nèi)存。你可以把 substring 理解為父 string 的其中一段。

舉個例子,如果從一個 8000 個字符的字符串中截取 100 個字符,并不需要重新初始化 100 個字符的內(nèi)存空間。

這也意味著你可能不小心就把父 string 的生命周期延長了。如果有一大段字符串,然后你只是截取了一小段,只要截取的小段字符串沒有釋放,大段的字符串也不會被釋放。

Substring 內(nèi)部到底是怎么做到的呢?

public struct Substring {
 internal var _slice: RangeReplaceableBidirectionalSlice
<string></string>

內(nèi)部的 _slice 屬性保存著所有關(guān)于父字符串的信息:

// Still inside Substring
internal var _wholeString: String {
 return _slice._base
}
public var startIndex: Index { return _slice.startIndex }
public var endIndex: Index { return _slice.endIndex }

計(jì)算屬性 _wholeString(返回整個父字符串),startIndex 和 endIndex 都是通過內(nèi)部的 _slice 返回。

也可以看出 slice 是如何引用父字符串的。

Substring 轉(zhuǎn)換為 String

最后代碼里可能有很多 substring,但是函數(shù)的參數(shù)類型需要的是 string。Substring 轉(zhuǎn)換到 string 的過程也很簡單:

let string = String(substring)

因?yàn)?substrings 和它的父字符串共享同一個內(nèi)存空間,猜測創(chuàng)建一個新字符串應(yīng)該會初始化一片新的存儲空間。那么 string 的初始化到底過程是怎樣的呢。

extension String {
 public init(_ substring: Substring) {
 // 1
 let x = substring._wholeString
 // 2
 let start = substring.startIndex
 let end = substring.endIndex
 // 3
 let u16 = x._core[start.encodedOffset..
<end encodedoffset="" nbsp="" 4a="" if="" start="" sameposition="" in:="" x="" unicodescalars="" end="" self="" 4b="" else=""></end>
  • 創(chuàng)建一個對原有父字符串的引用
  • 獲取 substring 在父字符串中的開始和結(jié)束位置
  • 獲取 UTF-16 格式的 substring 內(nèi)容。_core 是 _StringCore 的一個實(shí)例。
  • 判斷匹配的 unicode 編碼,生成一個新的字符串實(shí)例

把 substring 轉(zhuǎn)換成 string 的步驟非常簡單,但是你可能要考慮是不是一需要這樣做。是不是進(jìn)行 substring 操作的時候都要求類型是 string?如果對 substring 的操作都需要轉(zhuǎn)成 string,那么輕量級的 substring 也就失去了意義。

總結(jié)

以上就是這篇文章的全部內(nèi)容了,希望本文的內(nèi)容對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,如果有疑問大家可以留言交流,謝謝大家對腳本之家的支持。

相關(guān)文章

  • Springboot實(shí)現(xiàn)XSS漏洞過濾的示例代碼

    Springboot實(shí)現(xiàn)XSS漏洞過濾的示例代碼

    這篇文章主要介紹了Springboot實(shí)現(xiàn)XSS漏洞過濾的示例代碼,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-01-01
  • Java使用poi實(shí)現(xiàn)excel的導(dǎo)入操作指南

    Java使用poi實(shí)現(xiàn)excel的導(dǎo)入操作指南

    使用Apache Poi是一種流行且廣泛使用的方式,可以幫助開發(fā)人員直接從Java代碼中讀取、寫入和處理Excel文件,因此在這篇文章我們將著重介紹如何實(shí)現(xiàn)excel的導(dǎo)入,感興趣的朋友可以跟著小編一起來學(xué)習(xí)
    2023-06-06
  • 解決idea 項(xiàng)目編譯后沒有class文件的問題

    解決idea 項(xiàng)目編譯后沒有class文件的問題

    這篇文章主要介紹了解決idea 項(xiàng)目編譯后沒有class文件的問題,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2020-12-12
  • JDK8 new ReentrantLock((true)加鎖流程

    JDK8 new ReentrantLock((true)加鎖流程

    這篇文章主要介紹了java面試中常遇到的問題JDK8 new ReentrantLock((true)加鎖流程示例解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-07-07
  • Java8中Lambda表達(dá)式的理解與應(yīng)用

    Java8中Lambda表達(dá)式的理解與應(yīng)用

    Java8最值得學(xué)習(xí)的特性就是Lambda表達(dá)式和Stream?API,如果有python或者javascript的語言基礎(chǔ),對理解Lambda表達(dá)式有很大幫助,下面這篇文章主要給大家介紹了關(guān)于Java8中Lambda表達(dá)式的相關(guān)資料,需要的朋友可以參考下
    2022-02-02
  • 詳細(xì)總結(jié)IDEA中打jar包的兩種方式

    詳細(xì)總結(jié)IDEA中打jar包的兩種方式

    發(fā)現(xiàn)有很多小伙伴都不會用IDEA打jar包,今天給大家詳細(xì)總結(jié)了兩種IDEA打jar包的方式,對正在學(xué)習(xí)IDEA使用的小伙伴很有幫助,需要的朋友可以參考下
    2021-05-05
  • 如何使用Spring boot的@Transactional進(jìn)行事務(wù)管理

    如何使用Spring boot的@Transactional進(jìn)行事務(wù)管理

    這篇文章介紹了SpringBoot中使用@Transactional注解進(jìn)行聲明式事務(wù)管理的詳細(xì)信息,包括基本用法、核心配置參數(shù)、關(guān)鍵注意事項(xiàng)、調(diào)試技巧、最佳實(shí)踐以及完整示例,感興趣的朋友一起看看吧
    2025-02-02
  • java繪制國際象棋與中國象棋棋盤

    java繪制國際象棋與中國象棋棋盤

    這篇文章主要為大家詳細(xì)介紹了java繪制國際象棋與中國象棋棋盤,文中示例代碼介紹的非常詳細(xì),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-05-05
  • Spring MVC多種情況下進(jìn)行文件上傳的實(shí)例

    Spring MVC多種情況下進(jìn)行文件上傳的實(shí)例

    上傳是Web工程中很常見的功能,SpringMVC框架簡化了文件上傳的代碼,本文給大家總結(jié)了Spring MVC多種情況下進(jìn)行文件上傳的實(shí)例,并通過代碼示例給大家介紹的非常詳細(xì),需要的朋友可以參考下
    2024-02-02
  • 解決springboot遇到autowire注入為null的問題

    解決springboot遇到autowire注入為null的問題

    這篇文章主要介紹了解決springboot遇到autowire注入為null的問題,具有很好的參考價值,希望對大家有所幫助。一起跟隨小編過來看看吧
    2021-03-03

最新評論

樟树市| 河池市| 福安市| 顺平县| 盘锦市| 盐源县| 广州市| 东乌珠穆沁旗| 定安县| 扎兰屯市| 竹北市| 布拖县| 厦门市| 高雄市| 舒兰市| 信宜市| 漯河市| 桑日县| 崇文区| 常熟市| 团风县| 卫辉市| 宜黄县| 陆丰市| 上栗县| 西昌市| 喜德县| 嘉祥县| 仙游县| 辽宁省| 英吉沙县| 广南县| 乐安县| 鹿泉市| 仁布县| 潮州市| 仙居县| 星座| 金川县| 高密市| 沈阳市|