Scala系列之:函数式编程

news2024/11/17 14:22:20

Scala系列之:函数式编程

  • 一、面向对象编程和函数式编程
  • 二、函数基本语法
  • 三、函数和方法的区别
  • 四、函数定义
  • 五、函数参数
  • 六、函数至简原则
  • 七、匿名函数

一、面向对象编程和函数式编程

面向对象编程:

  • 解决问题,分解对象,行为,属性,然后通过对象的关系以及行为的调用来解决问题。
  • 对象:用户
  • 行为:登录、连接JDBC、读取数据库
  • 属性:用户名、密码
  • Scala语言是一个完全面向对象编程语言。万物皆对象
  • 对象的本质:对数据和行为的一个封装。

函数式编程:

  • 面向过程编程: 分析解决问题所需要的步骤, 然后用函数把这些步骤一一实现;

二、函数基本语法

基本语法:

在这里插入图片描述

三、函数和方法的区别

  • 为完成某一功能的程序语句的集合,称为函数
  • 类中的函数称为方法
  • Scala语言可以在任何的语法结构中声明任何的语法
  • 函数没有重载和重写的概念。方法可以进行重载和重写
  • Scala中函数可以嵌套定义

四、函数定义

  • 函数1:无参,无返回值
  • 函数2:无参,有返回值
  • 函数3:有参,无返回值
  • 函数4:有参,有返回值
  • 函数5:多参,无返回值
  • 函数6:多参,有返回值
package com.bigdata

object function {
  def main(args: Array[String]): Unit = {
    //函数1:无参,无返回值
    def f1(): Unit = {
      println("函数1:无参数,无返回值")
    }

    f1()

    //函数2;无参,有返回值
    def f2(): Int = {
      println("函数2:无参,有返回值")
      return 12
    }

    println(f2())

    //函数3:有参数,无返回值
    def f3(name: String): Unit = {
      println("函数3:有参数,无返回值 " + name)
    }

    f3("好好学scala")

    //函数4:有参数,有返回值
    def f4(name: String): String = {
      println("函数4:有参数,有返回值 " + name)
      return "好好学scala " + name
    }

    println(f4("加油"))

    //函数5:多参数,无返回值
    def f5(name: String, hobby: String): Unit = {
      println("函数5:多参数,无返回值")
      println(name + "喜欢" + hobby)
    }

    f5("飞", "足球")


    //函数6:多参数,有返回值
    def f6(a: Int,b: Int): Int = {
      println("函数6:多参数,有返回值")
      return a + b
    }

    println(f6(3,6))

  }
}

输出如下所示:

函数1:无参数,无返回值
函数2:无参,有返回值
12
函数3:有参数,无返回值 好好学scala
函数4:有参数,有返回值 加油
好好学scala 加油
函数5:多参数,无返回值
飞喜欢足球
函数6:多参数,有返回值
9

五、函数参数

  • 可变参数
  • 如果参数列表中存在多个参数,可变参数一般放置在最后
  • 参数默认值,一般将有默认值的参数放置在参数列表的后面
  • 带名参数
package com.bigdata

object function {
  def main(args: Array[String]): Unit = {
    //1.可变参数
    def f7(str: String*): Unit = {
      println(str)
    }
    f7("足球")
    f7("足球","羽毛球")

    //2.参数列表中存在多个参数,那么可变参数一般放置在最后
    def f8(str1: String,str2: String*): Unit = {
      println("str1: " + str1 + " str2: " + str2)
    }

    f8("足球","羽毛球","乒乓球")

    //3.参数默认值,一般有默认值的参数放置在参数列表的后面
    def f9(name: String = "huoying"): Unit = {
      println(name)
    }
    f9()
    f9("haizeiwang")

    //4.带名参数
    def f10(name: String = "鸣人", age: Int): Unit = {
      println(s"${age}岁的${name}在学习")
    }
    
    f10("佐助",20)
    f10(age = 11,name= "卡卡西")
    f10(age=5)

  }

}

输出如下所示:

