第2关:函数排序

简介: 第2关:函数排序


任务描述

    本关任务:本关主题是利用Scala函数式编程中已经实现的排序函数实现相关的排序需求。在一次考试中,Cathy、Daniel和Andy的成绩如下:

科目 语文 数学 英语 物理 化学 生物
Cathy 100 110 108 78 95 89
Daniel 110 98 110 80 94 88
Andy 105 120 115 85 90 95


 试给这三位同学进行排名,排名规则:按总分降序排序,若总分相同,则按语数英三门总分降序排序;若三门总分仍然相同,则按姓名升序排序。请仔细阅读下面“相关知识”中的内容,理解排序的各种操作,补全代码中的内容,使得程序运行结果如预期输出。


相关知识

   排序方法在实际的应用场景中非常常见,Scala里面有三种排序方法,分别是: sorted,sortBy ,sortWith。

(1)sorted

   对一个集合进行自然排序,通过传递隐式的Ordering。

(2)sortBy

   对一个属性或多个属性进行排序,通过它的类型。

(3)sortWith

   基于函数的排序,通过一个comparator函数,实现自定义排序的逻辑。


基于单集合单字段的排序

object TestSort_01{
def main(args:Array[String]){
val xs=Seq(1,5,3,4,6,2)
println("==============sorted排序=================")
println(xs.sorted) //升序
println(xs.sorted.reverse) //降序
println("==============sortBy排序=================")
println( xs.sortBy(d=>d) ) //升序
println( xs.sortBy(d=>d).reverse ) //降序
println("==============sortWith排序=================")
println( xs.sortWith(_<_) )//升序
println( xs.sortWith(_>_) )//降序
}
}


结果:

==============sorted排序=================

List(1, 2, 3, 4, 5, 6, 7, 8, 9)

List(9, 8, 7, 6, 5, 4, 3, 2, 1)

==============sortBy排序=================

List(1, 2, 3, 4, 5, 6, 7, 8, 9)

List(9, 8, 7, 6, 5, 4, 3, 2, 1)

==============sortWith排序=================

List(1, 2, 3, 4, 5, 6, 7, 8, 9)

List(9, 8, 7, 6, 5, 4, 3, 2, 1)


基于元组多字段的排序

    多字段的排序,使用sorted比较麻烦,一般使用sortBy和sortWith。


(1)基于sortBy的实现:

object TestSort_02{
def main(args:Array[String]){
val pairs = Array(
("a", 5, 1),
("c", 3, 1),
("b", 1, 3) )
//按第三个字段升序,第一个字段降序,注意,排序的字段必须和后面的tuple对应
val bx= pairs.sortBy(r => (r._3, r._1))( Ordering.Tuple2(Ordering.Int, Ordering.String.reverse) )
//打印结果
bx.map( println )
}
}

结果:

(c,3,1)

(a,5,1)

(b,1,3)


(2)基于sortWith的实现:

object TestSort_03{
def main(args:Array[String]){
val pairs = Array(
("a", 5, 1),
("c", 3, 1),
("b", 1, 3) )
val b= pairs.sortWith{
case (a,b)=>{
if(a._3==b._3) {//如果第三个字段相等,就按第一个字段降序
a._1>b._1
}else{
a._3<b._3 //否则第三个字段降序
}
}
}
//打印结果
b.map(println)
}
}

结果:

(c,3,1)

(a,5,1)

(b,1,3)


   可以看出,基于sortBy的实现比较优雅,语义比较清晰,基于sortWith的灵活性更强,但代码稍加繁琐。


基于类的排序

(1)sortBy的实现方法

   排序规则:先按年龄排序,如果一样,就按照名称降序排。

object TestSort_04{
def main(args:Array[String]){
case class Person(val name:String,val age:Int)
val p1=Person("cathy",23)
val p2=Person("daniel",23)
val p3=Person("andy",25)
val pairs = Array(p1,p2,p3)
//先按年龄排序,如果一样,就按照名称降序排
val bx= pairs.sortBy(person =>(person.age, person.name))
( Ordering.Tuple2(Ordering.Int, Ordering.String.reverse) )
bx.map(println)
}
}

结果:

Person(daniel,23)

Person(cathy,23)

Person(andy,25)


(2)sortWith的实现方法

    排序规则:年龄一样,按名字降序排,否则按年龄升序排。

object TestSort_05{
def main(args:Array[String]){
case class Person(val name:String,val age:Int)
val p1=Person("cathy",23)
val p2=Person("daniel",23)
val p3=Person("andy",25)
val pairs = Array(p1,p2,p3)
val b=pairs.sortWith{
case (person1,person2)=>{
person1.age==person2.age match {
//年龄一样,按名字降序排
case true=> person1.name > person2.name
case false=>person1.age < person2.age //否则按年龄升序排
}
}
}
b.map(println)
}
}

结果:

Person(daniel,23)

