【问题标题】:Array filter in Swift3Swift3 中的数组过滤器
【发布时间】:2017-06-05 10:48:57
【问题描述】:

我有一段代码。我没有得到这段代码里面的内容。谁能解释一下?

 let wordFreqs = [("k", 5), ("a", 7), ("b", 3)]

        let res = wordFreqs.filter(
        {
            (e) -> Bool in

            if e.1 > 3 {
                return true
            } else {
                return false
            }

        }).map { $0.0 }

        print(res)

给出输出:

["k","a"]

【问题讨论】:

  • 简单,首先您的数组已被过滤(按值> 3)然后映射(为键),您可以阅读更多关于Apple 书中的 Swift 语言。
  • 如果有人对我的问题有任何疑问。请给出评论,而不仅仅是负面标记。
  • 我认为投反对票是因为这是一个非常简单的问题,可以通过阅读 Apple 发布的免费 Swift 书籍的前几页来回答。在这里提出问题表明在提出问题之前缺乏理解代码的努力。 (虽然不是我的反对票。只是为了清楚。)
  • 我知道,但我想以简单的方式理解它。在搜索了它之后,当我觉得这个概念对我来说不是很清楚时,我就在这里问了。有什么问题吗?
  • 我不明白为什么人们不赞成这个问题。你需要的不仅仅是阅读文档的第一页来理解它,因为它包含许多概念:元组、过滤器、映射、闭包、函数链接,......首先,赞成它。我坚信 SO 不是高级程序员的专属,欢迎初学者。

标签: ios arrays filter swift3


【解决方案1】:

如果我们一个接一个地获取这段代码的各个部分:

let wordFreqs = [("k", 5), ("a", 7), ("b", 3)]

您从一组元组开始。

来自 Swift 文档:

元组类型是以逗号分隔的类型列表,括在括号中。

和:

元组将多个值组合成一个复合值。元组中的值可以是任何类型。

在这种情况下,元组是 2 个值的“对”,一个是 String 类型,一个是 Int 类型。


        let res = wordFreqs.filter(
        {
            (e) -> Bool in

这部分对数组应用过滤器。您可以在此处看到过滤器的闭包接受一个元素 e(因此,在我们的例子中,一个元组),并返回一个 Bool。使用'filter'函数,返回true表示保留值,返回false表示过滤掉。


            if e.1 > 3 {
                return true
            } else {
                return false
            }

e.1 语法返回索引 1 处的元组的值。 因此,如果索引 1(第二个)处的元组值超过 3,则过滤器返回 true(因此元组将被保留);如果不是,则过滤器返回 false(因此从结果中排除元组)。 此时,过滤器的结果将是[("k", 5), ("a", 7)]


        }).map { $0.0 }

map函数基于元组数组创建一个新数组:对于输入数组($0)的每个元素,它返回索引0处的元组值。所以新数组是["k", "a"]


        print(res)

这会将结果打印到控制台。


这些函数(filter、map、reduce 等)在函数式编程中非常常见。 它们通常使用点语法链接,例如,[1, 2, 3].filter({ }).map({ }).reduce({ })

【讨论】:

  • 感谢您的解释!
  • 很高兴!我仍在添加一些细节以使其更易于理解。
【解决方案2】:
// this creates an array of tuples
let wordFreqs = [("k", 5), ("a", 7), ("b", 3)]

let res = wordFreqs.filter {
    (e) -> Bool in

    // this filters the array
    // it removes any items that have the second part of the tuple
    // of 3 or less
    if e.1 > 3 {
        return true
    } else {
        return false
    }
}.map {
    // this "maps" the array and returns the first part of the tuple
    $0.0
}

print(res)

注意...如果我正在写这篇文章,我会将其缩短为...

let res = wordFreqs.filter { $0.1 > 3 }
                   .map { $0.0 }

【讨论】:

    【解决方案3】:

    wordFreqstuple 的数组。

    元组

    元组是一组零个或多个值表示为一个值。

    例如(“John”、“Smith”)包含一个人的名字和姓氏。您可以使用 dot(.) 符号后跟值的索引来访问内部值:

    var person = ("John", "Smith")
    
    var firstName = person.0 // John
    var lastName = person.1 // Smith
    

    现在,在您的情况下,您有类型为 (String, Int) 的元组和 filter 您正在比较 e.1 > 3(这里 e 保存数组迭代中的元组值与 filter)意味着那是 @987654329 @值大于3。

    现在您在 filter 结果上使用 map 并从元组中重新调整 String($0.0)

        //array of tuples
        let wordFreqs = [("k", 5), ("a", 7), ("b", 3)]
    
        let res = wordFreqs.filter(
        {
            (e) -> Bool in
            //Comparing the Second Int value of tuple in filter
            if e.1 > 3 {
                return true
            } else {
                return false
            }
    
        })
        //Mapping the result of filter
        .map { 
             //return the String from the tuple
             $0.0 
        }
    

    【讨论】:

    • 不错!这里的“e”是什么?当我运行代码时,它不会进入过滤器方法。为什么?
    • @Amanpreet 检查我回答中的括号声明:e.1 > 3(Here e is holds the tuple value from the array iteration with filter)
    • @Amanpreet 同样适用于map,但在那个地方它使用的是$0
    • @Amanpreet 如果你想删除代码,那么就像let res = wordFreqs.filter { $0.1 > 3 }.map { $0.0 }
    【解决方案4】:

    您的 e 对象代表 (String, int) 类型。正如您在[("k", 5), ("a", 7), ("b", 3)] 中的数组中看到的那样。

    首先,您使用的是filter 方法,这就是为什么您必须返回truefalse 值的原因。在这种情况下,您检查 e.1(表示 int 值)是否大于 3,如果不是,则返回 false。在所有这些处理之后,filter 方法返回 (String,int) 对象的过滤数组。

    下一步是map 函数。在您的情况下很简单,只需将所有数组值映射到元组的第一个对象(String,int)。

    为了更好地理解,您的代码可能如下所示:

    let filteredArray = wordFreqs.filter
    ({
        (e) -> Bool in
        return e.1 > 3
    })// the filteredArray is [("k", 5), ("a", 7)]
    
    
    let finalValue = filteredArray.map { 
      $0.0
    }// here you're creating a new array with String. $0 represents object from filteredArray
    
    print(finalValue) // ["k", "a"]
    

    【讨论】:

    • 谢谢。现在我理解了这个概念。
    猜你喜欢
    • 1970-01-01
    • 2018-01-04
    • 1970-01-01
    • 1970-01-01
    • 2022-08-11
    • 2020-02-24
    • 2021-07-19
    • 2018-03-02
    • 2018-04-26
    相关资源
    最近更新 更多