1。可变参数
WrappedArray(足球)
1。可变参数
WrappedArray(足球, 羽毛球)
2。参数列表中存在多个参数,那么可变参数一般放置在最后 
str1: 足球 str2: WrappedArray(羽毛球, 乒乓球)
3。参数默认值,一般有默认值的参数放置在参数列表的后面
huoying
3。参数默认值,一般有默认值的参数放置在参数列表的后面
haizeiwang
4。带名参数
20岁的佐助在学习
4。带名参数
11岁的卡卡西在学习
4。带名参数
5岁的鸣人在学习

六、函数至简原则

  1. return可以省略,Scala会使用函数体的最后一行代码作为返回值
  2. 如果函数体只有一行代码,可以省略花括号
  3. 返回值类型如果能够推断出来,那么可以省略,:和返回值类型一起省略
  4. 如果有return,则不能省略返回值类型,必须指定
  5. 如果函数明确声明unit,那么即使函数体中使用return关键字也不起作用
  6. Scala如果期望是无返回值类型,可以省略等号
  7. 如果函数无参,但是声明了参数列表,那么调用时,小括号,可加可不加
  8. 如果函数没有参数列表,那么小括号可以省略,调用时小括号必须省略
  9. 如果不关心名称,只关心逻辑处理,那么函数名def可以省略
object function2 {

  def main(args: Array[String]): Unit = {
    //1.return可以省略,Scala会使用函数体的最后一行代码作为返回值
    def f1(name: String): String = {
      return name
    }

    println(f1("足球"))

    def f1bak(name :String): String = {
      name
    }

    println(f1bak("篮球"))

    // 2. 如果函数体只有一行代码,可以省略花括号
    def f2(name: String): String = name
    println(f2("羽毛球"))

    //3. 返回值类型如果能够推断出来,那么可以省略,:和返回值类型一起省略

    def f3(name: String) = name
    println(f3("水球"))

    //4. 如果有return,则不能省略返回值类型,必须指定
    def f4(name: String): String = {
      return name
    }

    //5. 如果函数明确声明unit,那么即使函数体中使用return关键字也不起作用
    def f5(name: String): Unit = {
      return name
    }

    println(f5("哈哈"))

    //6. Scala如果期望是无返回值类型,可以省略等号
    def f6(name: String) {
      println(f6("水球"))
    }

    //7. 如果函数无参,但是声明了参数列表,那么调用时,小括号,可加可不加
    def f7(): Unit = {
      println("强啊")
    }

    f7

    // 8. 如果函数没有参数列表,那么小括号可以省略,调用时小括号必须省略
    def f8: Unit = {
      println(" 8. 如果函数没有参数列表,那么小括号可以省略,调用时小括号必须省略")
    }

    f8

    // 9.如果不关心名称,只关心逻辑处理,那么函数名def可以省略
    def f9(name: String): Unit = {
      println(name)
    }
    //匿名函数,lambda表达式
    (name: String) => {println(name)}

  }

  }

七、匿名函数

  • 没有名字的函数就是匿名函数
  • (x:Int)=>{函数体}
  • x:表示输入参数类型
  • Int:表示输入参数类型
  • 函数体:表示具体代码逻辑

匿名函数的至简原则

object LambdaTest {
  def main(args: Array[String]): Unit = {
    val fun = (name: String) => {println(name)}
    fun("篮球")



    //匿名函数作为参数
    def f(func: String => Unit): Unit = {
      func("足球")
    }

    f(fun)
    println("--------")
    f((name: String) => {println(name)})
  }
}

匿名函数的至简原则

  1. 参数的类型可以省略,会根据形参进行自动推导
  2. 类型省略后,发现只有一个参数,则圆括号可以省略。其他情况,没有参数和参数超过1的永远不能省略圆括号。
  3. 匿名函数如果只有一行,则大括号也可以省略
  4. 如果参数只出现一次,则参数省略且后面参数可以用_代替。
  5. 如果可以推断出,当前传入的println是一个函数体,而不是调用语句,可以直接省略下划线
