scala(3)

强调:

(1)子类继承父类,如果new一个子类,那么一定会先去调用父类的构造方法。

(2)private[this] 表示私有的,只能在自己的类里面使用,子类不能用

1.字符串插值

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
def main(args: Array[String]): Unit = {
val name="哈哈"
println("name is:"+name)
//String Interpolation 插值
println(s"name is:$name")

// 字符串多行
val lines=
s"""
|好好学习天天向上
|$name
|向前看
""".stripMargin
println(lines)
}

2.读取文件

(1)读取本地文件

1
2
3
4
5
6
7
8
9
def main(args: Array[String]): Unit = {
//Source是 io的包,不要导错了
val lines=Source.fromFile("d:/workspace/xixi.txt")//传进来一个路径

for (line <- lines){//这里也可以用 line <-lines.getlines(),然后 println打印
print(line)
}

}

(2)读取网络资源

1
2
3
4
val lines =Source.fromURL("http://www.baidu.com")
for (line<-lines.getLines()){
println(line)
}

比如说现在有很多工具类,都是java的,在scala中也可以调用java的类。

3.Haoop读取文件

1.首先需要引入依赖

1
2
3
4
5
6
7
8
9
10
11
12
13
//环境上装的Haoop是 hadoop-2.6.0-cdh5.7.0
// 我们编程引入依赖可以引入不一样的,相邻的也没有关系,因为我们打包打的是瘦包,
// 仅仅是把代码打进去,Hadoop没有打
<dependency>
<groupId>org.apache.hadoop</groupId>
<artifactId>hadoop-client</artifactId>
<version>2.6.5</version>
</dependency>

// 如果要用cdh依赖,那么 还需要加
<repositories>
<repository></repository>
</repositories>

2.编写程序

(1)创建文件系统入口

1
2
3
4
5
6
7
8
9
10
11
12
def main(args: Array[String]): Unit = {
//new 一个配置参数
val configuration=new Configuration()

// 创建一个文件系统的入口,FileSystem.get(URI,configuration)
// 获取两个参数,这个入口就可以直接操作hdfs
val filesystem=FileSystem.get(new URI("hdfs://hadoop001:8020"),configuration)

//传入一个Path路径,在hdfs上创建文件夹,返回值是一个 Bolean类型
val flag=filesystem.mkdirs(new Path("/date/system"))
println(flag)
}

(2)对hadfs上的文件或文件夹进行书写操作

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
//创建一个文件
val out=filesystem.create(new Path("/date/system/g6_text"))
//并向文件中写入,用流写出来
out.write("若泽大数据".getBytes)
out.flush() //最好刷新一下,因为写出来的放在缓存区
out.close() //关流

//更改文件的名字
val src=new Path("/date/system/g6_text") //原始路径
val dst=new Path("/date/system/g6_text1") //更改名字后的路径
val flag=filesystem.rename(src,dst)
print(flag)

//删除文件夹及文件
//true 表示是否采用递归
val flag =filesystem.delete(new Path("/date/system/"),true)
print(flag)

3.数组

(1)定长

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
//存放类型:数组中存放的是同一个数据类型
//长度:定长和变长

//定义一个长度为5的数组,存放的是String类型数据
scala> val a=new Array[String](5)
a: Array[String] = Array(null, null, null, null, null)

//求数组长度
scala> a.length
res1: Int = 5

//数组中的Index是从0开始的,如果要赋值,
scala> a(1)="ruoze"
scala> a
res4: Array[String] = Array(null, ruoze, null, null, null)

//方法
a.max
a.min
a.count(_>5)
//将所有元素连在一起
1)a.mkString //结果:ruozexiaoxinwangwu
2)a.mkString(Seq:String) //Seq表示分隔符,用什么分割
//看源码
def mkString(start: String, sep: String, end: String): String =
addString(new StringBuilder(), start, sep, end).toString

def mkString(sep: String): String = mkString("", sep, "")//调用上面的方法

def mkString: String = mkString("")//调用的是上面的方法


// 直接传值
def main(args: Array[String]): Unit = {
//定义一个数组,并传入数据
val array=Array("ruoze","xiaoxin","wangwu")
}

