Scala
基础
数据类型
scala中的数据类型和java的数据类型对应关系:
* java: scala:
* byte Byte
* short Short
* int Int
* long Long
* float Float
* double Double
* boolean Boolean
* char Char
定义变量
在scala中定义一个变量,需要使用一个关键词:var
在scala中定义一个常量,需要使用一个关键词:val
整的写法:var 变量名:数据类型 = 值
字符串
//正常使用双引号构建字符串
// var s1: String = "易政是世界上最帅的男人!"
// //使用三个一对双引号构建长字符串
// var sql1: String =
// """
// |select
// |*
// |from
// |students
// |where age>18
// |""".stripMargin
* 在scala中字符串是如何做拼接的?
// * 1、使用+号拼接 这种拼接方式比较消耗性能
// * 2、使用StringBuilder
// * 3、前提:有一组序列,使用scala特有的函数 mkString
// * 4、使用scala特有的字符串传递方式 s"${变量}" 底层就是使用StringBuilder方式拼接的
运算符
同java
条件语句
/**
* 条件语句
* 选择语句:if
* 循环语句:
*/
// if(age>18){
// println("成年了")
// }else{
// println("未成年")
// }
* 1、在scala语言中,没有++或者--的语法 i+=1 i= i+1
* 2、在scala语言中,不存在和java一样的普通for循环
* 3、scala中的for循环写法不太一样
// for (e <- arr2) {
// println(e)
// }
* while循环
*/
// var i:Int = 0
// while (i<arr2.length){
// println(arr2(i))
// i+=1
// }
/**
* 控制流程语句
* 注意:在scala中没有break或者continue关键字使用breakable
*/
breakable {
for (e <- 1 to 10) {
if (e == 5) {
break // 底层实现是一个函数,抛出一个异常,终止程序运行
}
println(e)
}
}
读写文件
//Source.fromFil 底层是使用了字节输入流读取数据FileInputStream
val bs: BufferedSource = Source.fromFile("scala/data/words.txt")
val bw = new BufferedWriter(new FileWriter("scala/data/words2.txt"))
bw.write("易政真的是世界上最帅的男人!")
异常
try {
/**
* 也可以手动的抛出异常
*/
val sc = new Scanner(System.in)
print("输入除数:")
val cs: Int = sc.nextInt()
if(cs!=0){
println(10/cs)
}else{
throw new ArithmeticException("您输入的除数是0")
}
}catch{
//类似于sql语句中case when
case e:ArithmeticException=>
// println("除0异常")
e.printStackTrace()
case e:ArrayIndexOutOfBoundsException=>
println("数组越界异常")
case _ =>
println("出现异常")
}finally {
//今后finally中的处理大部分情况下都与释放资源有关
println("这是finally代码块")
}
函数
/**
* def: 定义函数或者方法的关键字
* main: 是函数或者方法的名字,符合标识符的命名规则
* args: 函数形参的名字
* Array[String]: 参数的数据类型是一个元素为字符串的数组
* =: 后面跟着函数体
* Unit: 等同于java中的void 表示无返回值的意思
*
*
* def main(args: Array[String]): Unit = {
*
* }
* 在不同的地方定义,称呼不一样
* 函数:在object中定义的叫做函数
* 方法:在class中定义的叫做方法
//如果方法调用的函数只有一个参数的时候,可以将.和小括号用空格代替调用
// 如果函数有返回值,且最后一句话作为返回值的话,return关键字可以不写
//
如果函数体中只有一句实现,那么大括号也可以不写
如果函数没有参数的时候,小括号省略不写
//函数或者方法必须定义在class或者object中
/**
* scala中的函数也可以递归
* 方法定义时,调用自身的现象
*
* 条件:要有出口,不然就是死递归
*/
类class
/**
* scala提供了一个非常好用的功能:样例类
* 较少用户创建类所编写代码量,只需要定义成员变量即可,自动扩充成员变量,构造方法,重写toString方法
*/
/**
* 样例类中的成员变量,编译后默认是被jvm添加了final关键字,用户是改变不了的
* 对于scala来说,默认是被val修饰的
* 如果将来想要被改变,定义的时候需要使用var进行修饰
*/
case class Teacher(name:String,age:Int,var like:String)
函数式编程
/**
* scala中的函数式编程
*
* 面向对象编程:将对象当作参数一样传来传去
* 1、对象可以当作方法参数传递
* 2、对象也可以当作方法的返回值返回
* 当看到类,抽象类,接口的时候,今后无论是参数类型还是返回值类型,都需要提供对应的实现类对象
*
* 面向函数式编程:将函数当作参数一样传来传去
* 1、函数A当作函数B的参数进行传递
* 2、函数A当作函数B的返回值返回
*
* 在scala中,将函数也当作一个对象,对象就有类型
* 函数在scala也有类型的说法
* 参数类型=>返回值类型
*/
1.函数A作为函数B的参数定义
2.函数当作参数传递
3.函数当作返回值返回
函数的柯里化
* 面试题:什么是函数柯里化?
* 1、本身是一个数学界的一个名词,本意是原来一次传递多个参数,现在被改成了可以分开传递的形式,这种做法叫做柯里化
* 2、在scala中体现柯里化,指的是函数的返回值也是一个函数,将来调用时参数可以分开传递。
* 3、提高了程序的灵活性和代码复用性
* 4、在scala中也可以通过偏函数实现参数分开传递的功能
*/
集合
List
//获取List集合的长度
println(list2.size)
//可以直接通过索引下标获取元素
println(list2(0))
//scala推荐获取第一个元素的方式是调用head函数
println(list2.head)
println(list2.last)
//根据指定的分隔符拼接元素
println(list2.mkString("|"))
val resList1: List[Int] = list2.reverse //返回一个新的集合
val resList2: List[Int] = list2.distinct //返回一个新的集合(去重)
val resList3: List[Int] = list2.tail // 除去第一个,其余的元素返回一个新的集合
val resList4: List[Int] = list2.take(5) // 从左向右取元素,取若干个
val resList5: List[Int] = list2.takeRight(5) //取右边的几个,组成新的集合
//从第一个判断取数据,直到不符合条件停止
val resList10: List[Int] = list2.takeWhile((e: Int) => e % 2 == 0)
val res1: Int = list2.sum // 元素必须是数值
val res2: Int = list2.max
/**
* 高阶函数:
* foreach: 将集合中的元素依次取出传入到后面的函数中
* 注意:没有返回值的,要么就输出,要么就其他方式处理掉了
*/
/**
* 高阶函数:
* map: 依次处理每一个元素,得到一个新的结果,返回到一个新的集合中
*/
/**
* 高阶函数:
* filter: 保留符合条件的元素
*/
/**
* 高阶函数:
* sortBy: 排序
* sortWith: 两个数之间的关系排序
*/
/**
* 高阶函数:
* flatMap: 扁平化
*/
/**
* 高阶函数:
* groupBy: 分组
*/
Set
/**
* set集合:scala中的Set集合也是不可变的,除了排序相关的函数以外,List集合有的高阶函数,Set集合也有
*/
//List->Set
val resSet4: Set[Int] = list1.toSet
//Set->List
val list2: List[Int] = resSet4.toList.sortBy((e:Int)=>e)
Mutable
/**
* 通过观察api发现,不可变的集合是属于scala.collection.immutable包下的
* 如果将来想要使用可变的集合,就要去scala.collection.mutable包下寻找
*/
/**
* 这里的可变List集合,上午说的功能函数,这里都可以调用
*/
/**
* 可变的Set集合
*/
val hashSet1: mutable.HashSet[Int] = new mutable.HashSet[Int]()
Tuple
/**
* 大小,值是固定的,根据创建的类来定,每个元素的数据类型可以是不一样,最高可以创建存储22个元素的元组
*/
val t1: (Int, String, String, Int, String) = Tuple5(1001, "易政", "男", 17, "学习")
Map
//键是唯一的,键一样的时候,值会被覆盖
//可以根据键获取值
// println(map1(1006)) // 小括号获取值,键不存在报错
// println(map1.get(1006)) // get函数获取,键不存在,返回None
println(map1.getOrElse(1006, 0)) //根据键获取值,若键不存在,返回提供的默认值,默认值的类型可以是任意数据类型
println("=" * 50)
val keys: Iterable[Int] = map1.keys // 获取所有的键,组成一个迭代器
for (e <- keys) {
println(e)
}
val values: Iterable[String] = map1.values // 获取所有的值,组成一个迭代器
for (e <- values) {
println(e)
}
//遍历Map集合第一种方式,先获取所有的键,根据键获取每个值
val keys2: Iterable[Int] = map1.keys // 获取所有的键,组成一个迭代器
for (e <- keys2) {
val v: Any = map1.getOrElse(e, 0)
println(s"键:${e}, 值:${v}")
}
//遍历Map集合第二种方式,先获取所有的键,根据键获取每个值
for (kv <- map1) { // 直接遍历map集合,得到每一个键值对组成的元组
println(s"键:${kv._1}, 值:${kv._2}")
}
//遍历Map集合第三种方式,先获取所有的键,根据键获取每个值
map1.foreach((kv: (Int, String)) => println(s"键:${kv._1}, 值:${kv._2}"))
JDBC
/**
* jdbc的链接步骤
* 1、注册驱动
* 2、创建数据库链接对象
* 3、创建数据操作对象
* 4、执行sql语句
* 5、如果第4步是查询的话,分析查询结果
* 6、释放资源
*/
//1、注册驱动
Class.forName("com.mysql.jdbc.Driver")
//2、创建数据库链接对象
//jdbc:数据库名//host:port/数据库?xxx=xxx&xxx=xxx
val conn: Connection = DriverManager.getConnection("jdbc:mysql://192.168.44.100:3306/studentdb?useUnicode=true&characterEncoding=UTF-8&useSSL=false", "root", "123456")
//3、创建数据操作对象
val preparedStatement: PreparedStatement = conn.prepareStatement("select id,name,age,gender,clazz from student where clazz=?")
//4、执行sql语句
// preparedStatement.setInt(1,23)
preparedStatement.setString(1, "理科二班")
val resultSet: ResultSet = preparedStatement.executeQuery()
//5、如果第4步是查询的话,分析查询结果
while (resultSet.next()){
val id: Int = resultSet.getInt("id")
val name: String = resultSet.getString("name")
val age: Int = resultSet.getInt("age")
val gender: String = resultSet.getString("gender")
val clazz: String = resultSet.getString("clazz")
println(s"学号:$id, 姓名:$name, 年龄:$age, 性别:$gender, 班级:$clazz")
}
//6、释放资源
conn.close()
JSON
val lineList: List[String] = Source.fromFile("scala/data/stu.json").getLines().toList
val jsonStr: String = lineList.mkString("\r\n")
//使用fastjson包中的JSON类,将一个字符串转成json对象
//转成json对象之后,可以通过键获取值
//parseObject 将整体转成一个json格式数据
val jsonObj1: JSONObject = JSON.parseObject(jsonStr)
val s1: String = jsonObj1.getString("student_list")
//parseArray将一个"[{},{}]"变成一个元素是json对象的数组
val jSONArray: JSONArray = JSON.parseArray(s1)
var i = 0
while (i < jSONArray.size()) {
val obj1: JSONObject = jSONArray.getJSONObject(i)
val name: String = obj1.getString("name")
val like: String = obj1.getString("like")
println(s"${name}的爱好是${like}")
i += 1
}
Scala to Java
//创建一个java中的集合
val array1: util.ArrayList[Int] = new util.ArrayList[Int]()
array1.add(11)
array1.add(22)
array1.add(33)
array1.add(66)
/**
* 将java中的集合转成scala中的集合
*
* java中的集合本来是没有转换scala的功能,需要导入隐式转换
* scala中的导包,可以在任意地方
*
*/
import scala.collection.JavaConverters._
val list1: List[Int] = array1.asScala.toList
println(list1)
/**
* scala中的集合转java的集合
*/
val list2: util.List[Int] = list1.asJava
println(list2)
Match(模式匹配)
/**
* 模式匹配,就可以帮助我们开发的时候,减少代码量,让逻辑看起来更加清晰,以及可以避免一些异常
* 语法:
* 表达式 match {
* case 值|[变量名:类型]|元组|数组|对象=>
* 匹配成功执行的语句
* case xxx=>
* xxx
* _ xxx=>
* xxx
* }
*
* 模式匹配中,如果没有对应的匹配,那么就报错!!!
*/
/**
* 可以匹配变量值
*/
// var i: Int = 100
// i match {
// case 20 => println("该值是20")
// case 50 => println("该值是50")
// // case 100=>println("该值是100")
// case _ => println("其他值")
// }
//
// /**
// * 匹配数据类型
// */
// var flag1: Any = true
// flag1 match {
// case _: Int => println("是Int类型")
// case _: Boolean => println("是boolean类型")
// }
//
// /**
// * 匹配元组
// */
// val t1: (Int, String, Int) = Tuple3(1001, "张三", 18)
// t1 match {
// case (a1: Int, b1: String, c1: Int) =>
// println(s"学号:$a1, 姓名:$b1, 年龄:$c1")
// }
//
// /**
// * 匹配数组
// */
// val array: Array[Any] = Array(1001, "李四", "男", 18, "理科一班")
// array match {
// case Array(id: Int, name: String, gender: String, age: Int, clazz: String) =>
// println(s"学号:$id, 姓名:$name, 性别:$gender, 年龄:$age, 班级:$clazz")
// }
模式匹配的应用1:避免异常
模式匹配的应用2:简化代码
stuArrayList.map{
case Array(id: String, name: String, gender: String, age: String, clazz: String)=>
(id, name, gender, age, clazz)
}.foreach(println)
implicit(隐式转换)
/**
* 隐式转换
* 1、隐式转换函数
* 2、隐式转换类
* 3、隐式转换变量
*
* 将一个A类型将来会自动地转换成另一个B类型,类型可以式基本数据类型,也可以是引用数据类型
*
* 显式转换
*/
函数
// implicit def implicitFun1(s: String): Int = {
// return Integer.parseInt(s)
// }
// def fun1(s: Int): Int = {
// return s + 1000
// }
// println(fun1("300"))
类
正常调用
// val demo1 = new Demo12("scala/data/students.txt")
// val stuList: List[String] = demo1.show1()
使用隐式转换
// val stuList: List[String] = "scala/data/students.txt".show1()
// val scoreList: List[String] = "scala/data/scores.txt".show1()
"易政".f()
}
//`implicit' modifier cannot be used for top-level objects
//implicit class Demo12(path: String) {
//implicit使用的地方,不能超过object作用域
implicit class Demo12(path: String) {
def show1(): List[String] = {
Source.fromFile(path).getLines().toList
}
def f()={
println(s"好好学习,天天向上!$path")
}
}
隐式转换变量
//定义一个隐式转换参数
def fun1(a1: Int)(implicit a2: Int): Int = a1 + a2
//定义一个隐式转换变量
implicit var i1: Int = 1000
val res1: Int = fun1(100)
println(res1)
标签:String,val,scala,Int,Scala,println,函数
From: https://www.cnblogs.com/justice-pro/p/18339668