object LambdaTest {
  def main(args: Array[String]): Unit = {
    val fun = (name: String) => {println(name)}
    fun("篮球")



    //匿名函数作为参数
    def f(func: String => Unit): Unit = {
      func("足球")
    }

    f(fun)
    println("--------")
    f((name: String) => {println(name)})

    //1。参数的类型可以省略,会根据形参进行自动推导
    f((name) => {println(name)})


    //2。类型省略后,发现只有一个参数,则圆括号可以省略。其他情况,没有参数和参数超过1的永远不能省略圆括号。
    f(name => {println(name)})

    //3。匿名函数如果只有一行,则大括号也可以省略
    f(name => println(name))

    //4. 如果参数只出现一次,则参数省略且后面参数可以用_代替。
    f(println(_))

    //5.如果可以推断出,当前传入的println是一个函数体,而不是调用语句,可以直接省略下划线
    f(println)
  }

}

二元函数使用示例:

object LambdaTest {
  def main(args: Array[String]): Unit = {

  println("-----------------")
  //定义一个二元运算函数,只操作1和2两个数,具体运算通过参数传入
  def dualFunctionOneAndTwo(fun:(Int,Int)=>Int): Int = {
    fun(1,2)
  }

  val add = (a:Int,b:Int) => a + b
  val minus = (a:Int,b:Int) => a - b
  println(dualFunctionOneAndTwo(add))
  println(dualFunctionOneAndTwo(minus))

  //二元函数简化
  println("-------------二元函数简化----------")
  println(dualFunctionOneAndTwo(_ + _))
  println(dualFunctionOneAndTwo(_ - _))
  println(dualFunctionOneAndTwo(-_ + _))

}}

输出如下所示:

-----------------
3
-1
-------------二元函数简化----------
3
-1
1

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/186177.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

【最新消息】苹果放出新大招??!!

各位开发者新年快乐,许久没有更新了,近期我收到反馈意思遇到苹果回复的新政策,不知道各位开发者有没有碰到过,我也会在下文提出我的猜测,要是有开发者也遇到了同样的问题,欢迎一起交流哦。 疑似新政策&…

【寒假每日一题】洛谷 P1088 [NOIP2004 普及组] 火星人

题目链接:P1088 [NOIP2004 普及组] 火星人 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn) 题目描述 人类终于登上了火星的土地并且见到了神秘的火星人。人类和火星人都无法理解对方的语言,但是我们的科学家发明了一种用数字交流的方法。这种交流方法是…

vue-query 初探

vue-query,类似于vuex/pinia,以缓存为目的,但侧重的是对网络请求的缓存。 这是我预想的使用场景:假设在各个页面都需要发起相同的请求,去获取数据,而这种数据在一定时间内不会发生变化,那么这种…

【JavaWeb】带你走进Maven

文章目录1 什么是Maven?2 Maven 常用命令3 Maven 生命周期4 Maven 坐标详解5 IDEA 导入 Maven 项目1 什么是Maven? 如今我们构建一个项目需要用到很多第三方的类库,如写一个使用Spring的Web项目就需要引入大量的jar包。一个项目Jar包的数量之多往往让我们瞠目结舌…

线程execute()与submit()区别

线程池中有两个提交任务的方法 向线程池提交任务的两种方式大致如下: 方式一:调用execute()方法 方式二:调用submit()方法 一、区别 以上的submit()和execute()两类方法的区别在哪里呢?大致有以下三点: 1.二者所接收…

引入“ 自动化测试 ”都需要满足哪些条件?

📌 博客主页: 自动化软件测试 📌 专注于软件测试领域相关技术实践和思考,持续分享自动化软件测试开发干货知识! 📌 如果你也想学习软件测试,文末卡片有我的交流群,加入我们&#xff…

由浅入深,聊聊 LeakCanary 的那些事

引言 关于内存泄漏,Android 开发的小伙伴应该都再熟悉不过了,比如最常见的静态类间接持有了某个 Activity 对象,又比如某个组件库的订阅在页面销毁时没有及时清理等等,这些情况下多数时都会造成内存泄漏,从而对我们Ap…

linux内核-内存管理

linux内核内存管理 注意!内核空间和用户空间都是处于虚拟空间中 Linux的虚拟地址空间范围为0~4G,Linux内核将这4G字节的空间分为两部分 内核空间: 最高的1G字节(从虚拟地址0xC0000000到0xFFFFFFFF)&…

RTSP,RTP,RTCP协议

