Generic typealias in Swift

SwiftGenerics

Swift Problem Overview


In haskell you can do this:

type Parser a = String -> [(a, String)]

I tried to make something similar in Swift. So far I wrote these codes with no luck.

typealias Parser<A> = String -> [(A, String)]
typealias Parser a = String -> [(a, String)]
typealias Parser = String -> [(A, String)]

So is this simply impossible in swift? And if it is is there another ways to implement this behavior?

UPDATE: It seems generic typealiases are now supported in swift 3 https://github.com/apple/swift/blob/master/CHANGELOG.md

Swift Solutions


Solution 1 - Swift

Generic typealias can be used since Swift 3.0. This should work for you:

typealias Parser<A> = (String) -> [(A, String)]

Here is the full documentation: https://developer.apple.com/library/content/documentation/Swift/Conceptual/Swift_Programming_Language/Declarations.html#//apple_ref/swift/grammar/typealias-declaration

Usage (from @Calin Drule comment):

func parse<A>(stringToParse: String, parser: Parser) 

Solution 2 - Swift

typealias cannot currently be used with generics. Your best option might be to wrap the parser function inside a struct.

struct Parser<A> {
    let f: String -> [(A, String)]
}

You can then use the trailing closure syntax when creating a parser, e.g.

let parser = Parser<Character> { string in return [head(string), tail(string)] }

Solution 3 - Swift

Generic Type Aliases - SE-0048

Status: Implemented (Swift 3)

> The solution is straight-forward: allow type aliases to introduce type parameters, which are in scope for their definition. This allows one to express things like:

typealias StringDictionary<T> = Dictionary<String, T>
typealias IntFunction<T> = (T) -> Int
typealias MatchingTriple<T> = (T, T, T)
alias BackwardTriple<T1, T2, T3> = (T3, T2, T1)

Solution 4 - Swift

Here I am presenting example for typealias that demonistrate you to how to use typealias in protocols definitions: I hope this helps you understand typealias

protocol NumaricType {
    typealias elementType
    func plus(lhs : elementType, _ rhs : elementType) -> elementType
    func minus(lhs : elementType, _ rhs : elementType) -> elementType
}

struct Arthamatic :NumaricType {

    func addMethod(element1 :Int, element2 :Int) -> Int {
       return plus(element1, element2)
    }
    func minusMethod(ele1 :Int, ele2 :Int) -> Int {
        return minus(ele1, ele2)
    }
    
    typealias elementType = Int
    
    func plus(lhs: elementType,  _ rhs: elementType) -> elementType {
        return lhs + rhs
    }
    func minus(lhs: elementType, _ rhs: elementType) -> elementType {
        return lhs - rhs
    }
}

Output:

let obj =  Arthamatic().addMethod(34, element2: 45) // 79

Attributions

All content for this solution is sourced from the original question on Stackoverflow.

The content on this page is licensed under the Attribution-ShareAlike 4.0 International (CC BY-SA 4.0) license.

Content TypeOriginal AuthorOriginal Content on Stackoverflow
QuestionmustafaView Question on Stackoverflow
Solution 1 - SwiftstrannikView Answer on Stackoverflow
Solution 2 - SwiftIvica M.View Answer on Stackoverflow
Solution 3 - SwiftpkambView Answer on Stackoverflow
Solution 4 - SwiftNarendra GView Answer on Stackoverflow