//这里我们发现我们并没有new一个对象,为什么也可以呢?
//看底层源码,有apply这一个方法
// xs: "ruoze","jepson","diewu"
//底层帮我们new了一个Array对象,然后通过迭代器,将传进来的元素赋值给 array,然后返回array
val array = new Array[String](3)
var i = 0
for (x <- xs.iterator) {
array(i) = x;
i += 1
}

i=0
array(0) = ruoze
i=1
array(1) = jepson
i=2
array(2) = diewu

val array = new Array[String](3)
array(0) = ruoze
array(1) = jepson
array(2) = diewu
array

注意:这种 Array() ==> Array Object.apply 调用的是Objet里面的 apply方法
// 表象上看是没有new的,但是底层其实还是new

(2)变长

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
变长:ArrayBuffer
scala> import scala.collection.mutable.ArrayBuffer//导入这个包
import scala.collection.mutable.ArrayBuffer

scala> val d=ArrayBuffer[Int]()
d: scala.collection.mutable.ArrayBuffer[Nothing] = ArrayBuffer()

//长度
scala> d.length
res7: Int = 0

//向集合中添加元素
scala> d+=1
res12: d.type = ArrayBuffer(1)
//加一个定长
scala> d +=(2,3,4)
res13: d.type = ArrayBuffer(1, 2, 3, 4)
//++ 加一个定长的数组
scala> d ++=Array(5,6,7)
res14: d.type = ArrayBuffer(1, 2, 3, 4, 5, 6, 7)

