EDIT #2: Seluruh pertanyaan dan eksplorasi ini didasarkan pada hilangnya gagasan mendasar tentang ritsleting; bahwa mereka mewakili perspektif dalam struktur data dari sudut pandang node tertentu. Jadi ritsleting adalah - setiap saat - sepasang simpul saat ini dan tampilan pohon lainnya dari sudut pandang simpul tersebut. Awalnya saya mencoba membuat struktur yang benar-benar baru dari ritsleting, padahal selama ini hanya ritsleting itu sendiri yang saya perlukan. Saya akan meninggalkan semua ini untuk anak cucu, dengan harapan bahwa orang lain akan terbantu olehnya (atau lebih tepatnya ini berfungsi sebagai peringatan bagi penerusnya!).
Pertanyaan awal:
Saya mencoba menggunakan ritsleting untuk memanipulasi pohon. Masalah spesifiknya adalah saya perlu membuat rute runtime antara dua node yang cocok dengan kriteria arbitrer di pohon arbitrer.
Saya pikir saya bisa menggunakan fungsi path
untuk mendapatkan rute ke suatu lokasi dengan memanggil path
di lokasi saat ini. Namun jalur yang dikembalikan tampaknya menghilangkan langkah terakhir yang diperlukan untuk sampai ke sana.
Misalnya:
(def test-zip (vector-zip [0 [1] [2 [3 [4] 5 [6 [7] [8]]]]]))
(-> test-zip
down right right down
right down right right
node)
memberi 5
, tapi
(-> test-zip
down right right down
right down right right
path)
memberi
[[0 [1] [2 [3 [4] 5 [6 [7] [8]]]]] [2 [3 [4] 5 [6 [7] [8]]]] [3 [4] 5 [6 [7] [8]]]]
yang lokasinya tidak sama (efek dari tiga langkah terakhir tidak ada, down right right
).
Sepertinya fungsi jalur hanya membawa Anda ke lokasi induk di pohon, mengabaikan saudara kandung antara Anda dan lokasi sebenarnya.
Apakah saya melewatkan inti dari fungsi path
? Saya berasumsi bahwa dengan adanya pohon dan jalan, menerapkan jalan pada pohon tersebut akan membawa Anda ke lokasi asli jalan tersebut, bukan sebagian di sana.
PEMBARUAN: Saya telah menggunakan definisi fungsi berikut untuk mengkompilasi jalur node dari lokasi awal ke lokasi akhir:
(defn lca-path [start-loc end-loc]
(let [sczip (z/root start-loc)
start-path (z/path start-loc)
start-node (z/node start-loc)
end-path (z/path end-loc)
end-node (z/node end-loc)
lca-path (filter (set start-path) end-path)
lca-node [(last lca-path)]
lca-to-start (conj (vec (drop (count lca-path) start-path)) start-node)
lca-to-end (conj (vec (drop (count lca-path) end-path)) end-node)
]
(concat (reverse lca-to-start) lca-node lca-to-end))
)
Cukup banyak dipengaruhi oleh obrolan dengan @Mark Fisher, terima kasih!