medium

Number of Boomerangs

Count ordered triples of points where two of them sit the same distance from the third, by tallying squared distances per anchor point.

1. Define the problem

Number of Boomerangs

You are given points on a plane, each written as a pair [x, y]. A boomerang is an ordered group of three different points (i, j, k) where the distance from i to j equals the distance from i to k. Return how many boomerangs there are. The group is ordered , so (i, j, k) and (i, k, j) count as two different boomerangs. Pick each point in turn as the middle point i, then count how many of the other points sit at each distance using a hash map from distance to tally. If d points share a distance, they give d times (d - 1) ordered pairs, because you choose one for j and a different one for k.

Constraints

  • n == points.length, 1 ≤ n ≤ 500
  • pointsi.length == 2
  • -104 ≤ x, y ≤ 104
  • All points are different

Example

Inputpoints = [[0, 0], [1, 0], [2, 0]]
Output2

Explanation With [1, 0] as the anchor, both [0, 0] and [2, 0] sit at distance 1. That gives the two boomerangs ([1,0], [0,0], [2,0]) and ([1,0], [2,0], [0,0]).

2. Know the words first

In plain terms

Squared distance
The horizontal gap times itself plus the vertical gap times itself. It is used as the map key because it avoids square roots and rounding, and equal squared distances mean equal real distances.
Ordered pair
A pair where swapping the two items gives a different answer. With d points at the same distance there are d times (d - 1) ordered pairs of them.
Anchor point
The point in the middle of a boomerang, the one both distances are measured from. Every point takes a turn as the anchor.
3. Visualize the solution

One cell per distance key for the current anchor, plus the running total

One cell per distance key for the current anchor, plus the running total
Statusinit

Three points in a line, and no boomerangs counted yet.

What happens in this step

points = [[0,0], [1,0], [2,0]]
total = 0

The first three cells will hold distance keys for one anchor at a time.
The last cell keeps the running total.
Step 1 of 7

Steps to visualize

  1. The first three cells are the keys of the distance map for the anchor being worked on right now.
  2. The label is the squared distance and the value is how many points sit that far away.
  3. The last cell is the running total of boomerangs found so far.
  4. The map is emptied each time a new anchor is picked.
  5. Each tally of d adds d times (d - 1) to the total.
4. Walk through the code

Walk through the code

Same walkthrough, now with the code. Press Next to move one step and watch which lines run.

One cell per distance key for the current anchor, plus the running total
Statusinit

Three points in a line, and no boomerangs counted yet.

What happens in this step

points = [[0,0], [1,0], [2,0]]
total = 0

The first three cells will hold distance keys for one anchor at a time.
The last cell keeps the running total.
Step 1 of 7
5. Solution

Solution

solution.tsTypeScript
function numberOfBoomerangs(points) {
  let total = 0;

  for (const anchor of points) {
    const distances = new Map();

    for (const other of points) {
      const dx = anchor[0] - other[0];
      const dy = anchor[1] - other[1];
      const distance = dx * dx + dy * dy;

      distances.set(distance, (distances.get(distance) || 0) + 1);
    }

    for (const count of distances.values()) {
      total += count * (count - 1);
    }
  }

  return total;
}
Time
O(n^2)
Space
O(n)
6. Test cases

Test cases

InputExpectedCovers
points = [[0, 0], [1, 0], [2, 0]]2example from the description
points = [[1, 1], [2, 2], [3, 3]]2points evenly spaced along a diagonal
points = [[1, 1]]0too few points to form any boomerang
points = [[0, 0], [5, 5]]0a boomerang needs three points
points = [[0, 0], [1, 0], [-1, 0], [0, 1], [0, -1]]20a centre point with four neighbours all at the same distance
points = [[0, 0], [1, 0], [4, 0]]0no anchor has two neighbours at a matching distance