jak v takové reprezentaci efektivně najdete všechny hrany incidující s danným vrcholem, případně všechny sousední vrcholy?
Každá reprezentace je efektivní pro nějaké použití a neefektivní pro jiné. Reprezentace, která by byla optimální pro každé myslitelné použití, typicky neexistuje.
Ta reprezentace s kruhoými odkazy je zase neefektivní, pokud budu chtít seznam všech vrcholů - já to mám s časovou složitostí 0, vy s n.
Pokud by můj primární use case bylo hledat sousedící hrany, tak bych zvolil jinou reprezentaci, nejspíš tuhle:
%{vrchol1: [vrchol2, vrchol3], vrchol3: [vrchol4]}
- tj. asociativní pole vrchol=>seznam sousedů.
Představoval jsem si reprezentaci grafu jako seznam vrcholů, kde každý vrchol odkazuje na seznam svých hran. Hrany odkazují zpět na vrcholy. V takové reprezentaci se cykly vyskytují. Přidat hranu, která vytváří cyklus nejde, protože můžete přidávat hrany jen do dosud nevytvořených vrcholů.
Asi ne seznam hran, ale seznam vrcholů. Ano, to skutečně v FP pro obecný graf udělat nejde. Ale nevadí to, protože máme jiné možné reprezentace. A je otázka, jestli to, že to v ostatních jazycích jde, za to skutečně stojí. Plynou z toho totiž pak např. takové věci, jako že když chce Ruby udělat GC, musí zastavit celý svět. Velice nepříjemná vlastnost pro produkci...
Myslel jsem nějakou slovníkovou datovou strukturu. Ty jsou ve funkcionálních jazycích často implementované nějakým stromem a přístup má logaritmickou složitost. Imutabilní jsem myslel ve smyslu implementovatelné pomocí immutable n-tic. Ne neměnnou.
Jinak normální slovník (hashmap) je třeba v Elixiru first class citizen, takže je implementovaný v runtimu nejefektivnějším možným způsobem - maximální složitost pro čtení i zápis je log(n).
Horší je to právě s tím stromem - v FP musím při zápisu někde dole zpětně "přeskládat" celý strom, nemůžu jenom najít list, zapsat do něj a mám hotovo. To je pravda. Ale opakuju: No a? Co z toho plyne? Že FP není ve všem lepší? No jasně, to přece nikdo netvrdí.