swift_重载和自定义运算符

像这样定义一个结构体

struct Vector2D {

var x = 0.0

var y = 0.0

}

当 Vector2D 的两个变量相加时,我们需要这样做:

let v1 = Vector2D(x: 2.0, y: 3.0)
let v2 = Vector2D(x: 4.0, y: 5.0)
var v3 = Vector2D(x: v1.x + v2.x, y: v1.y + v2.y) 

只是一次这样的相加还好,如果需要多次重复用到这两个结构体的相加运算,就有必要重载一下 + 运算符。

func + (left: Vector2D, right: Vector2D) -> Vector2D {
    return Vector2D(x: left.x + right.x, y: left.y + right.y)
}

这样,这两个结构体相加就变得很简单了。

v3 = v1 +v2   // {x
6.0, y 8.0}

重载操作使运算变得简单,但 swift 有规定:等号运算符 = 和三木运算符 (a ? b : c) 不可被重载。

当标准的操作符不满足我们的要求时,就需要自定义一些操作符。

新的操作符需要用 operator 关键字声明在全局变量中,可以用 prefix,infix,postfix 声明

例如:

  • prefixoperator
    ? {}

现在我们定义一个新的操作符 ? 使结构体 Vector2D 做向量相乘

i infix operator ? {
    associativity none
    precedence 160
}

infix

表示要定义的是一个中位操作符,即前后都是输入

associativity

定义了结合律,即如果多个同类的操作符顺序出现的计算顺序。比如常见的加法和减法都是
left,就是说多个加法同时出现时按照从左往右的顺序计算
(因为加法满足交换律,所以这个顺序无所谓,但是减法的话计算顺序就很重要了)。点乘的结果是一个
Double,不再会和其他点乘结合使用,所以这里写成
none;详见:这里

precedence

运算的优先级,越高的话优先进行计算。swift 中乘法和除法的优先级是 150 ,加法和减法的优先级是 140 ,这里我们定义点积的优先级为 160 ,就是说应该早于普通的乘除进行运算。

func ? (left: Vector2D, right: Vector2D) -> Double {
    return left.x * right.x + left.y * right.y
}

let value = v1
? v2 // 23.0

这样就可以进行向量的点积运算了。

参考资料:

Advanced Operators

造个类型不是梦-白话swift类型创建

时间: 2024-08-04 08:24:42

swift_重载和自定义运算符的相关文章

C++重载流插入运算符和流提取运算符

C++的流插入运算符“<<”和流提取运算符“>>”是C++在类库中提供的,所有C++编译系统都在类库中提供输入流类istream和输出流类ostream.cin和cout分别是istream类和ostream类的对象.在类库提供的头文件中已经对“<<”和“>>”进行了重载,使之作为流插入运算符和流提取运算符,能用来输出和输入C++标准类型的数据.因此,凡是用“cout<<”和“cin>>”对标准类型数据进行输入输出的,都要用#incl

C++中不可重载5个运算符

C++中不可重载的5个运算符 C++中的大部分运算符都是可以重载的,只有以下5个运算符不可以重载,他们是: 1  .(点运算符)通常用于去对象的成员,但是->(箭头运算符),是可以重载的 2  ::(域运算符)即类名+域运算符,取成员,不可以重载 3  .*(点星运算符,)不可以重载,成员指针运算符".*,即成员是指针类型 4  ?:(条件运算符)不可以重载 5  sizeof不可以重载

网易云课堂_C++程序设计入门(下)_第8单元:年年岁岁花相似– 运算符重载_第8单元 - 作业2:OJ编程 - 重载数组下标运算符

第8单元 - 作业2:OJ编程 - 重载数组下标运算符 查看帮助 返回 温馨提示: 1.本次作业属于Online Judge题目,提交后由系统即时判分. 2.学生可以在作业截止时间之前不限次数提交答案,系统将取其中的最高分作为最终成绩. 练习数组下标运算符重载 依照学术诚信条款,我保证此作业是本人独立完成的. 1 练习数组下标运算符重载(6分) 本题目具体内容请参见 [第8单元 - 单元作业2说明] 时间限制:500ms内存限制:32000kb #include <iostream> #in

Swift_ uitableview使用自定义cell

uitableview 使用 xib 的自定义cell 新建cell:(假如命名 MyCell) 使用: 向 tableview 注册 nib 全局变量 let cellIdentifier = "myCell" myTableView!.registerNib(UINib(nibName: "MyCell", bundle:nil), forCellReuseIdentifier: cellIdentifier) 然后在 cellForRowAtIndexPath

C++ Primer 学习笔记_27_操作符重载与转换(2)--++/--运算符重载、!运算符重载、赋值运算符重载 、String类([]、 +、 += 运算符重载)、&gt;&gt;和&lt;&lt;运算符重载

C++ Primer 学习笔记_27_操作符重载与转换(2)--++/--运算符重载.!运算符重载.赋值运算符重载 .String类([]. +. += 运算符重载).>>和<<运算符重载 一.++/--运算符重载 1.前置++运算符重载 成员函数的方式重载,原型为: 函数类型 & operator++(); 友元函数的方式重载,原型为: friend 函数类型 & operator++(类类型 &); 2.后置++运算符重载 成员函数的方式重载,原型为:

C++运算符重载——输入/输出运算符

为了与IO标准库一致,重载输入输出运算符函数的第一个行参应该是流的引用,第二个行参是对象的引用. 如果重载为类的成员函数,第一个行参应该是对象的引用,第二个行参是流的引用. 使用方式是 ClassObj << cout 这样与标准IO库就不一致了,所以输入输出运算符不能重载为类的成员函数,可以重载为类的友元函数和普通函数. 通常重载输出运算符的第二个行参是const的,因为输出一个类不许要更改它: 但是重载输入运算符的第二个行参必须是非const的,否则无法赋值. 重载的基本方法如下: //重

Swift学习(一):自定义运算符 operator

自定义运算符仅能包含这些字符: / = - + * % < >!& | ^.~ 运算符位置: 前置运算符 prefix 中间运算符 infix 后置运算符 postfix 运算符其他配置 结合性 associativity 可取值范围 left,right和none 优先级 precedence 可取值范围 0-255 系统内置运算符结合性质及优先级 求幂相关(无结合,优先级160) << 按位左移(Bitwise left shift) >> 按位右移(Bit

C++重载自增运算符的效率问题

C++规定后缀形式有一个int类型参数,当函数被调用时,编译器传递一个0做为int参数的值给该函数. increment的前缀形式表示“增加然后取回”,后缀形式表示“取回然后增加”. 1 #include "stdafx.h" 2 #include "assert.h" 3 class A 4 { 5 public: 6 A(int i) 7 :m_i(i) 8 { 9 } 10 // ++i 11 A& operator++() 12 { 13 ++m_i

people为基类,student和graduate为子类,重载“==”运算符

//people为基类,student和graduate为子类,重载“==”运算符 //输入2个学生的信息:姓名.编号.身份证号.班级.专业 //输入1个研究生的信息:姓名.编号.身份证号.班级.专业.导师 //重载“==”,当两个学生的编号相同时,调用重载运算符,输出错误信息 源代码如下: #include <iostream>#include <string>using namespace std;//定义基类class People { public: //成员变量:姓名,编