With an 10000 x 10000 range, a point diameter of 300 and 1 million plus random points it will be almost impossible to place the points without a connection from every point to every other point. I suspect that you need to rethink these numbers.
The problem here is similar to collision detection where you what to test each point against every other point. Now if we have n points then the number of tests is n*(n-1)/2 so if n = 1,000,000 there are approximately 500,000,000,000 tests far too much. What we need is a means to reduce the number of tests.
The simplest solution is to use cell space partitioning (CSP).
The following description is to show the potential benefits of CSP. To simplify the situation I have made the following assumptions
- there are 40,000 points
- each point has a diameter of 50
- the domain coordinates (x and y) are in the range ≥0 and <16384
The domain range was chosen to be a power of 2 in this case 2^{16}=16384 because it will have benefits later.
The domain has to be split into cells like a chessboard. The cell size should be at least 4 * the point diameter, in this case 200 (4 * 50) but for efficiency we want the grid size to be the next smallest power of 2. So the next power of two greater than 200 is 256 (256 = 2^8)
This means that the domain is like a chess board with 64 cells on each side so lets do the maths.
There are 64*64 = 4096 cells so if the points are evenly distributed there will be approximately 10 points per cell.
So number of testes per cell would be 10*9/2 = 45 so the total number of tests would be 45 * 4096 = 184,320 tests so to summarize
The number of tests would be -
799,980,000
without cell space partitioning and
184,320
with cell partitioning
I said that using powers of 2 would help efficiency. A quick demonstration using our example.
Consider a point at position [x, y]
where both the x
and y
are integers in the range ≥0 to <16384 and a domain with a cell size of (2^8) we can calculate the 2D position of the cell [cx, cy]
using bit manipulation
cx = (x >> 8);
cy = (y >> 8)
we can use this to decide on the cell to store the point.
If needed we can find the position within the cell
mask = (1 << 8) - 1;
px = (x & mask);
py = (y & mask);
To use this approach you would need to create at least three classes
Point
- cannot use PVector because the coordinates are stored as floats
. It can be a very small class because it is simple a means of storing a position.
Cell
- each cell must have its own list
of Points
Domain
a 2D grid of cells