0

I am encountering a random crash in the NSRange creation. Because I added a check before, I do not understand how it can happen:

let textStr = "whatever you want"   
if let end = textStr.unicodeScalars.index(textStr.startIndex, offsetBy: slide.endIndex, limitedBy: textStr.endIndex){
    let realEnd = textStr.unicodeScalars.index(textStr.startIndex, offsetBy: slide.endIndex)
    nsRange = NSRange(start...realEnd, in: textStr)
}
  • slide is an object generated by a parser and representing a portion of textStr.
  • Parser uses textStr.unicodeScalars for performances reasons
AP.
  • 5,205
  • 7
  • 50
  • 94
  • 1
    What is `slide`, what is `start`, what error message do you get? – Joakim Danielson Jan 25 '20 at 16:09
  • 2
    You can't use the String Index from a different string. Btw why are you using unicodeScalars index? Related https://stackoverflow.com/a/43233619/2303865 – Leo Dabus Jan 25 '20 at 16:09
  • 1
    Most likely it's just `start.. – vadian Jan 25 '20 at 16:14
  • Added more context in initial question – AP. Jan 25 '20 at 16:24
  • @vadian I do not think that this is the issue (using your code does not take last char of the slide into account) – AP. Jan 25 '20 at 16:32
  • 2
    It was just a shot in the dark, you should add a reproducible example with a concrete value for `slide`. And what are the *performances reasons* you are talking about? The `String` API in Swift is highly optimized. – vadian Jan 25 '20 at 16:36
  • regarding **"using your code does not take last char of the slide into account"** comment you need to limit your method using the index before the end. Check out the `BidirectionalCollection` extension at https://stackoverflow.com/a/38215613/2303865 as reference – Leo Dabus Jan 25 '20 at 19:38
  • @vadian for a parser, using the String API is a dozen of time slower than using `unicodeScalars` – AP. Jan 27 '20 at 10:55

1 Answers1

0

This works in a Playground:

import Foundation

let textStr = "whatever you want"
let slide = "you"
let start = slide.startIndex // not sure what this was meant to be in your code
if textStr.index(textStr.unicodeScalars.startIndex, offsetBy: slide.unicodeScalars.distance(from: slide.startIndex, to: slide.endIndex), limitedBy: textStr.unicodeScalars.endIndex) != nil {
    let realEnd = textStr.index(textStr.unicodeScalars.startIndex, offsetBy: slide.unicodeScalars.distance(from: slide.unicodeScalars.startIndex, to: slide.unicodeScalars.endIndex))
    let nsRange = NSRange(start..<realEnd, in: textStr)
}

Seems like a weird way to go about this though. Perhaps rethink your approach.

Infinity James
  • 4,667
  • 5
  • 23
  • 36
  • What if there is more than one occurrence of "you" at textStr? – Leo Dabus Jan 25 '20 at 18:46
  • Btw try `let textStr = "Hello USA !!! Hello World !!!"`and `let slide = "!!!"` and use the resulting range `start.. – Leo Dabus Jan 25 '20 at 18:48
  • I am not so proud of this code. Given I have the caret position in an NSTextView and a set `unicodeScalars`, what would you do? – AP. Jan 27 '20 at 10:54