Relacje multipolygon a reguła KISS

Do popełnienia tego wpisu zmotywowało mnie zmapowanie tego sanktuarium: https://www.openstreetmap.org/#map=19/49.66772/21.21565, jak również te budynki: https://www.openstreetmap.org/#map=19/50.19653/21.26857
W obydwu przypadkach zostały użyte relacje multipolygon, moim zdaniem zupełnie niepotrzebnie, co spróbuję uzasadnić robiąc prosty test.

Na potrzeby testu weźmy te dwa budynki, przylegające do siebie ścianami: https://www.openstreetmap.org/way/323889001
W pierwszym przypadku narysujmy je klasycznie, czyli jako dwie linie z dwoma węzłami wspólnymi (tak, jak jest teraz w OSM). Otrzymujemy:

  • 7 węzłów
  • 2 linie
  • 2 tagi

Kod XML z tego przypadku (1211 znaków):

<?xml version='1.0' encoding='UTF-8'?>
<osm version='0.6' upload='true' generator='JOSM'>
  <node id='-278463' action='modify' visible='true' lat='49.66744380074' lon='21.21626754735' />
  <node id='-278461' action='modify' visible='true' lat='49.66737150969' lon='21.21642728848' />
  <node id='-278459' action='modify' visible='true' lat='49.66728518865' lon='21.21633403283' />
  <node id='-278456' action='modify' visible='true' lat='49.66741006663' lon='21.21605809099' />
  <node id='-278454' action='modify' visible='true' lat='49.66735747982' lon='21.2161742917' />
  <node id='-278452' action='modify' visible='true' lat='49.66742145131' lon='21.21624340243' />
  <node id='-278451' action='modify' visible='true' lat='49.66747403804' lon='21.21612720171' />
  <way id='-278460' action='modify' visible='true'>
    <nd ref='-278454' />
    <nd ref='-278459' />
    <nd ref='-278461' />
    <nd ref='-278463' />
    <nd ref='-278452' />
    <nd ref='-278454' />
    <tag k='building' v='yes' />
  </way>
  <way id='-278453' action='modify' visible='true'>
    <nd ref='-278451' />
    <nd ref='-278452' />
    <nd ref='-278454' />
    <nd ref='-278456' />
    <nd ref='-278451' />
    <tag k='building' v='yes' />
  </way>
</osm>

Rozważmy teraz drugi przypadek, czyli narysowanie tych budynków jako relacje type=multipolygon. Otrzymujemy:

  • 7 węzłów
  • 3 linie
  • 2 relacje
  • 4 tagi
  • 4 role

Kod XML z tego przypadku (1690 znaków):

<?xml version='1.0' encoding='UTF-8'?>
<osm version='0.6' upload='true' generator='JOSM'>
  <node id='-278463' action='modify' visible='true' lat='49.66744380074' lon='21.21626754735' />
  <node id='-278461' action='modify' visible='true' lat='49.66737150969' lon='21.21642728848' />
  <node id='-278459' action='modify' visible='true' lat='49.66728518865' lon='21.21633403283' />
  <node id='-278456' action='modify' visible='true' lat='49.66741006663' lon='21.21605809099' />
  <node id='-278454' action='modify' visible='true' lat='49.66735747982' lon='21.2161742917' />
  <node id='-278452' action='modify' visible='true' lat='49.66742145131' lon='21.21624340243' />
  <node id='-278451' action='modify' visible='true' lat='49.66747403804' lon='21.21612720171' />
  <way id='-278489' action='modify' visible='true'>
    <nd ref='-278452' />
    <nd ref='-278454' />
  </way>
  <way id='-278460' action='modify' visible='true'>
    <nd ref='-278454' />
    <nd ref='-278459' />
    <nd ref='-278461' />
    <nd ref='-278463' />
    <nd ref='-278452' />
  </way>
  <way id='-278453' action='modify' visible='true'>
    <nd ref='-278454' />
    <nd ref='-278456' />
    <nd ref='-278451' />
    <nd ref='-278452' />
  </way>
  <relation id='-278516' action='modify' visible='true'>
    <member type='way' ref='-278460' role='outer' />
    <member type='way' ref='-278489' role='outer' />
    <tag k='building' v='yes' />
    <tag k='type' v='multipolygon' />
  </relation>
  <relation id='-278513' action='modify' visible='true'>
    <member type='way' ref='-278453' role='outer' />
    <member type='way' ref='-278489' role='outer' />
    <tag k='building' v='yes' />
    <tag k='type' v='multipolygon' />
  </relation>
