Kotlin进阶知识(一)——重载算术运算符

682 阅读2分钟

一、重载二元算术运算

  • 定义一个***plus***运算符
// 定义
data class Point(val x: Int, val y: Int) {
    // 定义一个名为“plus”的方法
    operator fun plus(other: Point): Point {
        // 坐标分别相加,然后返回一个新的点
        return Point(x + other.x, y + other.y)
    }
}

// 测试
>>> val p1 = Point(10, 20)
>>> val p2 = Point(30, 40)
>>> Point(p1 + p2)
Point(x=40, y=60)

关键字***operator***:用于重载运算符的所有函数都需要用该关键字标记,用来表示将该函数作为相对的约定的实现。

  • 运算符可以被定义为扩展函数

可重载的二元算术运算符

表达式函数名
a * btimes
a / bdiv
a + bplus
a - bminus

自定义类型的运算符,基本上和与标准数字类型的运算符有着相同的优先级。

注意:Kotlin运算符不会自动支持交换性(交换运算符的左右两边)。

二、重载复合赋值运算符

复合赋值运算符+=、-=

>>> var point = Point(1, 2)
>>> point += Point(3, 4)
>>> println(point)
Point(x=4, y=6)

上述等效于 **point = point + Point(3, 4)**的写法。

  • 定义**+=运算可以修改使用它的变量所引用的对象,但不会重新分配引用**。

Kotlin标准库支持集合的这两种方法:“+”和“-”运算符总是返回一个新的集合“+=”和“-=”运算符用于可变集合时,始终就地修改它们;而它们用于只读集合时,会返回一个修改过的副本(这意味着只有当引用只读集合的变量被声明为**var**的时候,才能使用“+=”和“-=”)

三、重载一元运算符

重载一元运算符的过程和之前的方法相同:用预先定义的一个名称来声明函数(成员函数或扩展函数),并用修饰符**operator**标记。

  • 定义一个一元运算符
// 一元运算符无参数
operator fun Point.unaryMinus(): Point {
    // 坐标取反再返回
    return Point(-x, -y)
}

>>> val p = Point(10, 20)
>>> println(-p)
Point(x=-10, y=-20)

可重载的一元算法的运算符

表达式函数名
+aunaryPlus
-aunaryMinus
!anot
++a, a++inc
--a, a--dec
  • 定义一个自增运算符
operator fun BigDecimal.inc() = this + BigDecimal.ONE

// 在第一个println语句执行后增加
>>> var bd = BigDecimal.ZERO
>>> println(bd++)
0
// 在第二个println语句执行前增加
>>> println(++bd)
2