Ето решение, което ви позволява да преместите възел във всяка позиция в дървото само с един входен параметър – новата лява позиция (newpos) на възела.
По принцип има три набора:
- Създайте ново пространство за поддървото.
- Преместете поддървото в това пространство.
- Премахнете старото пространство, освободено от поддървото.
В psuedo-sql изглежда така:
//
* -- create new space for subtree
* UPDATE tags SET lpos = lpos + :width WHERE lpos >= :newpos
* UPDATE tags SET rpos = rpos + :width WHERE rpos >= :newpos
*
* -- move subtree into new space
* UPDATE tags SET lpos = lpos + :distance, rpos = rpos + :distance
* WHERE lpos >= :tmppos AND rpos < :tmppos + :width
*
* -- remove old space vacated by subtree
* UPDATE tags SET lpos = lpos - :width WHERE lpos > :oldrpos
* UPDATE tags SET rpos = rpos - :width WHERE rpos > :oldrpos
*/
Променливата :distance е разстоянието между новата и старата позиция, :width е размерът на поддървото, а :tmppos се използва за проследяване на преместването на поддървото по време на актуализациите. Тези променливи се дефинират като:
// calculate position adjustment variables
int width = node.getRpos() - node.getLpos() + 1;
int distance = newpos - node.getLpos();
int tmppos = node.getLpos();
// backwards movement must account for new space
if (distance < 0) {
distance -= width;
tmppos += width;
}
За пълен пример за код вижте моя блог на
https://rogerkeays.com/how -to-move-a-node-in-nested-sets-with-sql
Ако ви харесва това решение, моля, гласувайте за.