Esta es una solicitud de referencia, ya que estoy seguro de que lo que sigue no es nuevo, pero no puedo encontrarlo.
Supongamos que tenemos un árbol finito $T$ con pesos no negativos en las aristas. De manera ingenua, calcular las longitudes de los caminos (es decir, la suma de los pesos a lo largo del camino único) entre cada par requiere $O(n^3)$ pasos: hay $\binom{n}{2}$ pares de vértices y siempre podemos acotar el número de aristas en cualquier camino por $n-1$.
Sin embargo, podemos hacerlo mucho mejor con el siguiente truco. Elija una raíz $r$ para $T$ de manera arbitraria. Defina el ancestro común más cercano de $i$ y $j$ como el vértice $a$ donde el camino desde $i$ hasta $r$ se encuentra con el camino desde $j$ hasta $r$. Entonces, si $d(\cdot,\cdot)$ denota la distancia en $T$, obtenemos $d(i,j) = d(i,r) + d(j,r) - 2d(a,r).
Es fácil ver que todos los $d(i,r)$ se pueden calcular en $O(n)$ pasos con BFS. También hay una estructura de datos de Harel y Tarjan que, después de un preprocesamiento de $O(n)$, responderá consultas del ancestro común más cercano en tiempo $O(1)$. Entonces, todo el proceso se convierte en $O(n^2)$.