Hi, I think that's an awful idea. I can already tell you that this will never be accepted. It just complicates the design and the semantics of the `defer` statement, and I don't see any advantage. Sorry.
-Michael > Am 06.06.2016 um 22:14 schrieb donny wals via swift-evolution > <[email protected]>: > > Michael, > > How would this proposal break your snippet? > >> func g(x: Int) { >> defer { print("A"); } >> let b: Int >> if x == 3 { >> return >> } else { >> b = x >> } >> defer { print("b is \(b)") } >> } > > In this case if x==3 the function should return without executing the final > defer. The reason I think it should work like that is that the if statement > creates a scope of it’s own. You’re using a return inside of that scope, so > only if you’re adding a defer inside of that scope it should be executed even > if it’s after the return. The important part here is that the return and the > defer should be in the same scope for this proposal to apply. > >> On 06 Jun 2016, at 22:07, Michael Peternell <[email protected]> wrote: >> >> Hi, >> >> you may think of `defer` as a function that pushes a block onto an implicit >> cleanup stack that is part of every lexical closure. On each scope exit, all >> blocks from its cleanup stack are popped and executed. >> >> E.g.: >> >> func f(x: Int) { >> defer { print("A"); } >> defer { print("B"); } >> if x == 3 { >> return >> } >> defer { print("C"); } >> } >> >> So, f(2) will print "CBA", but f(3) will print "BA" instead. Furthermore, >> this will change semantics and break the following code: >> >> func g(x: Int) { >> defer { print("A"); } >> let b: Int >> if x == 3 { >> return >> } else { >> b = x >> } >> defer { print("b is \(b)") } >> } >> >> In the code above, b is only defined if x is not 3. If x is 3, the last >> `defer` block cannot be called, and that code would no longer compile. >> >> So I think the current language behavior is more powerful. `defer` is >> usually used to do cleanup work, and it is called near the place where some >> resource is initialized. Putting a `defer` block to the end of a function >> kinda defeats its purpose. And simple functions like fibonacci I would just >> write without using `defer` at all - it's just confusing to use `defer` and >> `inout` in this case IMO. >> >> /// Calculates the n'th fibonacci number. (n >= 1) >> func fibonacci(n: Int) -> Int { >> var a = 0 >> var b = 1 >> for _ in 1...n { >> (a,b)=(b, a+b) >> } >> return a >> } >> >> Regards, >> Michael >> >> >>> Am 06.06.2016 um 21:50 schrieb donny wals via swift-evolution >>> <[email protected]>: >>> >>> Hi, >>> >>> When we’re using defer we write some code that we want to execute the >>> moment a scope exits. >>> This leads to code that could read like: >>> >>> let fibonacci = sequence(state: (0, 1)) { (pair: inout (Int, Int)) -> Int in >>> defer { pair = (pair.1, pair.0 + pair.1) } >>> return pair.0 >>> } >>> >>> What I find strange about this is that we have to write the code that we >>> want to execute after the return before the return. >>> >>> I’d like to propose a change to defer that would allow the above code to be >>> written as: >>> >>> let fibonacci = sequence(state: (0, 1)) { (pair: inout (Int, Int)) -> Int in >>> return pair.0 >>> defer { pair = (pair.1, pair.0 + pair.1) } >>> } >>> >>> This would make the intent of the code more clear (return first, then >>> mutate state). Not all cases can benefit from this change, but anytime you >>> exit a scope using a return I think it might be more clear to define the >>> defer after the return. The code would more closely mirror the intent of >>> the code. >>> >>> A rule of thumb I’ve come up with for this is that whenever you’re using >>> return to exit a scope, any defer in that same scope should be executed >>> regardless of it’s position in that same scope. This proposal would >>> supplement the way defer currently works. >>> >>> What do you all think? >>> _______________________________________________ >>> swift-evolution mailing list >>> [email protected] >>> https://lists.swift.org/mailman/listinfo/swift-evolution >> > > _______________________________________________ > swift-evolution mailing list > [email protected] > https://lists.swift.org/mailman/listinfo/swift-evolution _______________________________________________ swift-evolution mailing list [email protected] https://lists.swift.org/mailman/listinfo/swift-evolution
