美文网首页
04-Swift函数(Functions)

04-Swift函数(Functions)

作者: 王梓懿_1fbc | 来源:发表于2018-10-20 17:34 被阅读15次

函数是用来完成特定任务的独立的代码块。可以给函数起一个名字,用于标识一个函数,当函数需要执行的时候,这个名字就会用于"调用"函数。
 在swift中,每个函数都有一种类型,包括函数的参数值类型和返回值类型。你可以把函数类型当做和其他普通变量类型一样处理,这就可以更简单的把函数当做其他的函数的参数,也可以从其他函数中返回函数。

一、函数定义与调用

  • 函数的定义与调用。func是函数的关键字,参数是在函数名后的括号中,指定函数返回值类型时,用返回箭头->后面跟着返回类型的方法是来表示。
/** 
func前缀即表示为函数
函数名: sayHello
参数名: persionName,类型是String 
返回值: 返回值是String类型的
*/
func sayHello(personName:String) -> String {
    let getString = "hello," + personName;
    return getString;
}
// 函数的调用
let str = sayHello("EndEvent");
print(str);
输出结果: hello,EndEvent

二、函数参数与返回值

  • 无参函数,即函数可以是没有参数的:
func speak() -> String{
    // 返回字符串
    return "hello Swift!";   
}
// 函数调用
print(speak());
输出结果: hello Swift!
  • 多参函数,多个参数以,逗号分隔:
// 参数1: name;   参数2: age;
func sayHi(name:String, age:Int) -> String {
    return "hi,我叫\(name),今年\(age)岁.";
}
print(sayHi("EndEvent", age: 20));
输出结果: hi,我叫EndEvent,今年20岁.
  • 无返回值函数,即没有返回值:
func sayBye(name:String) {
    print("Bye \(name)!");
}
sayBye("EndEvent");
// 输出结果: Bye EndEvent!
(备注: 虽然没有返回值定义,但实际`sayBye(_:)`函数依然是返回了值。这是一个特殊的返回值,叫`void`。其实返回是一个空的元组`tuple`,没有任何元素可以写成`()`)
  • 多重返回值函数,可以用元组(tuple)类型让多个值作为一个复合值返回:
// 该函数中带3个参数,返回值是一个元组
func getMaxAndMinValue(a:Int, b:Int, c:Int) -> (max:Int, min:Int){
    // 计算最大值的方法(系统自带)
    let maxValue = max(a, b, c);
    // 计算最小值的方法(系统自带)
    let minValue = min(a, b, c);
    
    return (maxValue,minValue);
}
let temp = getMaxAndMinValue(10, b: 3, c: 11);
// 因为元组成员值已命名,即可用点语法
print("maxValue:\(temp.max)");
print("minValue:\(temp.min)");
输出结果: 
maxValue:11
minValue:3
  • 可选元组返回类型。如果函数返回的元组类型,可能整个元组都是"空的",那么久可以使用* 可选的(Optional) *元组进行返回,这就表示整个元组是nil。例如(Int, Int)?、(String, String)?。
func getMaxAndMinValue(array: [Int]) -> (max: Int, min: Int)? {
    if array.isEmpty {  // 表示数组为空
        return nil     
    }
    
    var currentMin = array[0]
    var currentMax = array[0]
    // 遍历数组
    for value in array[1..<array.count] {
        if value < currentMin {
            currentMin = value
        } else if value > currentMax {
            currentMax = value
        }
    }
    return (currentMax, currentMin)
}
// 函数调用,不为空才打印输出
if let temp = getMaxAndMinValue([10,3,13,100,-50]) {
    print("maxValue:\(temp.max)");
    print("minValue:\(temp.min)");
}
输出结果:
maxValue:100
minValue:-50

注意: 可选元组类型如(Int, Int)?和 元组中包含可选类型如(Int?, Int?)是不一样的。可选的元组类型,整个元组是可选的,而不是元组中的每个元组值。

三、函数参数名称

函数参数都有一个* 外部参数名 和 一个 局部参数名 *。外部参数名用于在函数调用时标注传递给函数的参数,内部参数名在函数的内部使用。
 一般情况下,第一个参数省略其外部参数名,第二个以及随后的参数使用其局部参数名作为外部参数名。所有局部参数名必须是独一无二的。尽管多个参数可以有相同的外部参数名,但不同的外部参数名可以提高代码的可读性。

  • 指定外部参数名
