<html><head><meta http-equiv="content-type" content="text/html; charset=utf-8"></head><body dir="auto"><div><br></div><div><br>On Jun 22, 2016, at 5:51 PM, John McCall &lt;<a href="mailto:rjmccall@apple.com">rjmccall@apple.com</a>&gt; wrote:<br><br></div><blockquote type="cite"><div><meta http-equiv="Content-Type" content="text/html charset=us-ascii"><br class=""><div><blockquote type="cite" class=""><div class="">On Jun 22, 2016, at 12:15 AM, L. Mihalkovic via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a>&gt; wrote:</div><br class="Apple-interchange-newline"><div class=""><meta http-equiv="content-type" content="text/html; charset=utf-8" class=""><div dir="auto" class=""><div class="">Func asOpt&lt;T&gt;(v:Any) -&gt; Optional&lt;T&gt; {</div><div class="">&nbsp; If let val = v as? T {</div><div class="">&nbsp; &nbsp; Return val</div><div class="">&nbsp; }</div><div class="">&nbsp; Return nil</div><div class="">}</div><div class="">Regards<div class="">LM</div><div class="">(From mobile)</div></div></div></div></blockquote><div><br class=""></div>This is just:</div><div>&nbsp; return v as? T</div></div></blockquote><div><br></div><div>Had more code where i took it from... I thk it is one of these simple thgs that u never forget but may not be immediate to thk abt. Maybe worth adding to doc comment for Optional&lt;&gt; (forgive if is there already)</div><br><blockquote type="cite"><div><div><br class=""></div><div>John.</div><div><br class=""><blockquote type="cite" class=""><div class=""><div dir="auto" class=""><div class=""><br class="">On Jun 22, 2016, at 7:11 AM, Charlie Monroe via swift-evolution &lt;<a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a>&gt; wrote:<br class=""><br class=""></div><blockquote type="cite" class=""><div class="">Unfortunately, this is not as easy, because automatic bridging won't be applied:<div class=""><br class=""></div><div class=""><div style="margin: 0px; font-size: 9px; line-height: normal; font-family: Menlo;" class=""><div style="margin: 0px; line-height: normal;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> myString: </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">String</span><span style="font-variant-ligatures: no-common-ligatures" class="">? = </span><span style="font-variant-ligatures: no-common-ligatures; color: #d12f1b" class="">"Hello"</span></div><div style="margin: 0px; line-height: normal;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> anyValue: </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">Any</span><span style="font-variant-ligatures: no-common-ligatures" class=""> = </span><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">myString</span></div><div style="margin: 0px; line-height: normal; min-height: 10px;" class=""><span style="font-variant-ligatures: no-common-ligatures" class=""></span><br class=""></div><div style="margin: 0px; line-height: normal; color: rgb(0, 132, 0);" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">myString</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">as</span><span style="font-variant-ligatures: no-common-ligatures;" class="">? </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">AnyObject</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures" class="">// _NSContiguousString</span></div><div style="margin: 0px; line-height: normal; color: rgb(112, 61, 170);" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">anyValue</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">as</span><span style="font-variant-ligatures: no-common-ligatures;" class="">? </span><span style="font-variant-ligatures: no-common-ligatures" class="">AnyObject</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #008400" class="">// nil, since String is struct</span></div><div style="margin: 0px; line-height: normal; color: rgb(112, 61, 170);" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #008400" class=""><br class=""></span></div><div style="margin: 0px; line-height: normal; color: rgb(112, 61, 170);" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #008400" class=""><div style="margin: 0px; line-height: normal;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> array: [</span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">String</span><span style="font-variant-ligatures: no-common-ligatures" class="">]? = [</span><span style="font-variant-ligatures: no-common-ligatures; color: #d12f1b" class="">"Hello"</span><span style="font-variant-ligatures: no-common-ligatures" class="">]</span></div><div style="margin: 0px; line-height: normal;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> anyArray: </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">Any</span><span style="font-variant-ligatures: no-common-ligatures" class=""> = </span><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">array</span></div><div style="margin: 0px; line-height: normal; color: rgb(112, 61, 170);" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">anyArray</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">as</span><span style="font-variant-ligatures: no-common-ligatures;" class="">? </span><span style="font-variant-ligatures: no-common-ligatures" class="">AnyObject</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #008400" class="">// nil</span></div><div style="margin: 0px; line-height: normal; color: rgb(112, 61, 170);" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">anyArray</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">as</span><span style="font-variant-ligatures: no-common-ligatures;" class="">? [</span><span style="font-variant-ligatures: no-common-ligatures" class="">AnyObject</span><span style="font-variant-ligatures: no-common-ligatures;" class="">] </span><span style="font-variant-ligatures: no-common-ligatures; color: #008400" class="">// nil</span></div><div style="margin: 0px; line-height: normal;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">array</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">as</span><span style="font-variant-ligatures: no-common-ligatures;" class="">? </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">AnyObject</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures" class="">// ["Hello"]</span></div></span></div></div></div><div class=""><span style="font-variant-ligatures: no-common-ligatures" class=""><br class=""></span></div><div class="">And this goes for strings, arrays, dictionaries and possibly other types. Which means that you need to handle manually all of the bridging to ObjC types, which has really grown in Swift 3, taking into account all the Foundation types that are now structs.</div><div class=""><br class=""></div><div class="">Should this then be considered compiler bug that bridging isn't taken into account?</div><div class=""><br class=""></div><div class="">Nevertheless, I'd still find it useful exposing the isOptional() function as well as the asOptional which would allow a cast from Any to Optional&lt;Any&gt; which is not possible at all at this moment since any such cast will pick up the Optional first:</div><div class=""><br class=""></div><div class=""><div style="margin: 0px; font-size: 9px; line-height: normal; font-family: Menlo;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> myString: </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">String</span><span style="font-variant-ligatures: no-common-ligatures" class="">? = </span><span style="font-variant-ligatures: no-common-ligatures; color: #d12f1b" class="">"Hello"</span></div><div style="margin: 0px; font-size: 9px; line-height: normal; font-family: Menlo;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> anyValue: </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">Any</span><span style="font-variant-ligatures: no-common-ligatures" class=""> = </span><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">myString</span></div><div style="margin: 0px; font-size: 9px; line-height: normal; font-family: Menlo;" class=""><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">if</span><span style="font-variant-ligatures: no-common-ligatures" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">let</span><span style="font-variant-ligatures: no-common-ligatures" class=""> value = </span><span style="font-variant-ligatures: no-common-ligatures; color: #4f8187" class="">anyValue</span><span style="font-variant-ligatures: no-common-ligatures" class=""> </span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">as</span><span style="font-variant-ligatures: no-common-ligatures" class="">? </span><span style="font-variant-ligatures: no-common-ligatures; color: #703daa" class="">Any</span><span style="font-variant-ligatures: no-common-ligatures" class=""> {</span></div><div style="margin: 0px; font-size: 9px; line-height: normal; font-family: Menlo; color: rgb(0, 132, 0);" class=""><span style="font-variant-ligatures: no-common-ligatures;" class="">&nbsp; &nbsp; value.</span><span style="font-variant-ligatures: no-common-ligatures; color: #bb2ca2" class="">dynamicType</span><span style="font-variant-ligatures: no-common-ligatures;" class=""> </span><span style="font-variant-ligatures: no-common-ligatures" class="">// This is still Optional&lt;String&gt;, not naively just the value of the optional</span></div><div style="margin: 0px; font-size: 9px; line-height: normal; font-family: Menlo;" class=""><span style="font-variant-ligatures: no-common-ligatures" class="">}</span></div></div><div class=""><br class=""></div><div class=""><br class=""></div><div class=""><br class=""><blockquote type="cite" class="">On Jun 21, 2016, at 8:18 PM, Joe Groff &lt;<a href="mailto:jgroff@apple.com" class="">jgroff@apple.com</a>&gt; wrote:<br class=""><br class="">'as?' should already do this. If you have an Any that contains an Optional&lt;T&gt; and cast&nbsp;'any as? T', you'll get the value inside the Optional if there is one, or the cast will fail if the&nbsp;optional is nil or the type doesn't match.<br class=""><br class="">-Joe<br class=""><br class=""><blockquote type="cite" class="">On Jun 20, 2016, at 11:00 PM, Charlie Monroe via swift-evolution &lt;swift-<a href="mailto:evolution@swift.org" class="">evolution@swift.org</a>&gt; wrote:<br class=""><br class="">I've recently written a CoreData editor on iOS which automatically generates UI based&nbsp;on the model which is described using classes such as PrimitiveProperty, etc. Since it&nbsp;automatically sets the value on the entity, it needs to convert the value to AnyObject in&nbsp;order to pass it to setValue(_:forKey:), so it needs to be able to detect whether the value&nbsp;is Optional and in case it is, either transform the non-nil value to AnyObject (String -&gt;&nbsp;NSString, Array -&gt; NSArray, ...). Which is currently really hard to achieve:&nbsp;<br class=""><br class="">var obj: IndexPath? = IndexPath()<br class="">let anyValue: Any = obj<br class="">anyValue.dynamicType /// Optional&lt;Foundation.IndexPath&gt;.Type<br class=""><br class="">/// Using only anyValue, determine if it's Optional and retrieve its value if&nbsp;<br class="">/// non-nil as AnyObject.<br class="">func isOptional(anyValue: Any) -&gt; Bool {<br class="">&nbsp; &nbsp;// Error: Cannot downcast from 'Any' (aka 'protocol&lt;&gt;') to a more&nbsp;<br class="">&nbsp; &nbsp;// optional type 'Optional&lt;_&gt;'<br class="">&nbsp; &nbsp;return anyValue is Optional<br class="">&nbsp; &nbsp;return anyValue as? Optional != nil<br class="">&nbsp; &nbsp;...<br class="">}<br class=""><br class="">Unless there are major reasons why it's not exposed, I'd propose introducing a new&nbsp;function isOptional(anyValue: Any) -&gt; Bool, which would simply call Builtin.isOptional&nbsp;just like _isOptional does in Builtin.swift. (which pretty much is just taking the current&nbsp;_isOptional, removing underscore and marking it public).<br class=""><br class="">However, this still doesn't help with the issue of retrieving the value of the Optional. You&nbsp;now know the value in `anyValue` is Optional, but there is no good way to cast it to e.g.&nbsp;Optional&lt;AnyObject&gt;. Here we're getting into a vicious cycle that Any can be an&nbsp;Optional which is Any.<br class=""><br class="">My second part of the proposal introduces another function:<br class=""><br class="">func asOptional&lt;T&gt;(anyValue: Any) -&gt; Optional&lt;T&gt;?<br class=""><br class="">Which will:<br class="">- return nil if !isOptional(anyValue)<br class="">- return a non-nil value only if `anyValue` contains in fact an Optional of type T.<br class=""><br class="">Usage:<br class=""><br class="">if let anyObjOptional: AnyObject? = asOptional(anyValue: anyValue) {<br class="">&nbsp; &nbsp;if let anyObj = anyObjOptional {<br class="">&nbsp; &nbsp; &nbsp; &nbsp;// anyObj is now the actual content of the optional.<br class="">&nbsp; &nbsp;}<br class="">}<br class=""><br class="">As a sidenote, this is my current workaround:<br class=""><br class="">private protocol _XUOptional {<br class="">&nbsp; &nbsp;var objectValue: AnyObject? { get }<br class="">}<br class=""><br class="">extension Optional: _XUOptional {<br class="">&nbsp; &nbsp;var objectValue: AnyObject? {<br class="">&nbsp; &nbsp; &nbsp; &nbsp;switch self {<br class="">&nbsp; &nbsp; &nbsp; &nbsp;case .None:<br class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;return nil<br class="">&nbsp; &nbsp; &nbsp; &nbsp;case .Some(_):<br class="">&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;return self! as? AnyObject<br class="">&nbsp; &nbsp; &nbsp; &nbsp;}<br class="">&nbsp; &nbsp;}<br class="">}<br class=""><br class="">if let optional = anyValue as? _XUOptional {<br class="">&nbsp; &nbsp;let object = optional.objectValue<br class="">&nbsp; &nbsp;/// ...<br class="">}<br class=""><br class=""><br class=""><br class="">_______________________________________________<br class="">swift-evolution mailing list<br class=""><a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a><br class=""><a href="https://lists.swift.org/mailman/listinfo/swift-evolution" class="">https://lists.swift.org/mailman/listinfo/swift-evolution</a><br class=""></blockquote><br class=""></blockquote><br class=""></div></div></blockquote><blockquote type="cite" class=""><div class=""><span class="">_______________________________________________</span><br class=""><span class="">swift-evolution mailing list</span><br class=""><span class=""><a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a></span><br class=""><span class=""><a href="https://lists.swift.org/mailman/listinfo/swift-evolution" class="">https://lists.swift.org/mailman/listinfo/swift-evolution</a></span><br class=""></div></blockquote></div>_______________________________________________<br class="">swift-evolution mailing list<br class=""><a href="mailto:swift-evolution@swift.org" class="">swift-evolution@swift.org</a><br class=""><a href="https://lists.swift.org/mailman/listinfo/swift-evolution">https://lists.swift.org/mailman/listinfo/swift-evolution</a><br class=""></div></blockquote></div><br class=""></div></blockquote></body></html>