方法是与某些特定类型相关联的函数。
类、结构体、枚举都可以既定义实例方法,也可以定义类型方法。
- 实例方法为给定类型的实例封装了具体的任务与功能。
- 类型方法与类型本身相关联。
实例方法
实例方法是属于某个特定类、结构体或者枚举类型实例的方法。通过实例对象进行调用。
其调用形式同调用属性一样,通过 . 语法
class Person {
var age: Int = 18
func ageAdd() {
age += 1
}
}
var p = Person()
p.ageAdd()
self 属性
类型的每一个实例都有一个隐含属性叫做 self,self 完全等同于该实例本身。你可以在一个实例的实例方法中使用这个隐含的 self 属性来引用当前实例。
比如上面的例子:如果加上 self,则:
class Person {
var age: Int = 18
func ageAdd() {
self.age += 1
}
}
一般情况下无需写 self。不论何时,只要在一个方法中使用一个已知的属性或者方法名称,如果没有明确地写 self,则Swift 假定你是指当前实例的属性或者方法。
但是当实例方法的某个参数名称与实例的某个属性名称相同的时候。此时,参数名称享有优先权,需要使用 self 属性来区分参数名称和属性名称。
如 Person 类中,存储属性 age 和 形参 age 名称,如果不加self,则比较的判断条件中的两个 age 均指的是就近的形参 age:
class Person {
var age: Int = 18
func ageCompare(other age: Int) {
if age > age {
print("自己年纪更大")
} else if age < age {
print("自己年纪更小")
} else {
print("年纪相等")
}
}
}
var p = Person();
p.ageCompare(other: 17)
输入
年纪相等
此时必须要使用 self 来区分二者:
class Person {
var age: Int = 18
func ageCompare(other age: Int) {
if self.age > age {
print("自己年纪更大")
} else if self.age < age {
print("自己年纪更小")
} else {
print("年纪相等")
}
}
}
var p = Person();
p.ageCompare(other: 17)
输出:
自己年纪更大
结构体和枚举在实例方法中修改值类型
结构体和枚举是值类型。默认情况下,值类型的属性不能在它的实例方法中被修改。
但是,如果你确实需要在某个特定的方法中修改结构体或者枚举的属性,你可以为这个方法选择 可变(mutating)行为,然后就可以从其方法内部改变它的属性;并且这个方法做的任何改变都会在方法执行结束时写回到原始结构中。方法还可以给它隐含的 self 属性赋予一个全新的实例,这个新实例在方法结束时会替换现存实例。
要使用 可变方法,将关键字 mutating 放到方法的 func 关键字之前就可以了
不加编译报错:
image.png
添加关键字 mutating:
struct Point {
var x = 0.0
var y = 0.0
mutating func moveBy(deltaX: Double, y deltaY: Double) {
x += deltaX
y += deltaY
}
}
var p = Point()
p.moveBy(deltaX: 1, y: 2)
print(p.x, p.y) //1.0 2.0
上面的 Point 结构体定义了一个可变方法 moveByX(_:y:) 来移动 Point 实例到给定的位置。该方法被调用时修改了这个点,而不是返回一个新的点。方法定义时加上了 mutating 关键字,从而允许修改属性。
:不能在结构体类型的常量(a constant of structure type)上调用可变方法,因为其属性不能被改变,即使属性是变量属性。
如:
类型方法
定义在类型本身上调用的方法。在方法的 func 关键字之前加上关键字 static,来指定类型方法。类还可以用关键字 class 来允许子类重写父类的方法实现。
类型方法和实例方法一样用点语法调用。但是是,通过类型调用这个方法。
类型方法的方法体(body)中,self 指向这个类型本身,而不是类型的某个实例。这意味着你可以用 self 来消除类型属性和类型方法参数之间的歧义(类似于我们在前面处理实例属性和实例方法参数时做的那样)
class Person {
static var age: Int = 18
static func getAge() -> Int {
age
}
}
var age = Person.getAge() //18
关键字 @discardableResult
当调用一个有返回值的函数时,如果调用时不接受该返回值,则会出现 Result of call to ‘xx方法’ is unused
的警告⚠️,如果确实不想接收使用该返回值且又想消除该警告,则可以使用关键字 @discardableResult
。
使用 @discardableResult 消除警告:
class Person {
static var age: Int = 18
@discardableResult
static func getAge() -> Int {
age
}
}
Person.getAge()
网友评论