67

I get compiler error at this line:

UIDevice.currentDevice().identifierForVendor.UUIDString.substringToIndex(8)

Type 'String.Index' does not conform to protocol 'IntegerLiteralConvertible'

My intention is to get the substring, but how?

idmean
  • 14,540
  • 9
  • 54
  • 83
János
  • 32,867
  • 38
  • 193
  • 353
  • more elegant solution **(** UIDevice.currentDevice().identifierForVendor.UUIDString **as NSString)**.substringToIndex(8) - need convert type – János Aug 04 '14 at 06:34

1 Answers1

185

In Swift, String indexing respects grapheme clusters, and an IndexType is not an Int. You have two choices - cast the string (your UUID) to an NSString, and use it as "before", or create an index to the nth character.

Both are illustrated below :

However, the method has changed radically between versions of Swift. Read down for later versions...

Swift 1

let s: String = "Stack Overflow"
let ss1: String = (s as NSString).substringToIndex(5) // "Stack"
//let ss2: String = s.substringToIndex(5)// 5 is not a String.Index
let index: String.Index = advance(s.startIndex, 5)
let ss2:String = s.substringToIndex(index) // "Stack"

CMD-Click on substringToIndex confusingly takes you to the NSString definition, however CMD-Click on String and you will find the following:

extension String : Collection {
    struct Index : BidirectionalIndex, Reflectable {
        func successor() -> String.Index
        func predecessor() -> String.Index
        func getMirror() -> Mirror
    }
    var startIndex: String.Index { get }
    var endIndex: String.Index { get }
    subscript (i: String.Index) -> Character { get }
    func generate() -> IndexingGenerator<String>
}

Swift 2
As commentator @DanielGalasko points out advance has now changed...

let s: String = "Stack Overflow"
let ss1: String = (s as NSString).substringToIndex(5) // "Stack"
//let ss2: String = s.substringToIndex(5)// 5 is not a String.Index
let index: String.Index = s.startIndex.advancedBy(5) // Swift 2
let ss2:String = s.substringToIndex(index) // "Stack"

Swift 3
In Swift 3, it's changed again:

let s: String = "Stack Overflow"
let ss1: String = (s as NSString).substring(to: 5) // "Stack"
let index: String.Index = s.index(s.startIndex, offsetBy: 5)
var ss2: String = s.substring(to: index) // "Stack"

Swift 4
In Swift 4, yet another change:

let s: String = "Stack Overflow"
let ss1: String = (s as NSString).substring(to: 5) // "Stack"
let index: String.Index = s.index(s.startIndex, offsetBy: 5)
var ss3: Substring = s[..<index] // "Stack"
var ss4: String = String(s[..<index]) // "Stack"
Grimxn
  • 22,115
  • 10
  • 72
  • 85