你如何使用String.substringWithRange?(或者,Ranges如何在Swift中工作?)

 海边遗忘的时光_958 发布于 2023-01-11 16:42

我还没有弄清楚如何String在Swift中获取a的子串:

var str = “Hello, playground”
func test(str: String) -> String {
 return str.substringWithRange( /* What goes here? */ )
}
test (str)

我无法在Swift中创建一个Range.游乐场中的自动填充功能并不是非常有用 - 这就是它的建议:

return str.substringWithRange(aRange: Range)

我没有在Swift标准参考库中找到任何有帮助的内容.这是另一个疯狂的猜测:

return str.substringWithRange(Range(0, 1))

还有这个:

let r:Range = Range(start: 0, end: 2)
return str.substringWithRange(r)

我已经看到其他答案(查找Swift字符串中的字符索引)似乎表明,因为它String是一种桥接类型NSString,"旧"方法应该有效,但是不清楚如何 - 例如,这也不起作用(似乎不是有效的语法):

let x = str.substringWithRange(NSMakeRange(0, 3))

思考?

15 个回答
  • 您可以使用substringWithRange方法.它需要一个开始和结束String.Index.

    var str = "Hello, playground"
    str.substringWithRange(Range<String.Index>(start: str.startIndex, end: str.endIndex)) //"Hello, playground"
    

    要更改开始和结束索引,请使用advancedBy(n).

    var str = "Hello, playground"
    str.substringWithRange(Range<String.Index>(start: str.startIndex.advancedBy(2), end: str.endIndex.advancedBy(-1))) //"llo, playgroun"
    

    你仍然可以在NSRange中使用NSString方法,但是你必须确保使用这样的NSString:

    let myNSString = str as NSString
    myNSString.substringWithRange(NSRange(location: 0, length: 3))
    

    注意:正如JanX2所提到的,第二种方法对于unicode字符串是不安全的.

    2023-01-11 16:42 回答
  • 在我写作的时候,没有任何扩展与Swift 4.2兼容,所以这里有一个涵盖了我能想到的所有需求:

    extension String {
        func substring(from: Int?, to: Int?) -> String {
            if let start = from {
                guard start < self.count else {
                    return ""
                }
            }
    
            if let end = to {
                guard end >= 0 else {
                    return ""
                }
            }
    
            if let start = from, let end = to {
                guard end - start >= 0 else {
                    return ""
                }
            }
    
            let startIndex: String.Index
            if let start = from, start >= 0 {
                startIndex = self.index(self.startIndex, offsetBy: start)
            } else {
                startIndex = self.startIndex
            }
    
            let endIndex: String.Index
            if let end = to, end >= 0, end < self.count {
                endIndex = self.index(self.startIndex, offsetBy: end + 1)
            } else {
                endIndex = self.endIndex
            }
    
            return String(self[startIndex ..< endIndex])
        }
    
        func substring(from: Int) -> String {
            return self.substring(from: from, to: nil)
        }
    
        func substring(to: Int) -> String {
            return self.substring(from: nil, to: to)
        }
    
        func substring(from: Int?, length: Int) -> String {
            guard length > 0 else {
                return ""
            }
    
            let end: Int
            if let start = from, start > 0 {
                end = start + length - 1
            } else {
                end = length - 1
            }
    
            return self.substring(from: from, to: end)
        }
    
        func substring(length: Int, to: Int?) -> String {
            guard let end = to, end > 0, length > 0 else {
                return ""
            }
    
            let start: Int
            if let end = to, end - length > 0 {
                start = end - length + 1
            } else {
                start = 0
            }
    
            return self.substring(from: start, to: to)
        }
    }
    

    然后,您可以使用:

    let string = "Hello,World!"
    

    string.substring(from: 1, to: 7)得到你: ello,Wo

    string.substring(to: 7)得到你: Hello,Wo

    string.substring(from: 3)得到你: lo,World!

    string.substring(from: 1, length: 4)得到你: ello

    string.substring(length: 4, to: 7)得到你: o,Wo

    更新substring(from: Int?, length: Int)以支持从零开始.

    2023-01-11 16:42 回答
  • 一旦找到正确的语法,它就比这里的任何答案简单得多.

    我想带走[和]

    let myString = "[ABCDEFGHI]"
    let startIndex = advance(myString.startIndex, 1) //advance as much as you like
    let endIndex = advance(myString.endIndex, -1)
    let range = startIndex..<endIndex
    let myNewString = myString.substringWithRange( range )
    

    结果将是"ABCDEFGHI",startIndex和endIndex也可用于

    let mySubString = myString.substringFromIndex(startIndex)
    

    等等!

    PS:正如备注中所示,swift 2中有一些语法更改,包括xcode 7和iOS9!

    请看这个页面

    2023-01-11 16:42 回答
  • SWIFT 2.0

    简单:

    let myString = "full text container"
    let substring = myString[myString.startIndex..<myString.startIndex.advancedBy(3)] // prints: ful
    

    SWIFT 3.0

    let substring = myString[myString.startIndex..<myString.index(myString.startIndex, offsetBy: 3)] // prints: ful
    

    SWIFT 4.0

    子串操作返回Substring类型的实例,而不是String.

    let substring = myString[myString.startIndex..<myString.index(myString.startIndex, offsetBy: 3)] // prints: ful
    
    // Convert the result to a String for long-term storage.
    let newString = String(substring)
    

    2023-01-11 16:43 回答
  • 斯威夫特2

    简单

    let str = "My String"
    let subStr = str[str.startIndex.advancedBy(3)...str.startIndex.advancedBy(7)]
    //"Strin"
    

    斯威夫特3

    let startIndex = str.index(str.startIndex, offsetBy: 3)
    let endIndex = str.index(str.startIndex, offsetBy: 7)
    
    str[startIndex...endIndex]       // "Strin"
    str.substring(to: startIndex)    // "My "
    str.substring(from: startIndex)  // "String"
    

    斯威夫特4

    substring(to:)并且substring(from:)已弃用Swift 4.

    String(str[..<startIndex])    // "My "
    String(str[startIndex...])    // "String"
    String(str[startIndex...endIndex])    // "Strin"
    

    2023-01-11 16:43 回答
  • 例如,以我的全名查找名字(直到第一个空格):

    let name = "Joris Kluivers"
    
    let start = name.startIndex
    let end = find(name, " ")
    
    if end {
        let firstName = name[start..end!]
    } else {
        // no space found
    }
    

    start并且endString.Index这里是类型Range<String.Index>,用于在下标访问器中创建和使用(如果在原始字符串中找到空格).

    很难String.Index直接从开头文章中使用的整数位置创建.这是因为在我的名字中,每个字符的大小都是相等的.但是在其他语言中使用特殊重音的字符可能使用了几个字节(取决于所使用的编码).那么整数应该指的是什么字节?

    可以String.Index使用这些方法从现有方法创建一个新的succ,pred这将确保跳过正确的字节数以到达编码中的下一个代码点.但是在这种情况下,更容易搜索字符串中第一个空格的索引以查找结束索引.

    2023-01-11 16:43 回答
  • 在新的Xcode 7.0中使用

    //: Playground - noun: a place where people can play
    
    import UIKit
    
    var name = "How do you use String.substringWithRange?"
    let range = name.startIndex.advancedBy(0)..<name.startIndex.advancedBy(10)
    name.substringWithRange(range)
    
    //OUT:
    

    在此输入图像描述

    2023-01-11 16:43 回答
  • 由于String是NSString的桥接类型,"旧"方法应该可以工作,但是不清楚如何 - 例如,这也不起作用(似乎不是有效的语法):

     let x = str.substringWithRange(NSMakeRange(0, 3))
    

    对我来说,这是你问题中非常有趣的部分.字符串桥接到的NSString,所以大多数的NSString方法在一根绳子上直接工作.您可以自由地使用它们而无需考虑.因此,例如,这可以像您期望的那样工作:

    // delete all spaces from Swift String stateName
    stateName = stateName.stringByReplacingOccurrencesOfString(" ", withString:"")
    

    但是,正如经常发生的那样,"我得到了我的魔力,但它对你不起作用." 你碰巧选择了一种罕见的情况,其中存在一个并行的同名Swift方法,在这种情况下,Swift方法掩盖了Objective-C方法.因此,当你说str.substringWithRange,Swift认为你的意思是Swift方法而不是NSString方法 - 然后你就被软管了,因为Swift方法需要一个Range<String.Index>,而你不知道如何制作其中一个.

    最简单的方法是通过显式转换来阻止Swift像这样黯然失色:

    let x = (str as NSString).substringWithRange(NSMakeRange(0, 3))
    

    请注意,此处不涉及重要的额外工作."演员"并不意味着"转换"; String 实际上是一个NSString.我们只是告诉Swift如何在这一行代码中查看此变量.

    整个事情中非常奇怪的部分是导致所有这些麻烦的Swift方法没有记录.我不知道它的定义在哪里; 它不在NSString头中,也不在Swift头中.

    2023-01-11 16:43 回答
  • 有关如何在Swift 2.0中获取子字符串的示例代码

    (i)起始索引的子串

    输入: -

    var str = "Swift is very powerful language!"
    print(str)
    
    str = str.substringToIndex(str.startIndex.advancedBy(5))
    print(str)
    

    输出: -

    Swift is very powerful language!
    Swift
    

    (ii)来自特定指数的子串

    输入: -

    var str = "Swift is very powerful language!"
    print(str)
    
    str = str.substringFromIndex(str.startIndex.advancedBy(6)).substringToIndex(str.startIndex.advancedBy(2))
    print(str)
    

    输出: -

    Swift is very powerful language!
    is
    

    我希望它会对你有所帮助!

    2023-01-11 16:43 回答
  • 简短的回答是,现在Swift真的很难.我的预感是苹果仍然有很多工作要做方便的方法来做这样的事情.

    String.substringWithRange()期待一个Range<String.Index>参数,据我所知,该String.Index类型没有生成器方法.你可以String.Index从它们那里得到价值,aString.startIndex然后aString.endIndex再打电话.succ()或者打电话.pred()给他们,但这很疯狂.

    如果String类上的扩展需要很好的旧Ints?

    extension String {
        subscript (r: Range<Int>) -> String {
            get {
                let subStart = advance(self.startIndex, r.startIndex, self.endIndex)
                let subEnd = advance(subStart, r.endIndex - r.startIndex, self.endIndex)
                return self.substringWithRange(Range(start: subStart, end: subEnd))
            }
        }
        func substring(from: Int) -> String {
            let end = countElements(self)
            return self[from..<end]
        }
        func substring(from: Int, length: Int) -> String {
            let end = from + length
            return self[from..<end]
        }
    }
    
    let mobyDick = "Call me Ishmael."
    println(mobyDick[8...14])             // Ishmael
    
    let dogString = "This 's name is Patch."
    println(dogString[5..<6])               // 
    println(dogString[5...5])              // 
    println(dogString.substring(5))        // 's name is Patch.
    println(dogString.substring(5, length: 1))   // 
    

    更新: Swift beta 4解决了以下问题!

    由于它处于[beta 3及更早版本],即使是Swift本地字符串也存在处理Unicode字符的一些问题.上面的狗图标工作,但以下不是:

    let harderString = "1:1??"
    for character in harderString {
        println(character)
    }
    

    输出:

    1
    :
    1
    ?
    ?
    

    2023-01-11 16:43 回答
  • 您可以使用此扩展程序进行改进 substringWithRange

    斯威夫特2.3

    extension String
    {   
        func substringWithRange(start: Int, end: Int) -> String
        {
            if (start < 0 || start > self.characters.count)
            {
                print("start index \(start) out of bounds")
                return ""
            }
            else if end < 0 || end > self.characters.count
            {
                print("end index \(end) out of bounds")
                return ""
            }
            let range = Range(start: self.startIndex.advancedBy(start), end: self.startIndex.advancedBy(end))
            return self.substringWithRange(range)
        }
    
        func substringWithRange(start: Int, location: Int) -> String
        {
            if (start < 0 || start > self.characters.count)
            {
                print("start index \(start) out of bounds")
                return ""
            }
            else if location < 0 || start + location > self.characters.count
            {
                print("end index \(start + location) out of bounds")
                return ""
            }
            let range = Range(start: self.startIndex.advancedBy(start), end: self.startIndex.advancedBy(start + location))
            return self.substringWithRange(range)
        }
    }
    

    斯威夫特3

    extension String
    {
        func substring(start: Int, end: Int) -> String
        {
            if (start < 0 || start > self.characters.count)
            {
                print("start index \(start) out of bounds")
                return ""
            }
            else if end < 0 || end > self.characters.count
            {
                print("end index \(end) out of bounds")
                return ""
            }
            let startIndex = self.characters.index(self.startIndex, offsetBy: start)
            let endIndex = self.characters.index(self.startIndex, offsetBy: end)
            let range = startIndex..<endIndex
    
            return self.substring(with: range)
        }
    
        func substring(start: Int, location: Int) -> String
        {
            if (start < 0 || start > self.characters.count)
            {
                print("start index \(start) out of bounds")
                return ""
            }
            else if location < 0 || start + location > self.characters.count
            {
                print("end index \(start + location) out of bounds")
                return ""
            }
            let startIndex = self.characters.index(self.startIndex, offsetBy: start)
            let endIndex = self.characters.index(self.startIndex, offsetBy: start + location)
            let range = startIndex..<endIndex
    
            return self.substring(with: range)
        }
    }
    

    用法:

    let str = "Hello, playground"
    
    let substring1 = str.substringWithRange(0, end: 5) //Hello
    let substring2 = str.substringWithRange(7, location: 10) //playground
    

    2023-01-11 16:43 回答
  • 这适用于我的操场:)

    String(seq: Array(str)[2...4])
    

    2023-01-11 16:45 回答
  • 更新了Xcode 7.添加字符串扩展名:

    使用:

    var chuck: String = "Hello Chuck Norris"
    chuck[6...11] // => Chuck
    

    执行:

    extension String {
    
        /**
         Subscript to allow for quick String substrings ["Hello"][0...1] = "He"
         */
        subscript (r: Range<Int>) -> String {
            get {
                let start = self.startIndex.advancedBy(r.startIndex)
                let end = self.startIndex.advancedBy(r.endIndex - 1)
                return self.substringWithRange(start..<end)
            }
        }
    
    }
    

    2023-01-11 16:45 回答
  • 使用少量代码轻松解决问题

    制作一个包含几乎所有其他语言都具有的基本subStringing的扩展:

    extension String {
        func subString(start: Int, end: Int) -> String {
            let startIndex = self.index(self.startIndex, offsetBy: start)
            let endIndex = self.index(startIndex, offsetBy: end)
    
            let finalString = self.substring(from: startIndex)
            return finalString.substring(to: endIndex)
        }
    }
    

    简单地称之为

    someString.subString(start: 0, end: 6)
    

    2023-01-11 16:45 回答
  • 注意:@airspeedswift 对这种方法的权衡取得了一些非常有见地的观点,尤其是隐藏的性能影响.字符串不是简单的野兽,并且到达特定索引可能花费O(n)时间,这意味着使用下标的循环可以是O(n ^ 2).你被警告了.

    您只需添加一个新subscript功能,该功能需要一个范围并用于advancedBy()步行到您想要的位置:

    import Foundation
    
    extension String {
        subscript (r: Range<Int>) -> String {
            get {
                let startIndex = self.startIndex.advancedBy(r.startIndex)
                let endIndex = startIndex.advancedBy(r.endIndex - r.startIndex)
    
                return self[Range(start: startIndex, end: endIndex)]
            }
        }
    }
    
    var s = "Hello, playground"
    
    println(s[0...5]) // ==> "Hello,"
    println(s[0..<5]) // ==> "Hello"
    

    (这绝对应该是语言的一部分.请填写:rdar:// 17158813)

    为了好玩,您还可以+在索引上添加运算符:

    func +<T: ForwardIndex>(var index: T, var count: Int) -> T {
      for (; count > 0; --count) {
        index = index.succ()
      }
      return index
    }
    
    s.substringWithRange(s.startIndex+2 .. s.startIndex+5)
    

    (我还不知道这个是否应该成为该语言的一部分.)

    2023-01-11 16:45 回答
撰写答案
今天,你开发时遇到什么问题呢?
立即提问
热门标签
PHP1.CN | 中国最专业的PHP中文社区 | PNG素材下载 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有