The math seems to be above my league
MATCH (m1) WHERE m1.range < m.range AND m1.range < m.range WITH m1, m MATCH (m2) WHERE m2.range > m1.range AND m2.range > m1.range WITH m1,m2,m RETURN m1.name AS startPart, m2.name AS endPart
I don't know how many nodes are there in the graph. If there are not too many, you can create a relationship between the nodes.
WITH m MATCH (n:MyNode) WHERE (m <> n) AND (m.range < n.range AND m.range < n.range)
You might need to look for apoc.periodic.iterate() if there are too many of them in order to avoid running out of memory.
When it's done, then you can use
MATCH (m:MyNode)<-[: IS_IN_RANGE_OF]-(n)
RETURN m, COLLECT(n) AS parts
The only thing you might need is to decide which is start and which is end.
My two cents.