//插入元素 insert
insert(n: Int, elems: A*)
n:表示Index
A*:表示的是一个可变的元素 (12),也可以是(12345

scala> d.insert(0,0)
//会发现 第1个元素变成了0
scala> d
res16: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(0, 1, 2, 3, 4, 5, 6, 7)

//减掉元素
scala> d.remove(1)
res17: Int = 1

scala> d
res18: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(0, 2, 3, 4, 5, 6, 7)
//从哪个位置开始剪掉3个
scala> d.remove(0,3)

scala> d
res20: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(4, 5, 6, 7)

//移除最后几个元素
scala> d.trimEnd(2)

scala> d
res23: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(4, 5)

//变长转为定长
scala> d.toArray
res24: Array[Int] = Array(4, 5)

4.StringBuilder vs StringBuffer

1
2
3
4
5
6
String Buffer  线程是安全
在里面有 synchronized(锁) 这个关键字

扩展
Vector 安全的
ArrayList 不安全的

5.Nil是什么

1
2
3
4
scala> Nil
res25: scala.collection.immutable.Nil.type = List()

Nil就是一个空的List

6.List

一个类型的N个元素,有序可重复的

(1)定长

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
//定义一个List集合
scala> val l=List(1,2,3,4)
l: List[Int] = List(1, 2, 3, 4)
//查看
scala> l
res26: List[Int] = List(1, 2, 3, 4)

//一个集合是又一个头加一个尾巴组成
//List集合中的头
scala> l.head
res27: Int = 1

//List集合中的尾
scala> l.tail
res28: List[Int] = List(2, 3, 4)

// 1表示头,::表示拼接,Nil表示尾巴的集合
scala> val l2=1::Nil
l2: List[Int] = List(1)

scala> l2
res30: List[Int] = List(1)

(2)变长

1
2
3
scala> val l3=ListBuffer[Int]()
l3: scala.collection.mutable.ListBuffer[Int] = ListBuffer()
其它操作方法 和 Array一样

7Map 映射 key=value

(1)定长

1
2
3
4
5
6
7
//定义一个Map
scala> val m=Map("ruoze"->18,"dashu"->20)
m: scala.collection.immutable.Map[String,Int] = Map(ruoze -> 18, dashu -> 20)

//取值
scala> m("ruoze")
res31: Int = 18

(2)变长

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
//mutable 表示可变

scala> import scala.collection.mutable
import scala.collection.mutable

scala> val f=scala.collection.mutable.Map("ruoze"->18,"dashu"->20)
f: scala.collection.mutable.Map[String,Int] = Map(ruoze -> 18, dashu -> 20)

//也可以用HashMap 取值比较舒服
scala> val g=scala.collection.mutable.HashMap[String,Int]()
g: scala.collection.mutable.HashMap[String,Int] = Map()

scala> g("ruoze")=18

res33: scala.collection.mutable.HashMap[String,Int] = Map(ruoze -> 18)

scala> g +=("wangwu"->30,"lisi"->15)
res34: g.type = Map(lisi -> 15, ruoze -> 18, wangwu -> 30)

(3)for循环取值

1
2
3
4
5
6
7
8
9
10
11
12
13
14
  val b=mutable.Map("ruoze"->18,"大树"->20)
1//第一种方式,这种是将b中赋值给key和value,
for ((key,value)<-b){
println(key+" :"+value)
}

2//第二种方式,将所有的key取出来,赋值给key,然后通过getOrElse取出value,如果没有取成功,则返回0
for (key<-b.keySet){
println(key+" : "+b.getOrElse(key,0))
}
3//第三种只取value,不关注key
for (value<-b.values){
println(value)
}

(4)[Option]

1
2
3
4
5
6
7
8
9
10
11
for (key<-b.keySet){
println(key+" : "+b.get(key)) //ctil+左键点进去看源码
//这里b.get(key)底层调用的是 Option,是一个抽象类
abstract class Option //抽象类

//这个抽象类下有两个子类,一个是取到值,一个是没有取到值
class Some[+A](x: A) extends Option[A] 取上
object None extends Option 没取上

//如果没有取到值,就会报错,这是不允许的,所以我们要调用这个方法
b.getOrElse(key,0) //取不到给我返回一个 东西

(5)case class

1
2
定义 的是一个 实体类,
想要用,不需要new,直接用

(6)可变参数

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
def main(args: Array[String]): Unit = {
println(sum(1,5))
println(sum(1,5,6))
println(sum(1,5,7,8))
println(sum(1.to(10):_*)) //把一个Range转变成一个可变参数

}

// Int*表示传进来的参数是Int类型的,可以传入多个
def sum(nums: Int*)={
var result=0
for (num<-nums){
result += num
}
result
}

(7)默认参数

1
2
3
4
5
6
7
def main(args: Array[String]): Unit = {
say() //如果这样调用,打印出来的默认参数
say("ruoze") //如果这样调用,打印出来的就是传进来的参数
}
def say(name:String="若泽"): Unit ={
println(name)
}

8.模式匹配

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
定义:变量 match{
case1 => 代码
case2 => 代码
case3 => 代码
}

//例子
def main(args: Array[String]): Unit = {
val coaches=Array("你","我","他")
val coach =coaches(Random.nextInt(coaches.length))

print(say(coach))

def say(name:String)=name match {
case "你" => println("You")
case "我" => println("Me")
case _ => println("He")
}
}

生产上用于异常处理

1
2
3
4
5
6
7
8
9
10
11
 try{
val i=1/0
}catch {

// 这里匹配的是异常,匹配的是一个类型
case e:ArithmeticException => throw new RuntimeException("除数不能为0")
case e:Exception =>e.printStackTrace()

}finally{

}
总结:模式匹配,既可以匹配类型,也可以匹配值

PartialFunction 偏函数

1
2
3
4
5
6
7
8
9
   print(say2(coach))
//第一个参数是传入参数类型,第二个参数是返回值类型
def say2:PartialFunction[String,String] ={
case "你" => "You"
case "我" => "Me"
case _ => "He"
}
是一种{}内没有 match的一种语句
偏函数和模式匹配是一样的 ,但是必须要知道

9.补充

集合

Tuple

1
2
val a=(1.2.3.4.5)   //这种定义 都是 Tuple
a._1 // 取值

本文标题:scala(3)

文章作者:skygzx

发布时间:2019年04月26日 - 19:45

最后更新:2019年04月28日 - 16:14

原始链接:http://yoursite.com/2019/04/26/Scala(3)/

许可协议: 署名-非商业性使用-禁止演绎 4.0 国际 转载请保留原文链接及作者。

-------------本文结束感谢您的阅读-------------
0%