Today’s article is relatively basic, which is the most important thing at any time. Speaking of functions, as long as you have written a program, you must know what a function is. Today we will discuss the features of functions in Swift and closures in Swift. I’m going to do a little example today where I’m going to use analogies to write functions in Objective-C and so forth. Functions in Swift have many useful features, such as input parameters, using tuples to return multiple values, defining parameter names, setting default parameters and mutable parameters, etc. Closures in Swift are objective-C blocks, which are used the same way except syntactically. So, without further ado, let’s start with functions in Swift, and then closures in Swift.

A function in Swift

1. Definition and use of functions

Before introducing functions in Swift, I want to use a simple addition function in Objective-C as a starting point, and then use the analogy of a function that implements the same function in Swift. The following code snippet is a function in Objc that takes the sum of two integers and returns the sum of them.

- (NSInteger)sumNumber1:(NSInteger) number1
                number2:(NSInteger) number2 {
    return number1 + number2;
}
Copy the code

The function simply passes in two integers and returns their sum. Next will use Swift language implementation, or through this example to familiarize yourself with the syntax of defining functions in Swift language. Below is the Swift function for finding the sum of two integers. The syntax is simpler. To define a function in Swift, we will use the keyword func to declare the function.

Func sum (number1:Int, number2:Int) -> Int{return number1 + number2; }Copy the code

Func function name (parameter list) -> return value type {function body}, so you can define a function. Of course, there are many other uses for function definition, which are described below. The above function is called as follows:

let sumTwoNubmer = sum(2, number2: 3);
Copy the code

2. List of parameters in a function

Parameter lists in functions are worth mentioning, because parameter lists are one of the data sources of functions, so it is worth doing a good job of parameter lists. Parameter lists can also be used in many useful ways, so let’s look at function parameter lists in more detail.

(1) The default parameter is constant (let)

In a function parameter list, the default parameter is a constant. This is equivalent to modifying the parameter with the let keyword. We can experiment by changing the above addition function. Increment number1 in the addition function by one, and you get an error that basically says “number1 cannot be modified because it is a let constant.” The compiler also provides a fix-it solution, which prefixes number1 with the var keyword to make it a variable so you can change its value.

A parameter is a constant by default. If you want it to be a variable, you can use the var keyword to modify a variable in the function. Below is the error reported and the compiler’s solution. (In Objc you can change parameter values in functions by default)

(2) Name the parameter

For code readability and maintainability, we need to give each parameter a name when defining a function, so that the caller can easily know what the parameter means. Next, make the changes in the above addition function, giving each parameter name a name, and see how it is called. Modify the above function by naming the first parameter numberOne, the second parameter numberTwo, and the modified function below. Then the sum() function is called with the names of its arguments, so that the caller can see them at a glance.

Func sum (numberOne number1:Int, numberTwo number2:Int) -> Int{return number1 + number2; } let sumTwoNubmer = sum(numberOne: 10, numberTwo: 20);Copy the code

When calling the above function, the following is the prompt given by the compiler, which can be seen at a glance.

In Swift1.0, you could add a # to the parameter name, and the parameter name would be the same as the name of a variable (or constant). In Swift2.0, this was removed, because the default is to add a # to Swift1.0.

(3) function transmission participation in the transmission of reference

For the moment, in C functions, you can pass in parameters to the function, or the memory address of the argument is called reference. If you pass in a reference and modify the value in the function, the modified value can be retained after the function exits. This is also possible in Swift, but you need to modify the parameter with the inout keyword and, when using the function, with &. Just like in C, ampersand takes the address character. Below is a small example of inout’s use.

func incrementStepTwo (inout myNumber:Int) {
    myNumber += 2
}
var myTestNumber = 6
incrementStepTow(&myTestNumber)  //myTestNumber = 8
Copy the code

The myTestNumber variable is incremented by 2 by the incrementStepTwo() function. If myTestNumber is a constant, the IDE will give you an error. The reason for the error is obviously that you moved a value that shouldn’t have been moved, that constant can’t be changed again.

(4) Indefinite parameter function

The number of parameters in an indeterminate function is indeterminate, but the types of parameters must be the same. How do I take an amorphous parameter when I use it? An indefinite number of parameters is actually an array. We can iterate through each parameter through a for loop and then use it. The incrementMultableAdd() function below takes an indeterminable number of parameters and sums integers. In a function we just iterate over each argument, add each argument, and return the sum. The function is relatively simple, but I won’t bother here.

(5) Default parameter values

Assigning initial values to parameters is supported in Swift, as it is in some other programming languages. But a seemingly ancient language like Objective-C does not support specifying initial values for parameters, as it does in the modern programming language Swift. Default parameter Specifies a default value for the parameter starting after the parameter list, otherwise an error will be reported. Below is an example of specifying default parameters for function parameters. YouName: sayLove(); loverName: sayLove(); youName: sayLove(); Then there are three different ways to call the sayLove function. You can call the function with no arguments, you can pass one argument, or you can pass two.

