2

I am getting an error message when I try to access the private array (arr) inside the class (MyArray). What I am trying to achieve is to create a closure for reversing the array contents and this closure can be called from outside the class using instance variables. I am not able to understand this error. Can someone please help !!

public class MyArray {
private var arr: [Int] = []
internal static var instance: MyArray?

public var reverse = { () -> [Int] in
        var returnArray : [Int] = []
        var counter = arr.count - 1 // Error: Instance member 'arr' cannot be used on type 'MyArray'

        for _ in (0...arr.count - 1) { // Error: Instance member 'arr' cannot be used on type 'MyArray'
            returnArray.append(arr[counter])
            counter -= 1
        }
        return returnArray
}

private init() {}

public static func getInstance() -> MyArray {
    if self.instance == nil {
        self.instance = MyArray()
    }
    return self.instance!
}
}
vermau
  • 75
  • 1
  • 8

1 Answers1

2

Use a lazy property to be able to access a variable that was declared outside the closure.

sooo...

• change this public var reverse = to this public lazy var reverse =

• then add self. in front of every variable that's defined outside a closure.

Please read this: understand the lazy property

Lazy rules:

You can’t use lazy with let .

You can’t use it with computed properties .

Because, a computed property returns the value every time we try to access it after executing the code inside the computation block.

You can use lazy only with members of struct and class .

Lazy variables are not initialised atomically and so is not thread safe.

PhillipJacobs
  • 2,337
  • 1
  • 16
  • 32
  • Thank you Phillip, your solution worked like charm. I am not aware of lazy properties because I am still learning swift. Now the other problem I am facing is that when I return the reversed array back to the main playground file, I receive it in a variable and print that variable hoping the whole array should print. I call it like this from the main playground file ( var a = arr1.reverse ) where “arr1” is the instance of “myArray” class and “reverse” is a property with a closure inside that class ( as described in the above code ) and the output I am getting on the console is “print(function)” – vermau May 13 '18 at 21:19
  • 1
    user3318752. I'm glad it worked. **Closures are self-contained blocks of functionality that can be passed around and used in your code.** So by having that code block (closure) bind to the "reverse" variable, the reverse variable kind of became a function rather than a variable... So if you just change *this :* `var a = arr1.reverse` *to this :* `var a = arr1.reverse()` you'll be good to go – PhillipJacobs May 14 '18 at 05:29
  • this is what helped me [understand closures](https://developer.apple.com/library/content/documentation/Swift/Conceptual/Swift_Programming_Language/Closures.html) – PhillipJacobs May 14 '18 at 05:33
  • Thank you sooooo much Phillip. This worked. I was stuck at this for last 4 days. Your simple explanation of the property-closure binding explained me the logic. – vermau May 14 '18 at 07:49
  • **for last 4 days** - that shows dedication!! and it's all my pleasure... Good luck with swift – PhillipJacobs May 14 '18 at 08:40