[SOLVED] `abs(_:)` returns negative numbers in Int extension

Pretty sure this is a bug:

extension Int {
  func f() -> Int {
    return abs(self)
  }
}

print(abs(-1))  //  1
print(-1.f())   // -1

SwiftFiddle link:

But I'm curious about what's happening here.

The extension function returns -1 even if I use a negative literal abs(-1) instead of abs(self).

It seems that print(-1.f()) is being parsed as print(-(1.f())), not print((-1).f()).

Personally, I’d expect it to parse as print((-1).f()) as well, especially given that -0x80 as Int8 is allowed but 0x80 as Int8 is not allowed. Perhaps there should be a warning about this behavior?

3 Likes

Oh, I was so focused on the abs(-1) part :sweat_smile: thanks for clearing that up! So it's not a bug after all! :sweat_smile:

I agree that the minus sign should have higher precedence as part of a literal, but perhaps that would be counterintuitive with variables and function calls.

2 Likes

Yep, that's a feature. Exaggerating:

print(-1   .   f())

-1
  .f()
2 Likes

I think there is definitely a bug in the syntax highlighter here.

If you write print(-1.f()) in Swift Playgrounds for iPad, then you’ll see that -1 is highlighted as a numeric literal, despite the fact that the - is not part of the numeric literal. The - should instead be highlighted as a function.

image

This even happens if you use parentheses in the expression, resulting in one parenthesis having a different color than the rest:

image

I haven’t tested this on my Mac yet, but it seems likely that Xcode has this bug too. Visual Studio Code’s syntax highlighter also has this bug when parentheses aren’t used, but behaves correctly when parentheses are used.

1 Like

Well spotted!

I can confirm that Swift Playgrounds on Mac has this bug.

VS Code has it when bracket pair colorization is not enabled*, or when directly preceding the digits.

* only with certain themes: Light+ (default light) has the bug, Noctis Lux doesn't.

colorized-pairs-2

Xcode does not have it.

1 Like

Well...it's complicated:

(From part 1 of my series of articles on numerics in Swift.)

3 Likes

- wouldn’t be part of the numeric literal in this context though, right?

Correct—not in terms of how it behaves from the user perspective.

1 Like

In the hindsight was it the right decision to make the precedence of prefix - lower than ".", given that there could be no space between - and 42?

    -42
       .trailingZeroBitCount

here I'm using the popular way to format chained code:

foo
   .bar()
   .baz
   .qux
2 Likes