// firstName: 第一个参数的外部参数名
// name: 第一个参数的内部参数
func sayHello (firstName name:String) {
    print("hello \(name)");
    // 错误的,因为外部参数只用于标注传递
    // print("hello \(firstName)"); 
}
// 有提供外部参数名,在调用时,必须使用外部参数名!!!
sayHello(firstName: "EndEvent");
输出结果: hello EndEvent
// 外部参数名和内部参数名可以是一样的
func sayHello (name name:String) {
    print("hello \(name)");
}
sayHello(name: "EndEvent");
输出结果: hello EndEvent
// 所有外部参数名都可以是一样的,即都为name
// 内部参数名是要在函数内使用,所以必须是不同
func sayHello (name name1:String, name name2:String) {
    print("hello \(name1)");
    print("hello \(name2)");
}
sayHello(name: "EndEvent", name: "Swift");
输出结果:

hello EndEvent
hello Swift
  • 忽略外部参数,如果不想为第二个以及后续的参数设置外部参数名,可以用_来代替一个明确的参数名:
// 第一个参数默认忽略其外部参数名称,显式写下划线是多余的
func sayHello (name1:String, _ name2:String) {
    print("hello \(name1)");
    print("hello \(name2)");
}
sayHello("EndEvent", "Swift");
输出结果: 
hello EndEvent
hello Swift
  • 默认参数值,即可以给函数体中每个参数定义默认值。如果有默认值,在调用的时候可以忽略此参数:
// 参数style是有默认值的
func goHome (name: String, style: String = "走路") {
    print("\(name)是\(style)回家的");
}
goHome("EndEvent");  // 可以忽略style参数
goHome("Swift",style: "飞");
goHome("liming", style: "开车");
输出结果:
EndEvent是走路回家的
Swift是飞回家的
liming是开车回家的

注意: 将带有默认值的参数放在函数参数列表的最后,这可以保证在函数调用时,非默认参数的顺序的一致性,同时在相同函数在不同情况下调用时显得更为清晰。

_ 可变参数,可变参数表示可以不接收或接收多个值。通过在变量类型们后加入...的方法来定义可变参数:

// 计算平均值方式,参数是可变的
func arithmeticMean(numbers:Int...) -> Float {
    var total:Float = 0;
    var sum = 0;
    for number in numbers {
        sum += number;
    }
    total = Float(sum) / Float(numbers.count);
    
    return total;
}
let total = arithmeticMean(1,2,3,4,5,6,7,8,9);
print(total);
输出结果: 5.0

注意: 一个函数中最多只能有一个可变参数。

  • 常量参数和变量参数。函数参数默认是常量,试图在函数体重修改参数值这会导致编译出错。但有时候如果想修改参数值,那么久可以将参数定义为变量参数:
func myAppend(var str:String) -> String {
    str.appendContentsOf(" --- haha");
    return str;
}
print(myAppend("EndEvent"));
输出结果: EndEvent --- haha

注意: 对于变量参数,在函数调用结束后便会消失,即是变量参数仅仅存在于函数调用的生命周期中。

  • 输入输出参数。如果想要在一个函数可以修改参数的值,并且在函数调用结束后仍然存在,即可以把这个参数定义为* 输入输出参数(In-Out Parameters) *
// 值的交换
func swapTwoInts(inout a:Int, inout b: Int) {
    let tempValue = a;
    a = b;
    b = tempValue;
}
// 定义两个变量,并初始化
var a = 10;
var b = 30;
// 调用函数交换两个变量的值
swapTwoInts(&a, b: &b);
print("a = \(a)");
print("b = \(b)");
输出结果: a = 30    b = 10

注意:输入输出参数和返回值不一样,其实这就是将变量的地址传过去,在函数体中通过变量的地址进行修改值。

四、函数类型

每个函数都有特定的函数类型,由函数的参数类型和返回值类型组成。

  • 使用函数类型。在swift中,使用函数类型就像使用其他类型一样:
// 相加函数
func sumFunc(a:Int, b:Int) -> Int {
    return a + b;
}
// 相乘函数
func mathFunc(a:Int, b:Int) -> Int {
    return a * b;
}
// 定义变量str,类型为(Int,Int) -> Int
var str:(Int,Int) -> Int = sumFunc;      
// 调用相加函数
print("10 + 20 = \(str(10, 20))");
// 给str这个变量赋值一个函数
str = mathFunc;
// 调用相乘函数
print("10 * 20 = \(str(10, 20))");
输出结果: 10 + 20 = 30    10 * 20 = 200
  • 函数类型作为参数类型。即你可以将(Int, Int) -> Int这样的函数类型作为另外一个函数的参数类型:
// 相乘函数
func mathFunc(a:Int, b:Int) -> Int {
    return a * b;
}
// 输出函数
func printMathFuncResult(mathFunc:(Int, Int) -> Int, a:Int, b:Int){
    print("\(a) * \(b) = \(mathFunc(a,b))");
}
// 调用输出函数
printMathFuncResult(mathFunc, a: 10, b: 10);
输出结果: 10 * 10 = 100

