How do I convert a contained forced value to a contained optional value?

108 views Asked by At

Converting an optional value to a forced value works fairly simply:

    var aString: String? = "Hello"

    var anotherString: String = aString!

And it's even more simple in the opposite direction, because there's no unwrapping:

    var myString: String = "Hello"

    var myOtherString: String? = myString

It's a little more complicated to convert a forced value array containing optional values, to a forced value array containing forced values:

    var anArray: Array<String?> = ["Hello"]

    var anotherArray: Array<String> = anArray as Array<String>

What's a little different here is that you don't need the ! to unwrap the value. You're only telling it what type to expect.

Here's where I get stuck. Doing the opposite, to me, should look like this:

    var myArray: Array<String> = ["Hello"]

    var myOtherArray: Array<String?> = myArray as Array<String?>

But this gives the error:

'String' is not identical to 'String?'

Put simply as this, it gives the same error:

var myOtherArray: Array = myArray

I thought I had a fair grasp on this, but now I'm left unsure. How do I convert a contained forced value to a contained optional value (short of using a recreational for-loop)?

The recreational for-loop (not ideal):

    var myArray: Array<String> = ["Hello"]

    var myOtherArray: Array<String?> = []

    for loopString: String in myArray {
        myOtherArray.append(loopString)
    }
1

There are 1 answers

0
Martin R On BEST ANSWER

You have to create a new array by converting each element to an optional. But instead of a for-loop, you can use map():

var myArray = ["Hello"]
var myOtherArray = map(anotherArray) { Optional($0) }
println(myOtherArray) // [Optional("Hello")]

And your method for converting the other way around

var anArray: Array<String?> = ["Hello"]
var anotherArray: Array<String> = anArray as Array<String>

aborts with

fatal error: can't unsafeBitCast between types of different sizes

in my current Xcode 6.1. Using map() here works:

var anArray: Array<String?> = ["Hello"]
var anotherArray = map(anArray) { $0! }
println(anotherArray) // [Hello]

(Of course this will abort at runtime if any array element is nil.)