2014-06-14 30 views
0

在我UIFontExtension.swift文件,我得到的是指明瞭斯威夫特編譯器錯誤...可選類型'NSNumber'的值未解包;你的意思是使用'!'要麼 '?'?

Value of optional type 'NSNumber' not unwrapped; did you mean to use '!' or '?'?

此錯誤指向w!h!上,我都不得不結束註釋行。

import Foundation 
import UIKit 

extension UIFont { 
    func sizeOfString (string: String, maxWidth w: CGFloat?, maxHeight h: CGFloat?) -> CGSize { 
    var width = w != nil ? w! : DBL_MAX // Error on this line 
    var height = h != nil ? h! : DBL_MAX // And on this line 
    var size = CGSize(width: width, height: height) 
    var options = NSStringDrawingOptions.UsesLineFragmentOrigin 
    var attributes = [NSFontAttributeName: self] 
    var nsstring = NSString(string: string) 
    return nsstring.boundingRectWithSize(size, options: options, attributes: attributes, context: nil).size 
    } 
} 

這只是一個錯誤?

+0

我斯威夫特REPL不會產生你所描述的錯誤。 – GoZoner

+0

有趣。如果不使用本地別名(在函數中使用maxWidth和maxHeight而不是w和h),它會發生嗎? –

回答

1

哦,等等,我認爲問題(可能)是該分配被解釋爲比比較更高的優先級。編譯器不知道比較是應該用於整個賦值還是僅用於賦值的表達式。嘗試添加括號:

extension UIFont { 
    func sizeOfString (string: String, maxWidth w: CGFloat?, maxHeight h: CGFloat?) -> CGSize { 
    var width = (w != nil ? w! : DBL_MAX) // Error on this line 
    var height = (h != nil ? h! : DBL_MAX) // And on this line 
    var size = CGSize(width: width, height: height) 
    var options = NSStringDrawingOptions.UsesLineFragmentOrigin 
    var attributes = [NSFontAttributeName: self] 
    var nsstring = NSString(string: string) 
    return nsstring.boundingRectWithSize(size, options: options, attributes: attributes, context: nil).size 
    } 
} 

我認爲,如果沒有括號,在分配被解釋爲:

(var width = w) != nil ? w! : DBL_MAX // Error on this line 
+0

太棒了!你是對的。這是最簡單的解決方案。 – aleclarson

+0

@aleclarson:我認爲它仍然是一個錯誤,因爲如果它是真的,編譯器應該推斷類型爲'GFloat?'而不是'GFloat'。 –

+0

@aleclarson:也就是說,'width'的類型應該被推斷爲'GFloat?'。看起來他們使用不同的代碼來推斷類型,而不是用於確定優先級的類型,這樣做顯示了爲什麼這是一個壞主意。 –

0

通過改變這些三線解決它......

func sizeOfString (string: String, maxWidth w: CGFloat?, maxHeight h: CGFloat?) -> CGSize { 
    var width = w != nil ? w! : DBL_MAX // Error on this line 
    var height = h != nil ? h! : DBL_MAX // And on this line 

...這個...

func sizeOfString (string: String, maxWidth w: CGFloat, maxHeight h: CGFloat) -> CGSize { 
    var width = w < 0 ? CGFLOAT_MAX : w 
    var height = h < 0 ? CGFLOAT_MAX : h 

CGFloat參數不再是可有可無的。相反,當我不需要約束寬度和/或高度時,我將負值轉換爲CGFLOAT_MAX

0

這裏是另一種方式來繞過這個錯誤...

var width: CGFloat 
if w { 
    width = w! 
} else { 
    width = CGFLOAT_MAX 
} 

var height: CGFloat 
if h { 
    height = h! 
} else { 
    height = CGFLOAT_MAX 
} 

三元運算符與可選的是造成問題,顯然相結合。

相關問題