Since each parameter of a function has a name, it is possible to pass a value to any parameter and take the default value to other parameters when calling a function with default parameters. This is also one of the features of Swift, as shown in the following simple code example:

3. Function types

Each function has its own type. In plain English, if two functions have the same argument list and return value type, they have the same function type. In Swift you can define a variable or constant to store the type of a function. I’ll use an example and show you what a function type is.

(1) First create two functions of the same type, one function returns the difference of two integers, and the other function returns the product of two integers. Of course, these two functions are relatively simple, directly on the code:

Func diff (number1:Int, number2:Int) -> Int {return number1 - number2; } func mul (number1:Int, number2:Int) -> Int { return number1 * number2; }Copy the code

(2) After the function is defined, we need to define an enumeration to enumerate the type of each function.

Enum CountType:Int {case DiffCount = 0 case MulCount}Copy the code

(3) The next step is to combine the things defined in (1) and (2) by a function. In plain English, you define a function that returns the function type of an enumerated value. Sometimes it’s easy to get confused when you talk too much, so just go straight to the code. The function below returns the corresponding function type based on the enumerated value passed in.

// Select the type of function, Func choiseCountType(countType: countType) -> ((Int, Int) -> Int) {var myFuncType (Int, Int) -> Int switch countType { case .DiffCount: myFuncType = diff case .MulCount: myFuncType = mul } return myFuncType; }Copy the code

Select * from choiseCountType(); select * from choiseCountType(); select * from choiseCountType(); select * from choiseCountType(); select * from choiseCountType(); The results of the implementation on Playground are as follows:

4. Function nesting

We can rewrite the code in 3 using function nesting, which is supported in Swift. So we can put the functions in 3.1 and 3.2 into 3.3, so we can rewrite the above code using function nesting. The code rewrite using nested functions is shown below. Of course, the choiseCountType() function is called in the same way as in 3.4.

// Select the type of function, Func choiseCountType(countType: countType) -> ((Int, Int) -> Int) { number2:Int) -> Int { return number1 - number2; } func mul (number1:Int, number2:Int) -> Int { return number1 * number2; Var myFuncType:(Int, Int) -> Int switch countType {case.diffCount: myFuncType = diff case.mulcount: myFuncType = mul } return myFuncType; }Copy the code

2. Closure

When it comes to closures in Swift, I have to say blocks in Objective-C, they’re the same thing, they’re used the same way, they’re used in the same way. Closure in Swift is a good analogy to Blocks in Objective-C. It’s an anonymous function. In this section, I’ll introduce you to the basic syntax of closures in Swift, and then peek into the Closure scenario using the analogy of blocks in ObjC.

1.Closure variable declaration

Closure is an anonymous function, and we can define a Closure variable whose type is the “function type” described above. Defining a closure variable is simply defining a variable of a particular function type as follows. Since the Closure variable does not have an initial value, we declare it as a variable of optional type. In use, use! Force open.

var myCloure0:((Int, Int) -> Int)?
Copy the code

In addition to the above approach, we use another common way of declaring closure variables. Using the keyword TypeAlias to define a specific function type, we can use this type to declare a Closure variable, as shown below

Typealias MyClosureType = (Int, Int) -> Int var myCloure:MyClosureType?Copy the code

2. Assign the Closure variable

To assign a Closure variable is to assign a function body to a variable of a function type, not much different from the definition of a function. But the function body that assigns a value to the closure variable contains the argument list, and the argument list is separated from the actual function body using the in keyword. Closure optional variables are called just like normal functions, except that this function is called! To force open to use. The assignment and invocation are as follows.

3. Application examples of closure callback

Let’s call it closure callbacks for now, but it’s actually Block callbacks in Objc. Closure callbacks in Swift are consistent with Block callbacks in Objc, and an example of one of the applications of closures will be shown below. And down here we’re going to create two view controllers, let’s call them FirstViewController and SecondViewController. On FirstViewController you have a Label and a Button that jumps to SecondViewController and a Label that displays the values that are called back from SecondViewController. And SecondViewController also has a TextField and a Button, Clicking Button will bring the value from the input field back to the FirstViewController via closure callback and then display it on the Label on the FirstViewController.

(1) The first step to build this instance is to use Stroyboard to lay out the controls we need and manage the corresponding classes.

