网上学习资料一大堆,但如果学到的知识不成体系,遇到问题时只是浅尝辄止,不再深入研究,那么很难做到真正的技术提升。
一个人可以走的很快,但一群人才能走的更远!不论你是正从事IT行业的老鸟或是对IT行业感兴趣的新人,都欢迎加入我们的的圈子(技术交流、学习资源、职场吐槽、大厂内推、面试辅导),让我们一起学习成长!
* @param args
*/
def main(args: Array[String]): Unit = {
def getHelloFunc(msg:String) = (name:String) => println(msg + "," + name)
val sayHello = getHelloFunc("hello") // 传入msg的值 ,后面sayHello依然可以访问到
val sayHi = getHelloFunc("hi")
// 两次条用getHelloFunc,传入不同的msg,创建不同的函数返回
// 然而msg只是一个局部变量,
// 在getHelloFunc调用后,还继续存在创建的函数中,当sayHello("yxj")调用时,值为hello的msg保留在了函数内部,可以反复使用
// 这种变量超出了其作用域,还可以使用的情况,就是闭包
// scala
sayHello("yxj") // 打印 hello,yxj
sayHi("yxj") // 打印 hi,yxj
}
}
### 3. Scala 中的柯里化
柯里化函数也叫多参数列表函数,本身就是指**把接受多分参数的函数变化成接受一个单一参数(最初函数的第一个参数)的函数**,并且返回接受余下的参数且返回结果的新函数的技术
简单理解就是**改变函数的形式,不改变函数的功能**。用途:和隐式参数结合使用大大简化代码,但降低了代码的可读性
//该函数接受两个参数
def mul(x:Int,y:Int) = x*y
//该函数接受一个参数生成另外一个接受单个参数的函数
def mulOneAtTime(x:Int)(y:Int) = x*y
//也可以写成
def mulOneAtTime(x:Int) = (y:Int) => x * y
### 4. Java 和 Scala 的联系和区别
**联系:**
* Scala 源于 Java,但又高于 Java,Scala 在 Java 的基础上增加了**函数式编程**,让开发人员可以通过函数式编程来开发程序
* 由于 Scala 最终被编译为 .class 文件运行在 JVM 中,其实**本质上还是 Java**,所以在 Scala 和 Java 可以互调双方的 API
**区别:**
* 变量的声明:
+ 变量 var 常量 val,Scala 支持自动类型推测
+ Scala 更多的是采用**常量**而不是变量来解决问题,**好处是可以减少多线程并发的安全问题**,特别适合用于多并发分布式的场景
* 函数的声明
+ 关键字 def,Scala 函数没有返回值用 Unit,相当于 Java 中的 void
+ Scala 支持函数式编程,可以使用高阶函数,函数在 Scala 中是一等公民
* 基本类型
+ Scala 是存粹的面向对象的编程语言,所以并没有真正意义上的基本类型,他的类型都是类
* 静态
+ Java 中静态 static 是违背 Java 面向对象的编程思想和封装特性的
+ Scala 取消了静态的概念,使用单例对象 object 来实现
* 对字符串的支持
+ Scala 支持使用字符串差值的方式对字符串进行格式化,使用$开头进行取值
+ 另外支持使用三引号将其中的内容直接包起来,其中可以包括任何字符而不需要转义
* 类
+ Scala 中的字段自动带有 getter 和 setter 方法,另外可以使用 @BeanProperty 注解来生成 Java 中的 Get/Set 方法
+ Scala 中的每一个类都有一个主构造器,这个构造器和类定义“交织在一起”,类的参数直接成为类的字段,主构造器执行类体中所有的语句
* Scala 中不支持 break
+ 使用return 替代
+ 在循环中用 if 和布尔类型变量进行守卫
+ 导入 Java 中支持 break 的包
* 访问范围的问题
+ Java 中外部看不到内部,内部能看到外部
+ Scala 中外部看不到内部,内部看不到外部
* 通配符
+ Java 使用 \* 进行通配
+ Scala 使用 \_ 进行通配
* 默认导入的包
+ Scala 中默认导入 java.lang 包、Scala 包、Scala.Predef 类
+ Java 默认导入 java.lang 包
* 特质 trait 可以类比 Java 中的接口,但是又和接口非常不一样
+ Java 中称为类实现了接口,Scala 中称为混入了特质
+ 和 Java 中接口不同,Scala 中的特质可以包含带有方法体的方法
![](https://img-blog.csdnimg.cn/20210912204751256.png?x-oss-process=image/watermark,type_ZHJvaWRzYW5zZmFsbGJhY2s,shadow_50,text_Q1NETiBAVmlja3lfVGFuZw==,size_20,color_FFFFFF,t_70,g_se,x_16)
### 5. Scala 中的模式匹配
Scala 的模式匹配包括了一系列的备选项,每个替代项以关键字大小写为单位,每个替代方案包括一个模式或多个表达式,如果匹配将进行计算,箭头符号 => 将模式与表达式分离
Scala中的模式匹配类似于Java中的switch语法,但是更加强大。 模式匹配语法中,采用match关键字声明,每个分支采用case关键字进行声明,当需要匹配时,会从第一个case分支开始,如果匹配成功,那么执行对应的逻辑代码,如果匹配不成功,继续执行下一个分支进行判断。如果所有case都不匹配,那么会执行case \_ 分支,类似于Java中default语句。
obj match{
case 1 => “one”
case 2 => “two”
case 3 => “three”
case _ => default
}
### 6. case class 和 class 的区别
**case class 是一个样例类:**
样例类是一种不可变切可分解类的语法糖,也就是说在构建的时候会自动生成一些语法糖,具有以下几个特点:
* 自动添加与类名一致的构造函数(也就是半生对象,通过apply方法实现),也就是说在构造对象的时候不需要使用new关键字
* 样本类中的参数默认是val关键字,不可以修改
* 默认实现了toString,equals,hashcode,copy方法
* 样本类可以通过==来比较两个对象,不在构造方法内地二属性不会用在比较上
**class是一个类:**
class在构造对象的时候需要使用new关键字才可以。
### 7. 谈谈 Scala 中的隐式操作
(1)隐式变量
为函数提供隐式参数(常和柯里化结合使用)
def method(name:String)(prefix:String=“DEFAULT”) = print(prefix + name)
implicit prefix:String=“DEFAULT”
def method(name:String)(implicit prefix:String) = print(prefix + name)
(2)隐式函数
给函数类型的参数提供默认值,
**同一作用域下同一种类型只能出现一个**
应用:隐式类型转换
def main(args: Array[String]): Unit = {
//隐式函数,默认将字符串类型转换为整数类型
//同一作用域下同一类型只能出现一个,也就是说该作用域下不能再将字符串类型隐式转换成其他类型
implicit def fsi(v:String):Option[Int] = {
val regexInt = “\d+”.r
if (regexInt.pattern.matcher(v).matches){
Some(v.toInt)
}else{
Option.empty
}
}
val a:Option[Int]=“abc”
println(a)
}
(3)隐式类
隐式扩展唯一构造参数指定的类型的功能
//功能:如果数组类型为Int类型则求和,否则输出字符串,以空格为间隔符
implicit class ArrExtT{
def c()={
if (arr.isInstanceOf[Array[Int]] ){
arr.asInstanceOf[Array[Int]].sum
}else if(arr.isInstanceOf[Array[String]]){
arr.asInstanceOf[Array[String]].mkString(" ")
}else{
throw new RuntimeException(“unsupported array type”)
}
}
}
def main(args: Array[String]): Unit = {
println(Array(1, 2, 5).c())
println(Array(“aa”, “bb”, “cc”).c())
}
(4)隐式对象
扩展功能
//功能:根据传入的参数值类型自动实现对应类型的函数
def main(args: Array[String]): Unit = {
trait A[T]{
def combine(arr:Array[T]):T
def empty:T
}
implicit object StrArrA extends A[String] {
override def combine(arr: Array[String]): String = arr.mkString(“,”)
override def empty: String = “”
}
implicit object IntArrA extends A[Int] {
override def combine(arr: Array[Int]): Int = arr.sum
override def empty: Int = 0
}
def combine[T](arr:Array[T])(implicit a:A[T]) = {
if (arr.isEmpty){
a.empty
}else{
a.combine(arr)
}
}
val arrStr: Array[String] = Array("aa", "bb", "cc")
val arrInt: Array[Int] = Array(1, 2, 3)
println(combine(arrStr))
println(combine(arrInt))
}
### 8. Scala 中的偏函数和偏应用函数
**偏函数(Partial Function)**
是一个数学概念它不是"函数"的一种, 它跟函数是平行的概念。Scala中 的 Partia Function是一个 Trait,其的类型为 PartialFunction[A,B],其中接收一个类型为 A 的参数,返回一个类型为 B 的结果。
**通常结合模型匹配使用**
scala> val pf:PartialFunction[Int,String] = {
| case 1=>“One”
| case 2=>“Two”
| case 3=>“Three”
| case _=>“Other”
| }
pf: PartialFunction[Int,String] =
scala> pf(1)
res0: String = One
scala> pf(2)
res1: String = Two
scala> pf(3)
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上大数据知识点,真正体系化!
由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新
mg-OQRbKUCH-1715429413196)]
[外链图片转存中…(img-D04CajGJ-1715429413197)]
既有适合小白学习的零基础资料,也有适合3年以上经验的小伙伴深入学习提升的进阶课程,涵盖了95%以上大数据知识点,真正体系化!
由于文件比较多,这里只是将部分目录截图出来,全套包含大厂面经、学习笔记、源码讲义、实战项目、大纲路线、讲解视频,并且后续会持续更新