一 RTSP 1 简介 实时流传输协议,是一个应用层协议(TCP/IP网络体系中),它是一个多媒体播放控制协议,主要用来使用户在播放流媒体时可以像操作本地的影碟机一样进行控制,即可以对流媒体进行暂停/继续、后退和…

SAP FICO 关于资产的详细解析

SAP资产模块概述 一、概述 资产(AA)模块是资产会计模块的简称,是财务会计(FI)模块的一个子模块,主要处理与各类长期资产相关业务的模块。不单指固定资产,也不泛指资产负债表中的资产&#xff0c…

Week4

1.试题 历届真题 时间显示【第十二届】【省赛】【B组】 思路 不难发现,应该从小时往秒处理,这样可以用O(1)的时间复杂度求出,不过有比较麻烦的进位处理。 先看里面可以拼成几个小时,然后得到的小时%24,然后把总时间减去小时的时间,再看有多少分钟,分钟%60,都是此时判断分…

vue多环境配置之 .env配置文件

Vue之.env环境配置文件 .env文件是运行项目时的环境配置文件。但是在实际开发过程中,有本地环境、测试环境、预生产、生产环境等等,不同环境对应的配置会不一样。因此,需要通过不同的.env文件实现差异化配置。 * 文章目录Vue之.env环境配置文…

【JAVA核心知识】46:什么是零拷贝Zero-copy

零拷贝相较于传统的IO流程拥有更高的数据发送效率,无论是RocketMq,Kafka还是Netty等都用到了零拷贝技术,那究竟什么是零拷贝呢,零拷贝又是通过什么方式提升数据发送效率呢? 首先我们要明白,一次数据发送过程就是将磁盘…

Java基础--方法

前言:介绍 Java 中方法的基本语法、分类、执行并分析参数传值。 关键字:方法、形参、实参、返回值、实例方法、静态方法、参数传值 程序引例–为什么要「方法」 public class IntroduceOfMethod {// 入口主方法。public static void main(String[] args…

docker 高级篇

一、DockerFile 1.1、概述 dockerfile 是用来构建docker镜像的文本文件,是由一条条构建镜像所需的指令和参数构成的脚本。 为什么要有dockerfile呢 在基础篇我们讲过,比如我们下载个 ubuntu镜像里面不包含 vim、ifconfig等组件,这个时候 新增…

DES加密算法

DES算法原理 对称密码算法中的分组加密算法(对应于流密码) 密钥64位,56位参与运算8位校验位(校验位为:8、16、24、32、40、48、56、64) 加密原理 1. IP置换 将明文数据转化为二进制数,并将它…

Lnix文件权限的修改

首先我们要清楚Linux文件的权限信息 在Linux中输入ls -l 或者 ll查看文件和目录的详细信息 文件详情实例中,a目录的第一个属性用“d”标识这个a是一个目录。 anaconda-ks.cfg第一个属性用“-”标识他是一个文件。 在Linux文件详情的后面属性需要分为三组查看 rwx&am…

三种调用机制: 同步调用、异步调用、回调(同步/异步)

c并发编程-01-并发与并行_发如雪-ty的博客-CSDN博客 c并发编程02-什么是I/O_发如雪-ty的博客-CSDN博客 c并发编程03-I/O多路复用_发如雪-ty的博客-CSDN博客 c并发编程04-同步与异步_发如雪-ty的博客-CSDN博客_c同步和异步 c并发编程05-什么是回调函数_发如雪-ty的博客-CSDN…

Web前端:使用ReactJS构建的应用类型

使用ReactJS,你可以构建各种各样的应用程序,包括单页应用程序、渐进式web应用程序、移动应用程序、仪表板、电子商务平台、企业web应用程序以及社交媒体和消息应用程序。1.单页应用程序(spa)单页应用程序(SPA)基本上是一个网页,它通过使用从w…

MySQL(七):undo日志——保证事务的原子性

目录一、前言1.1 如何回滚事务1.2 事务id1.3 roll pointer 隐藏列1.4 trx_id 隐藏列二、undo日志2.1 undo日志的格式2.2 insert 对应的undo日志2.3 delete 操作对应的undo日志2.4 update操作对应的undo日志2.5 Undo页面链表2.6 undo日志写入过程2.6.1 Undo Log Header2.7 回滚段…