Scala_Day02
文章目录
使用scala和java来编写wordcount代码
package org.xlj.day02
import scala.collection.mutable
import scala.io.{BufferedSource, Source}
object WordCountScala {
def main(args: Array[String]): Unit = {
val hashMap: mutable.HashMap[String, Integer] = new mutable.HashMap[String, Integer]()
val bs: BufferedSource = Source.fromFile("src/main/data/words.txt")
for (elem <- bs.getLines()) {
val strings: Array[String] = elem.split(",")
for (elem <- strings) {
if (!hashMap.contains(elem)) {
hashMap.put(elem, 1)
} else {
hashMap.put(elem, hashMap(elem) + 1)
}
}
}
println(hashMap)
}
}
package org.xlj.day02;
import java.io.BufferedReader;
import java.io.FileReader;
import java.util.HashMap;
import java.util.Map;
import java.util.Set;
public class WordCountJava {
public static void main(String[] args) throws Exception {
HashMap<String, Integer> map = new HashMap<>();
BufferedReader br = new BufferedReader(new FileReader("src/main/data/words.txt"));
String line = null;
while ((line = br.readLine()) != null) {
String[] s = line.split(",");
for (String s1 : s) {
if (!map.containsKey(s1)) {
map.put(s1, 1);
} else {
map.put(s1, map.get(s1) + 1);
}
}
}
Set<Map.Entry<String, Integer>> entries = map.entrySet();
for (Map.Entry<String, Integer> entry : entries) {
String key = entry.getKey();
Integer value = entry.getValue();
System.out.println(key + "----" + value);
}
}
}
//scala代码的简化写法
Source
.fromFile("scala/data/words.txt")
.getLines()
.toList
.flatMap(_.split(","))
.groupBy(word=>word)
.map(kv=>s"${kv._1},${kv._2.size}")
.foreach(println)
}
普通函数的省略规则
/*
1.在Scala代码中默认最后一行就是返回值,return关键字可以省略
2.如果代码中只有一行,则花括号可以省略
3.函数的返回值类型可以自动的根据返回值推断出来,所以可以省略(以函数作为返回值时不能省略)
4.如果函数没有参数,则括号可以省略
*/
package org.xlj.day02
object Demo01 {
//定义一个函数,参数类型是String类型,返回值是Int类型,然后将String类型转换为int类型再加上100作为返回值
/*
1.在Scala代码中默认最后一行就是返回值,return关键字可以省略
2.如果代码中只有一行,则花括号可以省略
3.函数的返回值类型可以自动的根据返回值推断出来,所以可以省略
4.如果函数没有参数,则括号可以省略
*/
def func1(s : String) : Int = {
s.toInt + 100
}
def func2 = "200".toInt + 100
def main(args: Array[String]): Unit = {
println(func1("200"))
println(func2)
}
}
将函数作为参数传来传去
package org.xlj.day02
object Demo02 {
//自定义函数func2,传入两个参数一个String类型,一个Int类型,
//将String类型转换为Int类型之后再加上另一个Int类型的参数,最后函数的返回值是Int类型的
def func2(s: String, i: Int): Int = {
s.toInt + i
}
def funX(f: (String, Int) => Int) = {
f("200", 100) + 100
}
//面向对象编程:将对象传来传去,会将对象作为参数或者是返回值进行传递,需要注意对象的类型
//面向函数编程:将函数传来传去,会将函数作为参数或者是返回值进行传递,需要注意函数的类型
/**
* 函数的类型和什么没有关系?
* 1、跟关键宁def没有关系
* 2、跟函数名没有关系
* 3、跟参数名无关
* 4、跟函数实现的功能也无关
*
* 函数的类型怎么描述?
* 由参数的类型(类型、个数、顺序)以及返回值的类型一同决定
* (参数1的类型,参数2的类型,参数3类型) => 返回值类型
*
* 函数式编程:
* 1、以函数作为参数
* 2、以函数作为返回值
*
* @param args
*/
def main(args: Array[String]): Unit = {
println(funX(func2))
}
}
匿名函数的使用规则
package org.xlj.day02
object Demo04 {
// 匿名函数的省略规则
/**
* 匿名函数的省略规则:
* 1.如果代码只有一行,则花括号可以省略
* 2.如果匿名函数是作为参数传给另一个函数的,则参数的类型可以省略
* 3.如果匿名函数只有一个参数,则括号可以省略
* 4.如果匿名函数的参数只被使用了一次,则可以直接用下划线替,并且 => 及 左边的部分都可以省略
*/
(s: String, i: Int) => {
s.toInt + i + 100
}
(s:String) => {
s.toInt + 100
}
def funX(f: (String, Int) => Int) = {
f("200", 100) + 100
}
def funXX(f: (String) => Int) = {
f("200") + 100
}
def main(args: Array[String]): Unit = {
println(funX((s: String, i: Int) =>
s.toInt + i + 100
))
println(funX((s, i) =>
s.toInt + i + 100
))
println(funXX(s =>
s.toInt + 100
))
println(funX(
_.toInt + _ + 100
))
}
}
给匿名函数取名字
package org.xlj.day02
object Demo05 {
//匿名函数也可以取名字
private val function: (String, Int) => Int = (s: String, i: Int) => {
s.toInt + i
}
}
将函数作为返回值使用
package org.xlj.day02
//函数作为返回值进行传递
object HanshuZuoweiFanhuizhi {
def main(args: Array[String]): Unit = {
val intToInt: Int => Int = funXXX("100")
val i: Int = intToInt(100)
println(i)
println("*"*100)
println(funXXX("100")(100))
}
def funXXX(s: String): Int => Int = {
def func1(i: Int): Int = {
s.toInt + i + 100
}
func1
}
}
柯里化函数
package org.xlj.day02
object KeLiHua {
def main(args: Array[String]): Unit = {
val i: Int = func(1, 2, 3, 4)
val i1: Int = funcKLH(1)(2)(3)(4)
val i2: Int = funXXX("100")(100)
println(i,i1,i2)
}
//funXXX的简化写法
def funXXX(s: String)(i: Int): Int = {
s.toInt + i + 100
}
//所谓柯里化函数就是将一个带有N个参数的函数变为N个带有一个参数的函数
def func(i1: Int, i2: Int, i3: Int, i4: Int): Int = {
i1 + i2 + i3 + i4
}
def funcKLH(i1: Int)(i2: Int)(i3: Int)(i4: Int):Int = {
i1 + i2 + i3 + i4
}
}
偏应用函数
package org.xlj.day02
// 将含有一个N个参数的函数变为一个含有N-M个参数的函数
object PainYingYong {
def main(args: Array[String]): Unit = {
val i: Int = funPYY(1, 1)
val i1: Int = funPYY(1, 1, 0, 0)
println(i)
println(i1)
}
def funPYY(i1: Int, i2: Int, i3: Int = 1, i4: Int = 1): Int = {
i1 + i2 + i3 + i4
}
}
Scala中类初步定义和使用
package org.xlj.day02
import scala.beans.BeanProperty
class Student(id: Int, _name: String, age: Int) {
val _id: Int = id
@BeanProperty var name: String = _name //使用@BeanProperty的变量名必须以字母开头
val _age: Int = age
var _clazz: String = _ //_表示之后再对clazz进行初始化
def this(id: Int, name: String, age: Int, clazz: String) = { //构造方法不可以有返回值类型
this(id, name, age)
println("进入了构造方法")
this._clazz = clazz
}
// def getName: String = {
// this._name
// }
//
// def setName(s: String): Unit = {
// this._name = s
// }
override def toString = s"${_id},${_name},${_age},${_clazz}"
}
object Lei {
def main(args: Array[String]): Unit = {
val student = new Student(1001, "xlj", 23)
val student1 = new Student(1002, "xiahu", 25, "dashuju")
student.setName("zss")
println(student.getName())
println(student.toString)
println(student1)
}
}
访问权限问题
在Java中,访问权限分为:public,private,protected和默认。在Scala中,你可以通过类似的修饰符达到同样的效果。但是使用上有区别。
-
Scala 中属性和方法的默认访问权限为public,但Scala中无public关键字。
-
private为私有权限,只在类的内部和伴生对象中可用。
-
protected为受保护权限,Scala中受保护权限比Java中更严格,同类、子类可以访问,同包无法访问。
-
private[包名]增加包访问权限,包名下的其他类也可以使用
伴生类和伴生对象,以及apply方法的使用
package com.shujia
class Demo09ObjectApply(id: String) { // 伴生类
val _id: String = id
private val secret: String = "这是一个秘密"
}
object Demo09ObjectApply { // 伴生对象
def apply(id: String): Demo09ObjectApply = new Demo09ObjectApply(id)
def main(args: Array[String]): Unit = {
val one: Demo09ObjectApply = new Demo09ObjectApply("001") // 调用默认的构造方法创建对象
val two: Demo09ObjectApply = Demo09ObjectApply("002") // 调用伴生对象的apply方法来创建对象
println(one.secret)
println(two.secret)
}
}