注意: 可能认为这和函数调用效果是一样,现在这是否多此一举?其实不是,printMathFuncResult (:::)函数作用是输出另外一个适当类型的数学函数的调用结果。即在这里只关心传入的函数类型是否正确,而不在意函数如何实现。printMathFuncResult (:::)就是以一种安全类型(type-safe)的方式,将部分功能转给调用者实现,也即是方便代码的封装。

  • 函数类型作为返回类型。可以将函数类型作为另外一个函数的返回类型:
// 实现功能: 将currentInput值变为0的过程
var currentInput = -5;
// 加操作
func stepForward(input:Int) -> Int {
    return input + 1;
}
// 减操作
func stepBackward(input:Int) -> Int {
    return input - 1;
}
// 函数选择,参数为input,返回值为'(Int) -> Int'类型
func chooseStepFunction(isBackward:Bool) -> (Int) -> Int {
    // YES:即表示currentInput值是大于0的,选择stepBackward减操作
    // NO: 即表示currentInput值是小于0的,即选择stepForward加操作
    return isBackward ? stepBackward : stepForward;
}
// 循环操作,直到currentInput为0
while currentInput != 0 {
    print("currentInput: \(currentInput)");
    // 根据currentInput值,选择对应操作的函数
    var moveNearerToZero = chooseStepFunction(currentInput > 0);
    // 调用操作
    currentInput = moveNearerToZero(currentInput);
}
print("结束操作:\(currentInput)");
输出结果:
currentInput: -5
currentInput: -4
currentInput: -3
currentInput: -2
currentInput: -1
结束操作:0

五、嵌套函数

  • 在本节文章中你说见到函数都是* 全局函数(global functions) ,它们都是属于全局域的。但你也可以将函数定义在函数体中,而这种称之为 嵌套函数(nested functions) 。
  • 嵌套函数 ,在默认情况下对外界是不可见的,但却可以被它们的 外围函数(enclosing function) *调用。并且外围函数也可以返回其所嵌套的函数,使得这个函数也可以在其他域中被调用。
// 实现功能: 输入一个值,将值变为0的过程
var currentInput = -5;
// 函数选择 - 全局函数
func chooseStepFunction(isBackwark:Bool) -> (Int) -> Int {
    // 加操作 - 嵌套函数
    func stepForward(input:Int) -> Int {
        return input + 1;
    }
    // 减操作 - 嵌套函数
    func stepBackward(input:Int) -> Int {
        return input - 1;
    }
    
    return isBackwark ? stepBackward : stepForward;
}
// 即是接受'(Int) -> Int' 类型的函数
let moveNearerToZero = chooseStepFunction(currentInput > 0);
// 循环操作,直到currentInput为0
while currentInput != 0 {
    print("currentInput: \(currentInput)");
    currentInput = moveNearerToZero(currentInput);
}
print("结束操作:\(currentInput)");
输出结果:
currentInput: -5
currentInput: -4
currentInput: -3
currentInput: -2
currentInput: -1
结束操作:0

注:xcode7.3环境
作者:西门奄
链接:https://www.jianshu.com/u/77035eb804c3
來源:简书
简书著作权归作者所有,任何形式的转载都请联系作者获得授权并注明出处。

相关文章

  • 04-Swift函数(Functions)

    函数是用来完成特定任务的独立的代码块。可以给函数起一个名字,用于标识一个函数,当函数需要执行的时候,这个名字就会用...

  • Functions - 函数

    来源于 Ry’s Objective-C Tutorial - RyPress 一个学习Objective-C基础...

  • 函数(Functions)

    函数的概念: 函数也叫做方法,是有名字的闭包。 函数的参数: 无参数 func sayHello(personNa...

  • Functions (函数)

    Functionsare self-contained chunks of code that perform a...

  • 虚函数

    虚函数 Inheritance (继承) with virtual functions (虚函数) 非虚函数:继承...

  • solidity-8.函数

    函数(Functions) 函数的声明方式如下:function ( ) {internal|external} ...

  • Kotlin 函数编程详解

    函数 函数声明 Functions in Kotlin are declared using the fun ke...

  • 一、函数、值域和垂线检验

    1.函数(Functions) A function is a rule for transforming an ...

  • 6.函数 Functions

    定义和调用函数 没有参数的函数 Functions With Multiple Parameters 多参函数 无...

  • 笨办法学C 练习18:函数指针

    练习18:函数指针 原文:Exercise 18: Pointers To Functions 译者:飞龙 函数在...

网友评论

      本文标题:04-Swift函数(Functions)

      本文链接:https://www.haomeiwen.com/subject/vpumzftx.html