Szymon Lipiński
Szymon Lipiński

Reputation: 28574

Kotlin is ignoring expression

I'm wondering why the below code generates the strange results, and compiler doesn't show any error or warning. This looks like an extremely efficient source of bugs.

    val a = 10 * 20 +
            10 * 30

    val b = 10 * 20
          + 10 * 30

    val c = (
               (10 * 20)
             + (10 * 30)
            )

    val d = (10 * 20)
          + (10 * 30)

    println(a)
    println(b)
    println(c)
    println(d)

And the output is:

500
200
500
200

Upvotes: 3

Views: 2141

Answers (2)

Szymon Lipiński
Szymon Lipiński

Reputation: 28574

I looks like I was lucky to use an operator which also has unary version +. The problem is that Kotlin allows for a kind of expressions which do nothing in fact like this:

12345

I can also have:

- 12345

which is just a negative number. I can also have positive number:

+ 12345

So in this case:

val a = 20 +
        30

I have one expression, as the + requires another argument, which can be found in the next line.

However here I have two expressions

val a = 20
       + 30

The variable a will have value 20 and the second expression will do nothing.

However there is no unary version of *, so this works:

val a = 10 * 
        20 

and a == 200, and this makes a compilation error:

val a = 10
        * 20 

Error:(397, 17) Kotlin: Expecting an element

Adding semicolons doesn't change anything, as the last expression is still not valid, and causes the compilation error.

And you can always use brackets:

val x = (10
         + 20)

Upvotes: 2

s1m0nw1
s1m0nw1

Reputation: 81859

Kotlin has optional semicolons, it allows and encourages source code to omit a statement separator (i.e. semicolon ;). As a result, it can get hard for the compiler to guess what you, as a programmer, actually intend to do:

val b = 10 * 20
       + 10 * 30

Will be compiled to an assignment of b = 500 and a second statement that results in 300 but never gets assigned to anything (same with d). How would you consider the compiler to know that the second line is actually part of the first expression? It's valid on its own.

This thread gives further details.

Upvotes: 2

Related Questions