Search code examples
xcodeswiftfreezeswift-playground

Xcode freezes when trying to execute this in a Swift playground?


I was simply experimenting with Swift, so I threw together this in my playground:

// Playground - noun: a place where people can play

import Cocoa

func printCarInfo(car:Car?) -> Void {
    if let _car = car {
        println("This is a " + _car.make + " " + _car.model + " from \(_car.year). It's worth $" + _car.price + ".")
    }
}

class Car {
    init(make:String, model:String, year:UInt, color:NSColor, price:UInt) {
        self.make   = make
        self.model  = model
        self.year   = year
        self.color  = color
        self.price  = price
    }

    var make    : String
    var model   : String
    var year    : UInt
    var color   : NSColor
    var price   : UInt

    func isNewCar() -> Bool {
        let _formatter = NSDateFormatter()
        _formatter.dateFormat = "yyyy"
        let _currentYear = _formatter.stringFromDate(NSDate())
        return (_currentYear == String(self.year))
    }


}

let chevy = Car(make: "Chevrolet", model: "Camaro ZL1", year: 2014, color: NSColor.redColor(), price: 55355)

printCarInfo(chevy)

Very straight forward code, there's nothing complicated about it. But Xcode doesn't execute it. The little loading indicator in the bottom right keeps spinning, my macbook gets hot, the fans spin up, and nothing's happening. If I modify the println command in the printCarInfo(car:Car?) -> Void function to something like this:

println("Ok")

Then it's totally fine. But as soon as I put this line in:

println("This is a " + _car.make + " " + _car.model + " from \(_car.year). It's worth $" + _car.price + ".")

Xcode freezes like I described above. I tried saving the playground and reopening it, but the same thing happens every time.

I don't think there's anything wrong with the code. Is is just a bug in Xcode beta? Can anyone try to paste this into a playground and see what happens? It's an OS X playground and I use Xcode beta 5. Also, I'm on 10.10 DP5.


Solution

  • Definitely a bug in Xcode. There seems to be an issue with Compiler concatenating more than 5 strings in a single line execution. Below is my analysis:

    Currently you can concatenate maximum of 5 or 6 strings in a single line execution (It is not a feature, it's a bug). For e.g. Try this in Playground:

    var tstr = "A" + "B" + "C" + "D" + "E" + "F" + "G"
    

    or

    println("A" + "B" + "C" + "D" + "E" + "F");
    

    This execution hangs the Xcode and increases the Mac's CPU usage to 200%.

    Here's a strange fact. Now try this:

    var tstr = "A" + "B" + "C" + "D" + "E"
    tstr = tstr + "F" + "G"
    println(tstr) //Correct output: ABCDEFG
    

    So that seems to be the way around solution to this issue. Break and Concatenate.

    But your code also has one minor bug. You are concatenating UInt and a string. _car.price is of UInt type and you cannot directly concatenate it with a string. So either you use String conversion or use String interpolation. Below is how your above code will work:

    with UInt to String conversion

    var str = "This is a " + _car.make + " "
    str = str + _car.model + " from \(_car.year). It's worth $" + String(_car.price) +  "."
    println(str) //Prints: This is a Chevrolet Camaro ZL1 from 2014. It's worth $55355.
    

    or

    with String Interpolation

    var str = "This is a " + _car.make + " "
    str = str + _car.model + " from \(_car.year). It's worth $ \(_car.price)."
    println(str)//Same output: This is a Chevrolet Camaro ZL1 from 2014. It's worth $55355.