Why is Nil coalescing with Right Associative?

Should it be left associative?

I think it is let a = b ?? c ?? d

grouped as let a = (b ?? c) ?? d

not let a = b ?? (c ?? d)

But it is declared as right associativity. Am I not understanding something or is there something wrong?

+3


source to share


1 answer


I think this is an optimization. Joining left or right does not change the result.

It:

(b ?? c) ?? d

      

evaluates b ?? c

and its result is used as the left side x ?? d

. Therefore, even if b

it is not null, the coalescing operator is executed 2 times.

In this case, instead of

b ?? (c ?? d)

      

if b

not nil, the expression on the right is not evaluated, so it is not executed


Adding



To prove this, I did a simple test: I (re) defined the nil merge operator:

infix operator !!! {
    associativity left
    precedence 110
}

func !!!<T>(optional: T?, defaultValue: @autoclosure () -> T?) -> T? {
    if let value = optional {
        println(optional)
        return value
    }

    let def = defaultValue()
    println(def)
    return def
}

      

With this test data:

let a: String? = "a"
let b: String? = "b"
let c: String? = "c"

let d = a !!! b !!! c

      

Using associativity left

, this is what is printed on the console:

Optional("a")
Optional("a")

      

changing associativity to right

, output:

Optional("a")

      

This means that when using right associativity, the right side of the operator is ignored unless the left side is nil.

+5


source







All Articles