0

I want to make some operations when boolean values of property goes true to false and false to true.
I've set the getter setter for that, so I can do those operations on setter of boolean property.

But always crashes with EXC_BAD_ACCESS code = 2, can anyone help me to understand this what's wrong I'm doing here.

var reportActivityStarted:Bool {
        set {
            if self.reportActivityStarted {
                //Operations when boolean is true
            }else{
                //Operations when boolean is false
            }
        }
        get{
            return self.reportActivityStarted
        }
    }  

When I changes it's boolean value, it crashes at get{

self.reportActivityStarted = true
Kiran Jasvanee
  • 6,362
  • 1
  • 36
  • 52
  • 1
    Inside set, you should refer the value using the 'newValue' and should not access self.reportActivityStarted. – Shripada Feb 11 '16 at 09:06
  • @Martin R - can I know where you found this question in stackoverflow. as I searched for it, but didn't found relevant. – Kiran Jasvanee Feb 11 '16 at 09:42
  • Type `[swift] EXC_BAD_ACCESS get set` into the search field, it is among the result list. – Martin R Feb 11 '16 at 09:45
  • @Martin R - the link you have given it's recursive. I'm not changing the boolean value on setter. check the link you have provided and let me know how you think it's dublicate – Kiran Jasvanee Feb 11 '16 at 09:46
  • Your setter calls the getter method, and the getter calls itself recursively. It is the same issue. – Martin R Feb 11 '16 at 09:47
  • I clearly mention that I'm getting **[swift] EXC_BAD_ACCESS** on **get{** – Kiran Jasvanee Feb 11 '16 at 09:47
  • @Martin R - Look at that question's answer, it's calling the setter from within the setter. – Kiran Jasvanee Feb 11 '16 at 09:49
  • @Martin R - I'm not anyway setting the boolean in my setter. is it looks like that in my question.? – Kiran Jasvanee Feb 11 '16 at 09:50
  • In your setter method you call `if self.reportActivityStarted`. That calls the getter method!! And the getter method calls itself recursively. It is really the same issue: `get` or `set` in a computed property must not call itself. The solution is to use property observers, as in the referenced Q&A. – Martin R Feb 11 '16 at 09:52
  • And btw, just look at the stack backtrace when the exception occurs: You should *see* the recursion. – Martin R Feb 11 '16 at 09:55
  • @Martin R - Okay. I thought my case is different, I understand now. I already checked that question's answer and it was mention that he called the setter from within the setter, so misunderstood the case and thought might be different. Thanks :). – Kiran Jasvanee Feb 11 '16 at 10:04

2 Answers2

3

As already noted by @Unheilig you are generating an infinite recursive call. Infact the getter of reportActivityStarted is recursively invoking itself.

If you want to run some logic when a property is set or retrieved then you should use a property observer like this:

var reportActivityStarted: Bool {
    willSet(newValue) {
        switch reportActivityStarted {
        case true: print("reportActivityStarted is true before assignment") // <- your logic goes here
        case false: print("reportActivityStarted is false before assignment") // <- your logic goes here
        }
    }
}
Luca Angeletti
  • 58,465
  • 13
  • 121
  • 148
  • 1
    @Unheilig: No, I think you should undelete your answer. It did explain how to create a private variable for this scenario. It's a different approach and it would be nice having it explained here. – Luca Angeletti Feb 11 '16 at 10:26
0

if you want to use get, set you may need to have another variable to save the value on it in set and request it in get. like this:

var _reportActivityStarted = false 
var reportActivityStarted:Bool {
        set {
             _reportActivityStarted = newValue
            if _reportActivityStarted {
                //Operations when boolean is true
            }else{
                //Operations when boolean is false
            }
        }
    get{
        return _reportActivityStarted
    }
}  

But from what I see in you code sample you don't need set and get at all. you just need to use didSet instead. like this

var reportActivityStarted:Bool {
            didSet {
            if reportActivityStarted {
                //Operations when boolean is true
            }else{
                //Operations when boolean is false
            }
        }
}
Ismail
  • 2,778
  • 2
  • 24
  • 39