I feel a bit lost using swift inout parameter in the following code:
var shouldContinue: Bool = true
func doSomeWork1(shouldContinue: inout Bool)
{
while shouldContinue
{
// ERROR: the compiler wants: doSomeWork2(shouldContinue: &shouldContinue)
doSomeWork2(shouldContinue: shouldContinue)
}
}
func doSomeWork2(shouldContinue: inout Bool)
{
while shouldContinue
{
}
}
Why does the compiler want doSomeWork2(shouldContinue: &shouldContinue)
instead of the compiler wants: doSomeWork2(shouldContinue: shouldContinue)
? isn't shouldContinue
already a pointer in the scope of doSomeWork1() ???
You write an in-out parameter by placing the inout keyword right before a parameter's type. An in-out parameter has a value that's passed in to the function, is modified by the function, and is passed back out of the function to replace the original value.
All parameters passed into a Swift function are constants, so you can't change them. If you want, you can pass in one or more parameters as inout , which means they can be changed inside your function, and those changes reflect in the original value outside the function.
An InOut variable in a function header is for a variable that may be written as well as read within the function, but may also be written, as well as read outside the function.
We can define the parameters as in-out parameters. To define a parameter as in-out, swift provides an inout keyword before the parameter's type. The in-out parameter has the value changed inside the function and returned to replace the original value.
Being a pointer is only side-effect of optimization process for inout parameters. They actually work in different manner using copy-in copy-out behavior. So inside function that parameter is treated just like regular variable, not pointer. If you pass it to another function that takes inout parameter you have to mark it as such.
In-out parameters are passed as follows:
When the function is called, the value of the argument is copied.
In the body of the function, the copy is modified.
When the function returns, the copy’s value is assigned to the original argument.
This behavior is known as copy-in copy-out or call by value result. For example, when a computed property or a property with observers is passed as an in-out parameter, its getter is called as part of the function call and its setter is called as part of the function return.
As an optimization, when the argument is a value stored at a physical address in memory, the same memory location is used both inside and outside the function body. The optimized behavior is known as call by reference; it satisfies all of the requirements of the copy-in copy-out model while removing the overhead of copying. Write your code using the model given by copy-in copy-out, without depending on the call-by-reference optimization, so that it behaves correctly with or without the optimization.
In-Out Parameters
From: Matt Neuburg Book “iOS 13 Programming Fundamentals with Swift.” :
If we want a function to alter the original value of an argument passed to it, we must do the following:
Our removeCharacter(_:from:) now looks like this:
func removeCharacter(_ c:Character, from s: inout String) -> Int {
var howMany = 0
while let ix = s.firstIndex(of:c) {
s.remove(at:ix)
howMany += 1
}
return howMany
}
And our call to removeCharacter(_:from:) now looks like this: var s = "hello" let result = removeCharacter("l", from:&s) After the call, result is 2 and s is "heo". Notice the ampersand before the name s when we pass it as the from: argument. It is required; if you omit it, the compiler will stop you. I like this requirement, because it forces us to acknowledge explicitly to the compiler, and to ourselves, that we’re about to do something potentially dangerous: we’re letting this function, as a side effect, modify a value outside of itself.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With