首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >斯威夫特的功能思维?

斯威夫特的功能思维?
EN

Stack Overflow用户
提问于 2015-01-06 22:18:39
回答 3查看 436关注 0票数 1

我开始学习Haskell和Swift。我想知道这是否是正确的“功能性”思维方式?问题是要创造牌牌:我需要循环通过西装和等级-为每套西装创建卡片与给定的西装和等级。以“命令式”的方式:

代码语言:javascript
复制
let suits: Array<Character> = ...
let ranks: Array<Int> = ...

var cards: [Card]
for suit in suits {
    for rank in ranks {
        cards.addObject(Card(suit: suit, rank: rank))
    }
}

然后我尝试使用递归的纯函数,它可以工作,但是,它能用更少的代码来完成吗?对我来说斯威夫特的“函数式”的可读性很低,或者我做错了.

代码语言:javascript
复制
let cards = cardsWithSuits(suits, ranks, [Card]());

func cardsWithSuits(suits: [Character], ranks: [Int], cards: [Card]) -> [Card] {
   if suits.count == 0 { return cards }
   let suit: Character = head(suits)!
   let acc = cardsWithRanks(ranks, suit, cards)

   return cardsWithSuits(drop(1, suits), ranks, acc)
}

func cardsWithRanks(ranks: [Int], suit: Character, cards: [Card]) -> [Card] {
   if ranks.count == 0 { return cards }
   let acc = cards + [Card(suit: suit, rank: head(ranks)!)]

   return cardsWithRanks(drop(1, ranks), suit, acc)
}
EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2015-01-06 23:27:20

在使用Haskell的应用概念以及<$><*>的基础上,您可能会发现以下内容通常是有用的(我认为我已经正确翻译了,尽管它是基于数组而不是序列):

代码语言:javascript
复制
// use <^> because <$> is already used
infix operator <^> { associativity left }
public func <^> <T, U>(left:(T)->U, right:[T]) -> [U] {
    return map(right) { return left($0) }
}

public func flatten<T>(input:[[T]]) -> [T] {
    return input.reduce([], +)
}

infix operator <*> { associativity left }
public func <*> <T, U>(left:[(T)->U], right:[T]) -> [U] {
    return flatten(map(left) { (function) -> [U] in
        return map(right) { return function($0) }
    })
}

这样,您就可以使用以下内容:

代码语言:javascript
复制
let suits : [Character] = [ "C", "D", "H", "S"]
let ranks = Array(2...14)

struct Card {
    let suit : Character
    let rank : Int

    static func build(suit:Character)(rank:Int) -> Card {
        return Card(suit: suit, rank:rank)
    }
}

Card.build <^> suits <*> ranks
票数 5
EN

Stack Overflow用户

发布于 2015-01-07 03:28:32

这可能不太好,而且我不认为它是函数式编程,但它的代码较少,而且它使用了Swift的出色映射并减少了函数:

代码语言:javascript
复制
struct Card {
    let suit: String
    let rank: Int
}

let cards = ["Heart", "Diamond", "Club", "Spade"].reduce([Card]()) { (cards, suit) in
    return cards + map(1...13) { rank in return Card(suit: suit, rank: rank) }
}
票数 1
EN

Stack Overflow用户

发布于 2018-04-29 19:07:22

斯威夫特不是一种功能性语言。但是,您可以编写功能样式的快速代码。

代码语言:javascript
复制
func map<T: Collection, U>( _ transform: (T.Iterator.Element) -> U, _ xs: T) -> [U] {
    return xs.reduce([U](), {$0 + [transform($1)]})
}

func concatMap<A, B> (_ process: (A)->[B], _ xs: [A]) -> [B] {
    return xs.reduce([B](), {$0 + process($1)})
}

infix operator <*>
func <*><A, B>(_ xs: [A], _ ys: [B]) -> [(A, B)]{
    let transform: (A, B) -> (A, B) = {($0, $1)}
    return concatMap({x in map({transform(x, $0)}, ys)}, xs)
}

struct Card {
    let suit : Character
    let rank : Int

    static func build(_ sr: (s:Character, r:Int)) -> Card {
        return Card(suit: sr.0, rank: sr.1)
    }
}

func test() {
    let suits : [Character] = [ "C", "D", "H", "S"]
    let ranks = Array(1...13)
    let cards = map(Card.build, suits <*> ranks)
    print(cards)
}

如果你想学习Haskell和Swift,你可以参考https://github.com/unchartedworks/HaskellSwift

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/27808198

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档