Person(cathy,23)

Person(andy,25)


总结:

   本关介绍了scala里面的三种排序函数,都有其各自的应用场景:

(1)sorted:适合单集合的升降序。

(2)sortBy:适合对单个或多个属性的排序,代码量比较少,推荐使用这种。

(3)sortWith:适合定制化场景比较高的排序规则,比较灵活,也能支持单个或多个属性的排序,但代码量稍多,内部实际是通过java里面的Comparator接口来完成排序。

实际应用中,可以根据具体的场景来选择合适的排序策略。


编程要求

   补全代码中的内容,以使得程序运行结果如预期输出。具体请参见后续测试样例。


测试说明

   平台会对你编写的代码进行测试:


测试输入:无输入;

预期输出:

(Andy,340,610)

(Cathy,318,580)

(Daniel,318,580)


object TestSort{
  def main(args:Array[String]){
    val pairs = Array(
      ("Cathy",  100,  110,  108,  78,  95,  89),
      ("Daniel",  110,  98,  110,  80, 94,     88),
      ("Andy",   105,  120,  115, 85,     90,     95) )
    //**************Begin*************************
    //构造新数组(姓名,三科总分,六科总分)
    val  count = Array(
      (pairs{0}._1,pairs{0}._2+pairs{0}._3+pairs{0}._4,
        pairs{0}._2+pairs{0}._3+pairs{0}._4+pairs{0}._5+pairs{0}._6+pairs{0}._7),
      (pairs{1}._1,pairs{1}._2+pairs{1}._3+pairs{1}._4,
        pairs{1}._2+pairs{1}._3+pairs{1}._4+pairs{1}._5+pairs{1}._6+pairs{1}._7),
      (pairs{2}._1,pairs{2}._2+pairs{2}._3+pairs{2}._4,
        pairs{2}._2+pairs{2}._3+pairs{2}._4+pairs{2}._5+pairs{2}._6+pairs{2}._7) )
    //排序
    val b= count.sortWith{
      case (a,b)=>{
        if(a._3==b._3) {//如果总分相等,就按三科降序
          if(a._2==b._2)
            a._1<b._1
          else
            a._2>b._2
        }else {
          a._3>b._3 //否则总分降序
        }
      }
    }
    //**************End**************************
    //打印结果
    b.map(println)
  }
}


目录
相关文章
|
5月前
|
机器学习/深度学习 算法 物联网
基于WOA-CNN-LSTM-Attention、CNN-LSTM-Attention、WOA-CNN-LSTM、CNN-LSTM、LSTM、CNN6模型多变量时序预测一键对比研究(Matlab代码)
基于WOA-CNN-LSTM-Attention、CNN-LSTM-Attention、WOA-CNN-LSTM、CNN-LSTM、LSTM、CNN6模型多变量时序预测一键对比研究(Matlab代码)
208 0
|
Python
使用Python实现商品价格区间设置和排序
使用Python实现商品价格区间设置和排序
662 0
|
存储 监控 NoSQL
35个Redis企业级性能优化点与解决方案
Redis作为企业级应用中广泛使用的高性能键值存储数据库,其性能优化是一个复杂且多面的话题。以下是V 哥整理的一些关键的优化点和相应的解决方案,提供给兄弟们参考。
328 0
|
Java API
第3关:HDFS-JAVA接口之上传文件
第3关:HDFS-JAVA接口之上传文件
1254 0
第3关:HDFS-JAVA接口之上传文件
|
SQL 关系型数据库 MySQL
MySQL 聚合函数深入讲解与实战演练
MySQL 聚合函数深入讲解与实战演练
|
存储 计算机视觉 Python
python实现Gif图片的字符画
这是一个Python实战项目,旨在将GIF动态图转化为ASCII字符动画。项目适合有一定Python基础的学习者,主要使用os、imageio、PIL库。首先,代码导入所需库,然后通过PIL创建空白图片并添加文本。接着,程序读取GIF,拆分帧并转为字符画,存入“tmp”目录。同时,代码提供了清空“tmp”目录、将灰度值映射为ASCII字符、将图片处理成字符画的函数。此外,还有创建新画布和合成GIF的步骤。主函数调用这些模块,最终将ASCII字符画合并成GIF。项目展示了将动态图像转换为ASCII艺术的过程。
|
消息中间件 SQL canal
Flink转换问题之DataStream转成table失败如何解决
Apache Flink是由Apache软件基金会开发的开源流处理框架,其核心是用Java和Scala编写的分布式流数据流引擎。本合集提供有关Apache Flink相关技术、使用技巧和最佳实践的资源。
|
存储 开发工具 数据库
云计算:概念、优势与实践——附Python代码示例
云计算:概念、优势与实践——附Python代码示例
|
开发框架 JSON 资源调度
Locust压测框架入门
Locust压测框架入门
467 0

热门文章

最新文章