Scala学习(一)——基础语法
Scala语言是一种面向对象语言,结合了命令式(imperative)和函数式(functional)编程风格,其设计理念是创造一种更好地支持组件的语言。
特性
多范式(Multi-Paradigm)编程语言,类似Java、C#;
继承面向对象编程和函数式编程的特性;
面向对象:[1]. 子类继承,[2]. 混入(Mixin)机制;
函数式:支持高阶函数、嵌套函数,模式匹配,支持柯里化(Currying);
类型推断(Type Inference):根据函数体中的具体内容推断方法的返回值类型
更高层的并发模型,可伸缩;
静态类型,编译时检查;
允许与Java互操作(将来会支持与.Net互操作);
与Java对比
如果用作服务器端开发,Scala的简洁、灵活性是Java无法比拟的;
如果是企业级应用开发、Web开发,Java的强大是Scala无法匹敌的;
基础语法
表达式(Expressions)
表达式是可计算的语句。您可以使用println输出表达式的结果。
println(1) // 1
println(1 + 1) // 2
println("Hello!") // Hello!
println("Hello," + " world!") // Hello, world!
值(Values)
您可以使用val关键字命名表达式的结果。
val x = 1 + 1
println(x) // 2
命名结果(例如x)称为值。引用值不会重新计算它。值无法被重新分配。
val x = 1 + 1
x = 3 // This does not compile.
可以推断出值的类型,但您也可以显式声明类型,如下所示:
val x: Int = 1 + 1
注意类型声明Int如何在标识符x之后出现,你还需要一个“:”
变量(Variables)
变量就像值,除了你可以重新赋值。您可以使用var关键字定义变量。
var x = 1 + 1
x = 3 // This compiles because "x" is declared with the "var" keyword.
println(x * x) // 9
与值一样,您可以根据需要明确说明类型:
var x: Int = 1 + 1
块(Blocks)
您可以通过用{}包围表达式来组合表达式。我们称之为块。块中最后一个表达式的结果也是整个块的结果。
println({
val x = 1 + 1
x + 1
}) // 3
函数(Functions)
函数是带参数的表达式。
您可以定义一个返回给定整数加一的匿名函数(即无名称):
(x: Int) => x + 1
在=>的左边是参数列表。右边是涉及参数的表达式。
您也可以命名函数。
val addOne = (x: Int) => x + 1
println(addOne(1)) // 2
函数可能需要多个参数。
val add = (x: Int, y: Int) => x + y
println(add(1, 2)) // 3
或者它不需要参数。
val getTheAnswer = () => 42
println(getTheAnswer()) // 42
方法(Methods)
方法的外观和行为与函数非常相似,但它们之间存在一些关键差异。
方法使用def关键字定义。 def后跟名称,参数列表,返回类型和正文。
def add(x: Int, y: Int): Int = x + y
println(add(1, 2)) // 3
注意如何在参数列表和冒号之后声明返回类型:Int。
方法可以采用多个参数列表。
def addThenMultiply(x: Int, y: Int)(multiplier: Int): Int = (x + y) * multiplier
println(addThenMultiply(1, 2)(3)) // 9
或者根本没有参数列表。
def name: String = System.getProperty("user.name")
println("Hello, " + name + "!")
还有一些其他差异,但就目前而言,您可以将它们视为与函数类似的东西。
方法也可以有多行表达式。
def getSquareString(input: Double): String = {
val square = input * input
square.toString
}
正文中的最后一个表达式是方法的返回值。 (Scala确实有一个return关键字,但它很少使用。)
关于方法(Method)和函数(Function)
函数是一等公民,使用val语句可以定义函数,def语句定义方法;
函数是一个对象,继承自FuctionN,函数对象有curried,equals,isInstanceOf,toString等方法,而方法不具有;
函数是一个值,可以给val变量赋值,方法不是值、也不可以给val变量赋值;
通过将方法转化为函数的方式 method _ 或 method(_) 实现给val变量赋值;
若 method 有重载的情况,方法转化为函数时必须指定参数和返回值的类型;
某些情况下,编译器可以根据上下文自动将方法转换为函数;
无参数的方法 method 没有参数列表(调用:method),无参数的函数 function 有空列表(调用:function());
方法可以使用参数序列,转换为函数后,必须用 Seq 包装参数序列;
方法支持默认参数,函数不支持、会忽略之;
类(Classes)
您可以使用class关键字定义类,后跟其名称和构造函数参数。
class Greeter(prefix: String, suffix: String) {
def greet(name: String): Unit =
println(prefix + name + suffix)
}
方法greet的返回类型是Unit,它表示返回没有任何意义。它与Java和C中的void类似地使用。(不同之处在于,因为每个Scala表达式必须具有某个值,实际上存在Unit类型的单例值,write()。它不携带任何信息。)
您可以使用new关键字创建类的实例。
val greeter = new Greeter("Hello, ", "!")
greeter.greet("Scala developer") // Hello, Scala developer!
样本类(Case Classes)
Scala有一种特殊类型的类,称为样本类。默认情况下,样本类是不可变的,并按值进行比较。您可以使用“case class”关键字定义案例类。
case class Point(x: Int, y: Int)
您可以在没有new关键字的情况下实例化样本类。
val point = Point(1, 2)
val anotherPoint = Point(1, 2)
val yetAnotherPoint = Point(2, 2)
并且它们按值进行比较。
if (point == anotherPoint) {
println(point + " and " + anotherPoint + " are the same.")
} else {
println(point + " and " + anotherPoint + " are different.")
}
// Point(1,2) and Point(1,2) are the same.
if (point == yetAnotherPoint) {
println(point + " and " + yetAnotherPoint + " are the same.")
} else {
println(point + " and " + yetAnotherPoint + " are different.")
}
// Point(1,2) and Point(2,2) are different.
对象(Objects)
对象是它们自己定义的单个实例。你可以把它们想象成自己班级的单身人士。
您可以使用object关键字定义对象。
object IdFactory {
private var counter = 0
def create(): Int = {
counter += 1
counter
}
}
您可以通过引用其名称来访问该对象。
val newId: Int = IdFactory.create()
println(newId) // 1
val newerId: Int = IdFactory.create()
println(newerId) // 2
抽象类
你可以定义一个抽象类,它定义了一些方法但没有实现它们。取而代之是由扩展抽象类的子类定义这些方法。你不能创建抽象类的实例。
abstract class Shape {
def getArea():Int // subclass should define this
}
class Circle(r: Int) extends Shape {
def getArea():Int = { r * r * 3 }
}
val s = new Shape //error: class Shape is abstract; cannot be instantiated
val c = new Circle(2)
特质(Traits)
特质是包含某些字段和方法的类型。可以组合多种特质。
您可以使用trait关键字定义特质。
trait Greeter {
def greet(name: String): Unit
}
特质也可以有默认实现。
trait Greeter {
def greet(name: String): Unit =
println("Hello, " + name + "!")
}
您可以使用extends关键字扩展traits并使用override关键字覆盖实现。
class DefaultGreeter extends Greeter
class CustomizableGreeter(prefix: String, postfix: String) extends Greeter {
override def greet(name: String): Unit = {
println(prefix + name + postfix)
}
}
val greeter = new DefaultGreeter()
greeter.greet("Scala developer") // Hello, Scala developer!
val customGreeter = new CustomizableGreeter("How are you, ", "?")
customGreeter.greet("Scala developer") // How are you, Scala developer?
在这里,DefaultGreeter只扩展了一个特质,但它可以扩展多个特质。
什么时候应该使用特质而不是抽象类?
如果你想定义一个类似接口的类型,你可能会在特质和抽象类之间难以取舍。这两种形式都可以让你定义一个类型的一些行为,并要求继承者定义一些其他行为。一些经验法则:
优先使用特质。一个类扩展多个特质是很方便的,但却只能扩展一个抽象类。
如果你需要构造函数参数,使用抽象类。因为抽象类可以定义带参数的构造函数,而特质不行。例如,你不能说trait t(i: Int) {},参数i是非法的。
Main方法
Main方法是程序的切入点。 Java虚拟机需要将main方法命名为main,并使用一个参数,即一个字符串数组。
使用对象,您可以按如下方式定义main方法:
object Main {
def main(args: Array[String]): Unit =
println("Hello, Scala developer!")
}
本文主要翻译自Basics|Scala Documentation
Scala学习(一)——基础语法的更多相关文章
- JavaScript学习02 基础语法
JavaScript学习02 基础语法 JavaScript中很多基础内容和Java中大体上基本一样,所以不需要再单独重复讲了,包括: 各种算术运算符.比较运算符.逻辑运算符: if else语句.s ...
- Scala快速入门 - 基础语法篇
本篇文章首发于头条号Scala快速入门 - 基础语法篇,欢迎关注我的头条号和微信公众号"大数据技术和人工智能"(微信搜索bigdata_ai_tech)获取更多干货,也欢迎关注我的 ...
- Scala简介及基础语法
一.scala简介 官网:https://www.scala-lang.org/ Scala语言很强大,集成了面向对象和函数式编程的特点. 运行在JVM(jdk). 大数据中为什么学习scala? s ...
- JavaScript学习笔记-基础语法、类型、变量
基础语法.类型.变量 非数字值的判断方法:(因为Infinity和NaN他们不等于任何值,包括自身) 1.用x != x ,当x为NaN时才返回true; 2.用isNaN(x) ,当x为NaN或 ...
- less学习:基础语法总结
一. less是什么 Less 是一门 CSS 预处理语言,它扩充了 CSS 语言,增加了诸如变量.混合(mixin).函数等功能,让 CSS 更易维护.方便制作主题.扩充. 注意1):less使用. ...
- Python学习①. 基础语法
Python 简介 Python 是一种解释型,面向对象的语言.特点是语法简单,可跨平台 Python 基础语法 交互式编程 交互式编程不需要创建脚本文件,是通过 Python 解释器的交互模式进来编 ...
- 真香,理解记忆法学习Python基础语法
这篇文章很难写!我最开始学 Python,和大多数人一样,是看的菜鸟教程: 在写完这篇文章的第一遍后,我发现并没有写出新意,很可能读者看到后,会和我当初一样,很快就忘了.我现在已经不是读者而是作者了, ...
- Scala - 快速学习03 - 基础语法
1- 变量 变量 mutable variable 在程序运行过程中其值可能发生改变的量 关键词var定义变量,定义时直接进行求值 常量 immutable variable 在程序运行过程中其值不会 ...
- 学习fortran77基础语法
Program ParamaterDefine Implicit None C FORTRAN变量名和关键字不区分大小写.但调用外部函数的话,需要在编译选项里指定 c 大小写等选项 因为链接器是区分大 ...
- Python学习--Python基础语法
第一个Python程序 交互式编程 交互式编程不需要创建脚本文件,是通过 Python 解释器的交互模式进来编写代码. linux上你只需要在命令行中输入 Python 命令即可启动交互式编程,提示窗 ...
随机推荐
- O016、搭建实验环境
参考https://www.cnblogs.com/CloudMan6/p/5350536.html 在学习 OpenStack 各服务之前,需要先搭建一个实验环境. 一个看得到摸得着而且能让 ...
- 富文本编辑器--引入demo和简单使用
wangEditor —— 轻量级 web 富文本编辑器,配置方便,使用简单.支持 IE10+ 浏览器. 官网:www.wangEditor.com 文档:www.kancloud.cn/wangfu ...
- 25、Nginx常见典型故障
1.为什么nginx里面有的是浏览器渲染出的页面,有的时候就变成下载文件? 这个一个取决于服务端nginx,一个取决于你浏览器.在Nginx服务端的配置文件目录下,有一个mime.types 文件,内 ...
- oracle修改某个表的字段顺序
有时候会发现某个表的列顺序不理想,想修改 -1查询表, select * from AIRWAY_TYPE t --2 查询用户和表名,找到obj#,select object_id from all ...
- Oracle批量导出表数据到CSV文件
需求:把oracle数据库中符合条件的n多表,导出成csv文本文件,并以表名.csv为文件名存放. 实现:通过存储过程中utl_file函数来实现.导出的csv文件放入提前创建好的directory中 ...
- php多个数组组合算法 火车头免登录发布接口代码备忘
火车头发布产品的时候,有颜色.尺码.性别等等产品属性,需要进行不重复的组合,变成不重复的数组 <?php function comb($a){ $a = array_filter($a); $o ...
- glViewport函数用法
一. 其函数原型为glViewport(GLint x,GLint y,GLsizei width,GLsizei height) x,y 以像素为单位,指定了窗口的左下角位置. width,heig ...
- 文件操作相关函数(POSIX 标准 open,read,write,lseek,close)
POSIX标准 open函数属于Linux中系统IO,用于“打开”文件,代码打开一个文件意味着获得了这个文件的访问句柄. int fd = open(参数1,参数2,参数3): int fd = op ...
- C语言/C++知识
<C与指针>pdf 下载: 新浪微盘: https://vdisk.weibo.com/s/A6gkKkHrGH0g
- linux 下mysql忘记密码或者安装好linux后不知道mysql初始密码解决方案
1.使用yum安装mysql后 2.初始密码在/var/log/mysqld.log这个文件里 3.输入命令:grep 'temporary password' /var/log/mysqld.log ...