</osm>

Jak widać, w drugim przypadku wszystko jest bardziej skomplikowane i bajtowo zajmuje więcej pamięci (a to jest bardzo prosty przykład). Zalety? Ja ich tutaj nie widzę.

TL;DR
Sugeruję używać relacji type=multipolygon tylko tam, gdzie jest to zasadne - czyli np. gdy trzeba wyciąć otwór w jakimś obszarze. W innych przypadkach zasadność jest wątpliwa.

Reguła KISS: https://pl.wikipedia.org/wiki/KISS_%28regu%C5%82a%29

Nic, tylko się zgodzić.

o denerwującej konieczności używania czasem multipolygonów w absurdalnych miejscach, już gdzieś tu pisałem więc dorzucę moje przemyślenia:

ułomność mapnika w normalnym renderowaniu nakładających się na siebie warstw też niestety prowadzi do mnożenia się zajmujących pamięć i komplikujących sprawę relacji, kiedy tak naprawdę można to rozwiązać w inny, prostszy sposób - najlepszym przykładem są chyba wysepki na jeziorach, wiele razy spotkałem się z wysepkami narysowanymi po prostu, na obszarze jeziora, logiczne byłoby wyrenderowanie i jeziora i wysepki jednocześnie, tylko na podstawie tego że są wyrysowane, ale mapnik posiada hierarchię (kompletnie nieintuicyjną swoją drogą) warstw przez co w takim przypadku wyświetlane jest tylko jezioro, a wysepka bez multipolygonu “ukryta” pod nim; ja wiem zaraz ktoś napisze że to prosty przykład a czasem jest gorzej i powinna być hierarchia - tylko dlaczego nie może w danym miejscu decydować o niej mapowicz używając tagu “layer=” ? takie rozwiązanie pozwoliłoby na upraszczanie mapy; z relacjami multipolygon jest też ten problem że dla mniej zaawansowanych użytkowników są nieznane lub niezrozumiałe przez co na mapie mamy na pewno sporo takich poukrywanych wysepek jak z powyższego przykładu; innym możliwym rozwiązaniem oprócz odblokowania “layer=?” byłoby wprowadzenie oprócz punktów, linii, obszarów i relacji jeszcze jednego prostego elementu, mogłyby by być to “dziury” czyli dwa związane ze sobą, nakładające się obszary, ale bez potrzeby tworzenia relacji, bo moim zdaniem relacje multipolygon to w ogóle narzędzie prowizoryczne, którego przybywanie na mapie będzie ją komplikować i komplikować

Dlatego, że nie samym mapnikiem OSM żyje. Jeżeli by pójść za Twoją propozycją ,to miałbym kłopot, z tym, by wiedzieć, że posiadam całą geometrię obiektu. Mam linię otagowaną jako jezioro - skąd mam wiedzieć, jakie jeszcze linie muszę ściągnąć, by znaleźć w niej dziury? Relacje dają tą wiedzę, a przy okazji też ułatwiają mapnikowi robotę.

Cała twoja argumentacja opiera się o to, jak działa jakiś konkretny renderer i jak można na różny sposób przeciwdziałać jego ułomnościom. OSM to jednak coś więcej niż kafelki z Mapnika. Dane z mapy są przetwarzane maszynowo - zarówno w celu uzyskania wizualizacji, jak i w celu uzyskania innych wyników, np. analiz przestrzennych. Istnieją pewne standardy i praktyki w gromadzeniu danych geograficznych. Bardzo trafny argument dał już WiktorN. Poza tym, trzeba jeszcze wspomnieć o topologii mapy. W przypadku wyspy na jeziorze mamy taką właśnie sytuację: w dowolnym punkcie skartowanego obszaru jest albo ląd, albo woda, ale nigdy i jedno i drugie. Dla renderera to może nie mieć znaczenia, bo istotnie da się go tak zaprogramować, żeby obiekty lądowe rysował nad wodami, ale dla różnych zastosowań maszynowych pokrywające się obszary wody i lądu są już poważną wadą. Pewnie, że też można wyszukiwać nakładające się obiekty i wycinać jedne z drugich, ale tak się po prostu nie robi. Praktyka nakazuje, żeby od początku gromadzić dane geograficzne w spójnych topologicznie zestawach, bo tak po prostu jest na dłuższą metę łatwiej.

A poza tym trafią się kwiatki z wyspą na jeziorze na wyspie na jeziorze: http://earthobservatory.nasa.gov/IOTD/view.php?id=85342