Black Hole challenge from codewars

Python 2, 120 119 90 bytes

def f(n,a,b):n-=1;A,B,C=min((a,b,1),(n-b,a,2),(n-a,n-b,3),(b,n-a,4));return(n-A)*4*A+4*B+C

Try it online!


Python 3, 87 bytes

def f(n,a,b):A,B=min((a,b+1/4),(n+~b,a+.5),(n+~a,n-b-1/4),(b,n-a));return(n+~A)*4*A+B*4

Try it online!

Returns a float

-3 bytes, thanks to Arnauld


Explanation:

This takes advantage of the fact that there is some symmetry to the matrix.

The matrix can be split into four quarters, which are equal when rotated (+ an offset of 1-3).

enter image description here

The first part A,B,C=... finds out which quarter the current coordinates are in, by finding the smallest coordinates, relative to each quarter:

enter image description here

(green: (a,b), yellow: (n-b,a), red: (n-a,n-b), blue: (b,n-a))

The coordinate pair is then converted to a value:

(0,0) = 1, (0,1) = 5, and so on; each coordinate is 4 larger than the previous.

sum((n-(i*2))*4for i in range(A)) skips the rows above, +(B-A)*4 moves along the row, and +C adds the offset.

sum((n-(i*2))*4for i in range(A))+(B-A)*4+C is shortened to (n-A)*4*A+4*B+C


05AB1E (legacy), 36 31 28 25 bytes

<αìRDÀsā)ø{н`Š4*ŠD¹<α4**O

Port of @TFeld's Python answer, so make sure to upvote him!
-3 bytes thanks to @Emigna.

Inputs are \$n\$ and \$[a,b]\$.

Uses the legacy version instead of the new 05AB1E version, because there seems to be a bug with the sorting ({) of multidimensional lists.

Try it online or verify all test cases.

Explanation:

<          # Decrease the (implicit) input `n` by 1
 α         # Take the absolute difference with the (implicit) input-list
           #  (we now have `[n-1-a, n-1-b]`)
  ì        # Prepend the input (we now have `[n-1-a, n-1-b, a, b]`)
   R       # Reverse the list (we now have `[b, a, n-1-b, n-1-a]`)
DÀ         # Duplicate this list, and rotate it once towards the left
    s      # Swap these two lists
ā          # Push a list in the range [1, length_list] without popping the list: [1,2,3,4]
     )     # Wrap all three lists into a list (we now have 
           #  `[[a, n-1-b, n-1-a, b], [b, a, n-1-b, n-1-a], [1, 2, 3, 4]]`)
      ø    # Zip/transpose; swapping rows/columns (we now have
           #  `[[a, b, 1], [n-1-b, a, 2], [n-1-a, n-1-b, 3], [b, n-1-a, 4]]`)
       {н  # Get the minimum by sorting the lists and getting the first inner list
           # (since the minimum builtins in 05AB1E flatten multidimensional lists
           #  and give a single integer)
`          # Push all three values to the stack: `A`, `B`, and `C`
Š          # Triple-swap once, so the order is now `C`, `A`, `B`
 4*        # Multiply `B` by 4
Š          # Triple-swap again to `B*4`, `C`, `A`
 D         # Duplicate `A`
  ¹<α      # Take the absolute difference with `n-1` (so basically `n-1-A`)
     4*    # Multiply that by 4
       *   # Multiply it with the duplicated `A`
O          # Sum all values on the stack (`B*4 + C + (n-1-A)*4*A`)
           # (and output the result implicitly)