> On Mar 1, 2017, at 1:55 AM, Jonathan Hull via swift-evolution 
> <[email protected]> wrote:
> 
> What I would like is a way to specialize a generic function in a block of 
> code: (Strawman syntax)
> 
>       if T is Int.self {
>               //In this block of code T == Int
>       }
> 
> It seems to me that the compiler might even be able to optimize this without 
> a branch.

The compiler can already specialize away type checks like this (T.self is 
Int.Type will be reduced to a constant 'true' or 'false' when it specializes 
T). The type refinement part is missing, though, and I agree that it would be a 
useful addition.

-Joe

>  If there is a return in the block, then it might even be able to throw away 
> all the code after it for the Int version of the function.
> 
> Here is some actual (super ugly) code I wrote today.  I am unhappy with it 
> and looking to remove or improve it, but it is the best I can figure out at 
> the moment:
> 
> public static func operation<T>(symbol:String, type:T.Type)->((T,T)->T)?{
>         if T.self == Int.self {
>             var op:((Int,Int)->Int)? = nil
>             switch symbol {
>             case "+": op = (+)
>             case "-": op = (-)
>             case "*","x","•": op = (*)
>             case "/","÷": op = (/)
>             default: break
>             }
>             if op != nil {
>                 return op as! ((T,T)->T)?
>             }
>         }
> // Function continues...
> 
> All this function does is take a string with a mathematical symbol in it and 
> return an operation associated with that symbol/type (if it exists).  In 
> addition to the built in ones here, the user is able to register custom 
> symbols and operations (the machinery for that is further down and less ugly).
> 
> Notice that I need to cast the operation back to (T,T)->T because it doesn’t 
> know that T is an Int here. It has an error saying the cast always fails, but 
> that isn’t true.
> 
> Ideally, I would be able to check if T is Numeric and then just return the 
> operator.  I have to do a bunch of extra work here to disambiguate for the 
> compiler. It needs me to call out specific types (like Int) individually and 
> then cast them back to T.
> 
> What I would like to do:
> 
> public static func operation<T>(symbol:String, type:T.Type)->((T,T)->T)?{
>         if T.self is Numeric {
>             switch symbol {
>             case "+": return (+)
>             case "-": return (-)
>             case "*","x","•": return (*)
>             case "/","÷": return (/)
>             default: break
>             }
>         }
> // Function continues…
> 
> or at least:
> 
> public static func operation<T>(symbol:String, type:T.Type)->((T,T)->T)?{
>         if T.self is Int {
>             switch symbol {
>             case "+": return (+)
>             case "-": return (-)
>             case "*","x","•": return (*)
>             case "/","÷": return (/)
>             default: break
>             }
>         }
> // Function continues...
> 
> Is it something that could be possible in a future version of Swift?  or am I 
> missing something obvious that is much better than this?
> 
> Thanks,
> Jon
> 
>> On Feb 28, 2017, at 2:15 PM, Douglas Gregor via swift-evolution 
>> <[email protected] <mailto:[email protected]>> wrote:
>> 
>>> 
>>> On Feb 28, 2017, at 2:00 PM, David Hart <[email protected] 
>>> <mailto:[email protected]>> wrote:
>>> 
>>> 
>>>> On 28 Feb 2017, at 22:39, Douglas Gregor via swift-evolution 
>>>> <[email protected] <mailto:[email protected]>> wrote:
>>>> 
>>>> 
>>>>> On Feb 27, 2017, at 11:21 PM, Nicolas Fezans via swift-evolution 
>>>>> <[email protected] <mailto:[email protected]>> wrote:
>>>>> 
>>>>> +1
>>>>> I would also welcome to be able to use "or" and "and" logical operators 
>>>>> (not only the not operator) on these constraints.
>>>> 
>>>> You already have “and’ constraints: it’s what you get out of the 
>>>> comma-separated list of constraints in a where clause, or the “&” 
>>>> composition syntax.
>>>> 
>>>>> I have sometimes generic functions whose code is identical but is written 
>>>>> twice: first with 'where T=P1' and then with 'where T=P2', being able to 
>>>>> write for instance 'where T=(P1 or P2)' would be very handy IMO.
>>>>> One could often argue that additional protocols and extensions could be 
>>>>> defined as a workaround to the situation I just mentioned but it seems 
>>>>> often a bit of an overkill to me when you only have a couple of functions 
>>>>> with that combination of requirements.
>>>> 
>>>> “Or” constraints are a nonstarter for me, because you can’t meaningfully 
>>>> type-check a generic function that uses “or” constraints: the problem goes 
>>>> exponential in the number of “or” constraints and the meaning of the 
>>>> function can change considerably depending on which set of terms are 
>>>> satisfied—in which case you have ambiguities again!
>>>> 
>>>> Whenever this topic comes up, I like to point people at:
>>>> 
>>>>    http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2161.pdf 
>>>> <http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2007/n2161.pdf>
>>> Should we also follow Recommendation #2 and revert the P1 & P2 change to 
>>> return to Any<P1, P2> :) Half-joking.
>> 
>> That line of argument got thoroughly shot down in the core team meeting when 
>> we discussed the introduction of the & operator for types.
>> 
>>      - Doug
>> 
>> _______________________________________________
>> swift-evolution mailing list
>> [email protected] <mailto:[email protected]>
>> https://lists.swift.org/mailman/listinfo/swift-evolution 
>> <https://lists.swift.org/mailman/listinfo/swift-evolution>
> _______________________________________________
> swift-evolution mailing list
> [email protected]
> https://lists.swift.org/mailman/listinfo/swift-evolution

_______________________________________________
swift-evolution mailing list
[email protected]
https://lists.swift.org/mailman/listinfo/swift-evolution

Reply via email to