Of course, the focus of this Demo is not on how to lay out controls, how to associate controls, and how to use controls, so I won’t go into that. The focus of this example is on how to use Closure to implement a callback to a value. Below is a screenshot of our control layout and directory structure, showing the functionality of the controls in our Storyboard. Click the “Go SecondViewController” button on “FirstViewController” to jump to “SecondViewController”. Enter the value in the input field on the SecondViewController view, click the Back button to return to FirstViewController, and pass Back the text in the input field as a closure callback to display on the Label of FristViewController. That’s about it.

(2) FirstViewController. The contents of the swift

FirstViewController. The contents of the swift is simpler, is associated with a Label control and click a button, click on the button will jump to SecondViewController, specific code is as follows, in this not wordy, please see the comments in the code. The important point in the code below is to implement the closure callback provided by SecondViewController when jumping to it in order to accept the value passed back.

/ / / / / / FirstViewController swift SwiftDemo / / / / Created by Mr. LuDashi on 15/11/18. / / Copyright © 2015 ZeluLi. All rights reserved. // import UIKit class FirstViewController: UIViewController { @IBOutlet var showTextLabel: UILabel! Override func viewDidLoad() {super.viewdidLoad ()} override func didReceiveMemoryWarning() {override func didReceiveMemoryWarning() { Super. DidReceiveMemoryWarning ()} / / click on the button to jump to SecondViewController @ IBAction func tapGoSecondViewControllerButton (sender: UIButton) {// Load SecondViewController from Storyboard let secondVC = UIStoryboard(name: "Main", bundle: NSBundle.mainBundle()).instantiateViewControllerWithIdentifier("SecondViewController")as! SecondViewController // Implement the callback, Receive the callback to the value of the secondVC. SetBackMyClosure {(inputText: String) - > Void in the self. ShowTextLabel. Text = inputText} / / push to SecondViewController self. NavigationController? .pushViewController(secondVC, animated: true) } }Copy the code

(3) SecondViewController. The contents of the swift

SecondViewController. The contents of the swift, nor the trouble, that is, in addition to the associated control and events, also defines a closure type (function type), then use the specific function type declarations for a corresponding to the function type variable. We can use this variable to accept the closure from the previous page and pass back the value entered by the user through the closure to the previous page. The specific code is as follows:

/ / / / / / SecondViewController swift SwiftDemo / / / / Created by Mr. LuDashi on 15/11/18. / / Copyright © 2015 ZeluLi. All // import UIKit TypeAlias InputClosureType = (String) -> Void // Define closure type (specific function type function type) class SecondViewController: UIViewController { @IBOutlet var inputTextField: UITextField! / / input box, let the user input values, and then through the closure callback to a page on var backClosure: InputClosureType? Override func viewDidLoad() {super.viewdidLoad ()} override func didReceiveMemoryWarning() {override func didReceiveMemoryWarning() { Super. DidReceiveMemoryWarning ()} / / closure variables Seter method func setBackMyClosure (tempClosure: InputClosureType) {self. BackClosure = tempClosure } @IBAction func tapBackButton(sender: UIButton) { if self.backClosure ! = nil { let tempString:String? = self.inputTextField.text if tempString ! = nil { self.backClosure! (tempString!) } } self.navigationController! .popViewControllerAnimated(true) } }Copy the code

(4) After the above steps this example is complete, it is time to see the effect.

Originally wanted to make Git dynamic map, feel the instance function is simple, and the UI is relatively simple, so I didn’t do it, or look at the screenshot. A screenshot of the results is as follows:

4. Common closure functions in arrays

Swift’s array comes with some useful closure functions, such as Map, Filter, and Reduce. Let’s take a closer look at these closures, which are a little more fun to use.

(1) Map

When it comes to the usage and function of Map, it must be said that if you have used ReactiveCocoa framework, you are familiar with the use of Map in Sequence. In fact, the use of both methods and functions are very similar. It doesn’t matter if you haven’t used a Map in RAC, so let’s take a look at the Map closure function in an array.

As you can see from the code snippet above, the map closure function iterates through each item in the array, processes each item in the array using the mapping rule, and returns the processed array (as a new array). Of course, the values of the elements in the original array remain the same, which is how the map closure functions are used.

(2) Filter

The usage of Filter is relatively easy to understand. The Filter is a sieve, which is used to Filter the data that meets the conditions. Sequence in ReactiveCocoa also has Filter, which is used to Filter the data in Sequence. The Filter in the array is used to Filter the data in the array and return the new array, which stores the data that meets the criteria. The example below is a height Filter. The height of the person < 173 is filtered and the height of the person > 173 is returned.

(3) Reduce

There is also the concept of Reduce in ReactiveCocoa, which uses Reduce to merge subtractive semaphores. Use the Reduce closure function in swift’s array to merge items and the merged Value. The example below is a Salary array, which holds the monthly Salary. We will use the Reduce closure function to calculate the total salary. Below is a screenshot of the DEMO:

Since the | address

Sharing:Swift Books learning materials