[geos-commits] [SCM] GEOS branch master updated. 142466d2244614884386b1c49a23f8849857585c
git at osgeo.org
git at osgeo.org
Sat Dec 19 10:36:32 PST 2020
This is an automated email from the git hooks/post-receive script. It was
generated because a ref change was pushed to the repository containing
the project "GEOS".
The branch, master has been updated
via 142466d2244614884386b1c49a23f8849857585c (commit)
via 928ffac311678d131d47d9076fb0e837854239d0 (commit)
via 4c1cf5ae2ad3a0702debca5c6130434e97ccf407 (commit)
via 9a9ba9eb13b5891f2d5d34bb8a6ae3d85140959d (commit)
via 67cc8f7aac2531b6a4f5e970d9d85cb9bd2659e2 (commit)
via 2cffa09cf3819a03c809eee23b69291ba05e4c39 (commit)
from 4466ee0e4e85f21ef362098f0d61db4222b831b7 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 142466d2244614884386b1c49a23f8849857585c
Merge: 4466ee0 928ffac
Author: Daniel Baston <dbaston at gmail.com>
Date: Sat Dec 19 13:36:11 2020 -0500
Merge branch 'segment-node-list2'
commit 928ffac311678d131d47d9076fb0e837854239d0
Author: Daniel Baston <dbaston at gmail.com>
Date: Sat Dec 19 12:18:38 2020 -0500
Inline SegmentNode::compareTo
diff --git a/include/geos/noding/Makefile.am b/include/geos/noding/Makefile.am
index 56e8949..c4cc74b 100644
--- a/include/geos/noding/Makefile.am
+++ b/include/geos/noding/Makefile.am
@@ -1,5 +1,5 @@
#
-# This file is part of project GEOS (http://trac.osgeo.org/geos/)
+# This file is part of project GEOS (http://trac.osgeo.org/geos/)
#
SUBDIRS = \
snapround \
@@ -31,6 +31,7 @@ geos_HEADERS = \
SegmentIntersectionDetector.h \
SegmentIntersector.h \
SegmentNode.h \
+ SegmentNode.inl \
SegmentNodeList.h \
SegmentPointComparator.h \
SegmentSetMutualIntersector.h \
diff --git a/include/geos/noding/SegmentNode.h b/include/geos/noding/SegmentNode.h
index fd24425..3869475 100644
--- a/include/geos/noding/SegmentNode.h
+++ b/include/geos/noding/SegmentNode.h
@@ -124,4 +124,8 @@ struct GEOS_DLL SegmentNodeLT {
} // namespace geos.noding
} // namespace geos
+#ifdef GEOS_INLINE
+# include "geos/noding/SegmentNode.inl"
+#endif
+
#endif // GEOS_NODING_SEGMENTNODE_H
diff --git a/src/noding/SegmentNode.cpp b/include/geos/noding/SegmentNode.inl
similarity index 66%
copy from src/noding/SegmentNode.cpp
copy to include/geos/noding/SegmentNode.inl
index 8f9c306..a70f18b 100644
--- a/src/noding/SegmentNode.cpp
+++ b/include/geos/noding/SegmentNode.inl
@@ -4,10 +4,9 @@
* http://geos.osgeo.org
*
* Copyright (C) 2006 Refractions Research Inc.
- * Copyright (C) 2001-2002 Vivid Solutions Inc.
*
* This is free software; you can redistribute and/or modify it under
- * the terms of the GNU Lesser General Licence as published
+ * the terms of the GNU Lesser General Public Licence as published
* by the Free Software Foundation.
* See the COPYING file for more information.
*
@@ -17,45 +16,17 @@
*
**********************************************************************/
-#ifndef GEOS_DEBUG
-#define GEOS_DEBUG 0
-#endif
-
-#include <iostream>
-#include <sstream>
-#include <iomanip>
+#ifndef GEOS_NODING_SEGMENTNODE_INL
+#define GEOS_NODING_SEGMENTNODE_INL
#include <geos/noding/SegmentNode.h>
-#include <geos/noding/SegmentPointComparator.h>
-#include <geos/noding/NodedSegmentString.h>
#include <geos/geom/Coordinate.h>
-
-
-using namespace geos::geom;
+#include <geos/noding/SegmentPointComparator.h>
namespace geos {
-namespace noding { // geos.noding
-
-
-/*public*/
-SegmentNode::SegmentNode(const NodedSegmentString& ss, const Coordinate& nCoord,
- std::size_t nSegmentIndex, int nSegmentOctant)
- :
- segString(&ss),
- segmentOctant(nSegmentOctant),
- coord(nCoord),
- segmentIndex(nSegmentIndex)
-{
- // Number of points in NodedSegmentString is one-more number of segments
- assert(segmentIndex < segString->size());
+namespace noding {
- isInteriorVar = \
- !coord.equals2D(segString->getCoordinate(segmentIndex));
-
-}
-
-
-bool
+INLINE bool
SegmentNode::isEndPoint(unsigned int maxSegmentIndex) const
{
if(segmentIndex == 0 && ! isInteriorVar) {
@@ -72,7 +43,7 @@ SegmentNode::isEndPoint(unsigned int maxSegmentIndex) const
* @return 0 this EdgeIntersection is at the argument location
* @return 1 this EdgeIntersection is located after the argument location
*/
-int
+INLINE int
SegmentNode::compareTo(const SegmentNode& other) const
{
if(segmentIndex < other.segmentIndex) {
@@ -110,12 +81,10 @@ SegmentNode::compareTo(const SegmentNode& other) const
other.coord);
}
-std::ostream&
-operator<< (std::ostream& os, const SegmentNode& n)
-{
- return os << n.coord << " seg#=" << n.segmentIndex << " octant#=" << n.segmentOctant << std::endl;
+
+
+}
}
-} // namespace geos.noding
-} // namespace geos
+#endif
diff --git a/src/noding/SegmentNode.cpp b/src/noding/SegmentNode.cpp
index 8f9c306..2a4a7f7 100644
--- a/src/noding/SegmentNode.cpp
+++ b/src/noding/SegmentNode.cpp
@@ -26,7 +26,6 @@
#include <iomanip>
#include <geos/noding/SegmentNode.h>
-#include <geos/noding/SegmentPointComparator.h>
#include <geos/noding/NodedSegmentString.h>
#include <geos/geom/Coordinate.h>
@@ -36,81 +35,25 @@ using namespace geos::geom;
namespace geos {
namespace noding { // geos.noding
-
/*public*/
-SegmentNode::SegmentNode(const NodedSegmentString& ss, const Coordinate& nCoord,
+SegmentNode::SegmentNode(const NodedSegmentString& ss, const geom::Coordinate& nCoord,
std::size_t nSegmentIndex, int nSegmentOctant)
- :
- segString(&ss),
- segmentOctant(nSegmentOctant),
- coord(nCoord),
- segmentIndex(nSegmentIndex)
+ :
+ segString(&ss),
+ segmentOctant(nSegmentOctant),
+ coord(nCoord),
+ segmentIndex(nSegmentIndex)
{
// Number of points in NodedSegmentString is one-more number of segments
assert(segmentIndex < segString->size());
isInteriorVar = \
- !coord.equals2D(segString->getCoordinate(segmentIndex));
-
-}
+ !coord.equals2D(segString->getCoordinate(segmentIndex));
-
-bool
-SegmentNode::isEndPoint(unsigned int maxSegmentIndex) const
-{
- if(segmentIndex == 0 && ! isInteriorVar) {
- return true;
- }
- if(segmentIndex == maxSegmentIndex) {
- return true;
- }
- return false;
}
-/**
- * @return -1 this EdgeIntersection is located before the argument location
- * @return 0 this EdgeIntersection is at the argument location
- * @return 1 this EdgeIntersection is located after the argument location
- */
-int
-SegmentNode::compareTo(const SegmentNode& other) const
-{
- if(segmentIndex < other.segmentIndex) {
- return -1;
- }
- if(segmentIndex > other.segmentIndex) {
- return 1;
- }
-
-#if GEOS_DEBUG
- std::cerr << setprecision(17) << "compareTo: " << *this << ", " << other << std::endl;
-#endif
- if(coord.equals2D(other.coord)) {
-
-#if GEOS_DEBUG
- std::cerr << " Coordinates equal!" << std::endl;
-#endif
-
- return 0;
- }
-
-#if GEOS_DEBUG
- std::cerr << " Coordinates do not equal!" << std::endl;
-#endif
-
- // an exterior node is the segment start point,
- // so always sorts first
- // this guards against a robustness problem
- // where the octants are not reliable
- if (! isInteriorVar) return -1;
- if (! other.isInteriorVar) return 1;
-
- return SegmentPointComparator::compare(segmentOctant, coord,
- other.coord);
-}
-
-std::ostream&
+ std::ostream&
operator<< (std::ostream& os, const SegmentNode& n)
{
return os << n.coord << " seg#=" << n.segmentIndex << " octant#=" << n.segmentOctant << std::endl;
@@ -119,3 +62,7 @@ operator<< (std::ostream& os, const SegmentNode& n)
} // namespace geos.noding
} // namespace geos
+#ifndef GEOS_INLINE
+# include "geos/noding/SegmentNode.inl"
+#endif
+
commit 4c1cf5ae2ad3a0702debca5c6130434e97ccf407
Author: Daniel Baston <dbaston at gmail.com>
Date: Sat Dec 19 10:38:50 2020 -0500
Avoid Coordinate copy in SnapRoundingNoder
diff --git a/include/geos/noding/snapround/SnapRoundingNoder.h b/include/geos/noding/snapround/SnapRoundingNoder.h
index 6e5d221..0b614e9 100644
--- a/include/geos/noding/snapround/SnapRoundingNoder.h
+++ b/include/geos/noding/snapround/SnapRoundingNoder.h
@@ -96,8 +96,6 @@ private:
*/
void addIntersectionPixels(std::vector<SegmentString*>& segStrings);
- void round(const geom::Coordinate& pt, geom::Coordinate& ptOut);
-
/**
* Gets a list of the rounded coordinates.
* Duplicate (collapsed) coordinates are removed.
@@ -105,7 +103,7 @@ private:
* @param pts the coordinates to round
* @return array of rounded coordinates
*/
- std::unique_ptr<std::vector<geom::Coordinate>> round(const std::vector<geom::Coordinate>& pts);
+ std::vector<geom::Coordinate> round(const std::vector<geom::Coordinate>& pts) const;
/**
* Computes new segment strings which are rounded and contain
diff --git a/src/noding/snapround/SnapRoundingNoder.cpp b/src/noding/snapround/SnapRoundingNoder.cpp
index 7e6daae..9e70c64 100644
--- a/src/noding/snapround/SnapRoundingNoder.cpp
+++ b/src/noding/snapround/SnapRoundingNoder.cpp
@@ -96,26 +96,14 @@ SnapRoundingNoder::addVertexPixels(std::vector<SegmentString*>& segStrings)
}
/*private*/
-void
-SnapRoundingNoder::round(const Coordinate& pt, Coordinate& ptOut)
-{
- ptOut = pt;
- pm->makePrecise(ptOut);
- return;
-}
-
-/*private*/
-std::unique_ptr<std::vector<Coordinate>>
-SnapRoundingNoder::round(const std::vector<Coordinate>& pts)
+std::vector<Coordinate>
+SnapRoundingNoder::round(const std::vector<Coordinate>& pts) const
{
- std::unique_ptr<std::vector<Coordinate>> roundPts(new std::vector<Coordinate>);
- roundPts->reserve(pts.size());
- for (auto pt: pts) {
- Coordinate ptOut;
- round(pt, ptOut);
- roundPts->push_back(ptOut);
+ std::vector<Coordinate> roundPts = pts;
+ for (auto& pt: roundPts) {
+ pm->makePrecise(pt);
}
- roundPts->erase(std::unique(roundPts->begin(), roundPts->end()), roundPts->end());
+ roundPts.erase(std::unique(roundPts.begin(), roundPts.end()), roundPts.end());
return roundPts;
}
@@ -158,8 +146,8 @@ SnapRoundingNoder::computeSegmentSnaps(NodedSegmentString* ss)
* in preparation for snapping to the Hot Pixels
*/
std::vector<Coordinate> pts = ss->getNodedCoordinates();
- std::unique_ptr<std::vector<Coordinate>> ptsRoundVec = round(pts);
- std::unique_ptr<geom::CoordinateArraySequence> ptsRound(new CoordinateArraySequence(ptsRoundVec.release()));
+ std::vector<Coordinate> ptsRoundVec = round(pts);
+ std::unique_ptr<geom::CoordinateArraySequence> ptsRound(new CoordinateArraySequence(std::move(ptsRoundVec)));
// if complete collapse this edge can be eliminated
if (ptsRound->size() <= 1)
@@ -177,8 +165,8 @@ SnapRoundingNoder::computeSegmentSnaps(NodedSegmentString* ss)
* If the segment has collapsed completely, skip it
*/
Coordinate p1 = pts[i+1];
- Coordinate p1Round;
- round(p1, p1Round);
+ Coordinate p1Round = p1;
+ pm->makePrecise(p1Round);
if (p1Round.equals2D(currSnap))
continue;
commit 9a9ba9eb13b5891f2d5d34bb8a6ae3d85140959d
Author: Daniel Baston <dbaston at gmail.com>
Date: Sat Dec 19 10:29:05 2020 -0500
Tidy SegmentNodeList
diff --git a/include/geos/noding/NodedSegmentString.h b/include/geos/noding/NodedSegmentString.h
index 27d75fb..bc28cbf 100644
--- a/include/geos/noding/NodedSegmentString.h
+++ b/include/geos/noding/NodedSegmentString.h
@@ -85,7 +85,7 @@ public:
static SegmentString::NonConstVect* getNodedSubstrings(
const SegmentString::NonConstVect& segStrings);
- std::unique_ptr<std::vector<geom::Coordinate>> getNodedCoordinates();
+ std::vector<geom::Coordinate> getNodedCoordinates();
/** \brief
diff --git a/include/geos/noding/SegmentNodeList.h b/include/geos/noding/SegmentNodeList.h
index 5762cf7..a8c1407 100644
--- a/include/geos/noding/SegmentNodeList.h
+++ b/include/geos/noding/SegmentNodeList.h
@@ -124,29 +124,28 @@ private:
void findCollapsesFromInsertedNodes(
std::vector<std::size_t>& collapsedVertexIndexes) const;
- bool findCollapseIndex(const SegmentNode& ei0, const SegmentNode& ei1,
- size_t& collapsedVertexIndex) const;
+ static bool findCollapseIndex(const SegmentNode& ei0, const SegmentNode& ei1,
+ size_t& collapsedVertexIndex);
void addEdgeCoordinates(const SegmentNode* ei0, const SegmentNode* ei1, std::vector<geom::Coordinate>& coordList) const;
+public:
+
// Declare type as noncopyable
SegmentNodeList(const SegmentNodeList& other) = delete;
SegmentNodeList& operator=(const SegmentNodeList& rhs) = delete;
-public:
-
friend std::ostream& operator<< (std::ostream& os, const SegmentNodeList& l);
using container = decltype(nodeMap);
+ using iterator = container::iterator;
+ using const_iterator = container::const_iterator;
- typedef container::iterator iterator;
- typedef container::const_iterator const_iterator;
+ explicit SegmentNodeList(const NodedSegmentString* newEdge): edge(*newEdge) {}
- SegmentNodeList(const NodedSegmentString* newEdge): edge(*newEdge) {}
+ explicit SegmentNodeList(const NodedSegmentString& newEdge): edge(newEdge) {}
- SegmentNodeList(const NodedSegmentString& newEdge): edge(newEdge) {}
-
- ~SegmentNodeList();
+ ~SegmentNodeList() = default;
const NodedSegmentString&
getEdge() const
@@ -180,13 +179,25 @@ public:
return nodeMap.size();
}
- iterator begin();
+ iterator begin() {
+ prepare();
+ return nodeMap.begin();
+ }
- const_iterator begin() const;
+ const_iterator begin() const {
+ prepare();
+ return nodeMap.begin();
+ }
- iterator end();
+ iterator end() {
+ prepare();
+ return nodeMap.end();
+ }
- const_iterator end() const;
+ const_iterator end() const {
+ prepare();
+ return nodeMap.end();
+ }
/**
* Adds entries for the first and last points of the edge to the list
@@ -217,7 +228,7 @@ public:
* @return an array of Coordinates
*
*/
- std::unique_ptr<std::vector<geom::Coordinate>> getSplitCoordinates();
+ std::vector<geom::Coordinate> getSplitCoordinates();
};
diff --git a/src/noding/NodedSegmentString.cpp b/src/noding/NodedSegmentString.cpp
index 3855594..771ea65 100644
--- a/src/noding/NodedSegmentString.cpp
+++ b/src/noding/NodedSegmentString.cpp
@@ -133,7 +133,7 @@ NodedSegmentString::getNodedSubstrings(
}
/* public */
-std::unique_ptr<std::vector<Coordinate>>
+std::vector<Coordinate>
NodedSegmentString::getNodedCoordinates() {
return nodeList.getSplitCoordinates();
}
diff --git a/src/noding/SegmentNodeList.cpp b/src/noding/SegmentNodeList.cpp
index 4c4d7af..739ecde 100644
--- a/src/noding/SegmentNodeList.cpp
+++ b/src/noding/SegmentNodeList.cpp
@@ -58,10 +58,6 @@ SegmentNodeList::add(const Coordinate& intPt, std::size_t segmentIndex)
ready = false;
}
-SegmentNodeList::~SegmentNodeList()
-{
-}
-
void SegmentNodeList::prepare() const {
if (!ready) {
std::sort(nodeMap.begin(), nodeMap.end(), [](const SegmentNode& s1, const SegmentNode& s2) {
@@ -76,34 +72,6 @@ void SegmentNodeList::prepare() const {
}
}
-SegmentNodeList::iterator
-SegmentNodeList::begin()
-{
- prepare();
- return nodeMap.begin();
-}
-
-SegmentNodeList::const_iterator
-SegmentNodeList::begin() const
-{
- prepare();
- return nodeMap.begin();
-}
-
-SegmentNodeList::iterator
-SegmentNodeList::end()
-{
- prepare();
- return nodeMap.end();
-}
-
-SegmentNodeList::const_iterator
-SegmentNodeList::end() const
-{
- prepare();
- return nodeMap.end();
-}
-
void
SegmentNodeList::addEndpoints()
{
@@ -174,7 +142,7 @@ SegmentNodeList::findCollapsesFromInsertedNodes(
/* private */
bool
SegmentNodeList::findCollapseIndex(const SegmentNode& ei0, const SegmentNode& ei1,
- size_t& collapsedVertexIndex) const
+ size_t& collapsedVertexIndex)
{
assert(ei1.segmentIndex >= ei0.segmentIndex);
// only looking for equal nodes
@@ -215,11 +183,11 @@ SegmentNodeList::addSplitEdges(std::vector<SegmentString*>& edgeList)
// there should always be at least two entries in the list
// since the endpoints are nodes
- iterator it = begin();
+ auto it = begin();
const SegmentNode* eiPrev = &(*it);
assert(eiPrev);
++it;
- for(iterator itEnd = end(); it != itEnd; ++it) {
+ for(auto itEnd = end(); it != itEnd; ++it) {
const SegmentNode* ei = &(*it);
assert(ei);
@@ -313,23 +281,22 @@ SegmentNodeList::createSplitEdgePts(const SegmentNode* ei0, const SegmentNode* e
if (useIntPt1) {
pts.emplace_back(ei1->coord);
}
- return;
}
/*public*/
-std::unique_ptr<std::vector<Coordinate>>
+std::vector<Coordinate>
SegmentNodeList::getSplitCoordinates()
{
// ensure that the list has entries for the first and last point of the edge
addEndpoints();
- std::unique_ptr<std::vector<Coordinate>> coordList(new std::vector<Coordinate>);
+ std::vector<Coordinate> coordList;
// there should always be at least two entries in the list, since the endpoints are nodes
- iterator it = begin();
+ auto it = begin();
const SegmentNode* eiPrev = &(*it);
- for(iterator itEnd = end(); it != itEnd; ++it) {
+ for(auto itEnd = end(); it != itEnd; ++it) {
const SegmentNode* ei = &(*it);
- addEdgeCoordinates(eiPrev, ei, *coordList);
+ addEdgeCoordinates(eiPrev, ei, coordList);
eiPrev = ei;
}
return coordList;
diff --git a/src/noding/snapround/SnapRoundingNoder.cpp b/src/noding/snapround/SnapRoundingNoder.cpp
index 78363ea..7e6daae 100644
--- a/src/noding/snapround/SnapRoundingNoder.cpp
+++ b/src/noding/snapround/SnapRoundingNoder.cpp
@@ -157,8 +157,8 @@ SnapRoundingNoder::computeSegmentSnaps(NodedSegmentString* ss)
* The coordinates are now rounded to the grid,
* in preparation for snapping to the Hot Pixels
*/
- std::unique_ptr<std::vector<Coordinate>> pts = ss->getNodedCoordinates();
- std::unique_ptr<std::vector<Coordinate>> ptsRoundVec = round(*pts);
+ std::vector<Coordinate> pts = ss->getNodedCoordinates();
+ std::unique_ptr<std::vector<Coordinate>> ptsRoundVec = round(pts);
std::unique_ptr<geom::CoordinateArraySequence> ptsRound(new CoordinateArraySequence(ptsRoundVec.release()));
// if complete collapse this edge can be eliminated
@@ -169,20 +169,20 @@ SnapRoundingNoder::computeSegmentSnaps(NodedSegmentString* ss)
NodedSegmentString* snapSS = new NodedSegmentString(ptsRound.release(), ss->getData());
std::size_t snapSSindex = 0;
- for (std::size_t i = 0, sz = pts->size()-1; i < sz; i++ ) {
+ for (std::size_t i = 0, sz = pts.size()-1; i < sz; i++ ) {
const geom::Coordinate& currSnap = snapSS->getCoordinate(snapSSindex);
/**
* If the segment has collapsed completely, skip it
*/
- Coordinate p1 = (*pts)[i+1];
+ Coordinate p1 = pts[i+1];
Coordinate p1Round;
round(p1, p1Round);
if (p1Round.equals2D(currSnap))
continue;
- Coordinate p0 = (*pts)[i];
+ Coordinate p0 = pts[i];
/**
* Add any Hot Pixel intersections with *original* segment to rounded segment.
commit 67cc8f7aac2531b6a4f5e970d9d85cb9bd2659e2
Author: Daniel Baston <dbaston at gmail.com>
Date: Fri Dec 18 20:42:08 2020 -0500
Store SegmentNode in std::vector instead of std::map
Provides a roughly 5-percent performance gain.
diff --git a/include/geos/noding/SegmentNode.h b/include/geos/noding/SegmentNode.h
index 88bb674..fd24425 100644
--- a/include/geos/noding/SegmentNode.h
+++ b/include/geos/noding/SegmentNode.h
@@ -46,16 +46,12 @@ namespace noding { // geos.noding
*/
class GEOS_DLL SegmentNode {
private:
- const NodedSegmentString& segString;
+ const NodedSegmentString* segString;
int segmentOctant;
bool isInteriorVar;
- // Declare type as noncopyable
- SegmentNode(const SegmentNode& other) = delete;
- SegmentNode& operator=(const SegmentNode& rhs) = delete;
-
public:
friend std::ostream& operator<< (std::ostream& os, const SegmentNode& n);
diff --git a/include/geos/noding/SegmentNodeList.h b/include/geos/noding/SegmentNodeList.h
index 4ce01c2..5762cf7 100644
--- a/include/geos/noding/SegmentNodeList.h
+++ b/include/geos/noding/SegmentNodeList.h
@@ -55,7 +55,14 @@ namespace noding { // geos::noding
*/
class GEOS_DLL SegmentNodeList {
private:
- std::set<SegmentNode, SegmentNodeLT> nodeMap;
+ // Since we are adding frequently to the SegmentNodeList and iterating infrequently,
+ // it is faster to store all the SegmentNodes in a vector and sort/remove duplicates
+ // before iteration, rather than storing them in a set and continuously maintaining
+ // a sorted order.
+ mutable std::vector<SegmentNode> nodeMap;
+ mutable bool ready = false;
+
+ void prepare() const;
// the parent edge
const NodedSegmentString& edge;
@@ -169,29 +176,17 @@ public:
size_t
size() const
{
+ prepare();
return nodeMap.size();
}
- container::iterator
- begin()
- {
- return nodeMap.begin();
- }
- container::const_iterator
- begin() const
- {
- return nodeMap.begin();
- }
- container::iterator
- end()
- {
- return nodeMap.end();
- }
- container::const_iterator
- end() const
- {
- return nodeMap.end();
- }
+ iterator begin();
+
+ const_iterator begin() const;
+
+ iterator end();
+
+ const_iterator end() const;
/**
* Adds entries for the first and last points of the edge to the list
diff --git a/src/noding/SegmentNode.cpp b/src/noding/SegmentNode.cpp
index 83f663e..8f9c306 100644
--- a/src/noding/SegmentNode.cpp
+++ b/src/noding/SegmentNode.cpp
@@ -41,16 +41,16 @@ namespace noding { // geos.noding
SegmentNode::SegmentNode(const NodedSegmentString& ss, const Coordinate& nCoord,
std::size_t nSegmentIndex, int nSegmentOctant)
:
- segString(ss),
+ segString(&ss),
segmentOctant(nSegmentOctant),
coord(nCoord),
segmentIndex(nSegmentIndex)
{
// Number of points in NodedSegmentString is one-more number of segments
- assert(segmentIndex < segString.size());
+ assert(segmentIndex < segString->size());
isInteriorVar = \
- !coord.equals2D(segString.getCoordinate(segmentIndex));
+ !coord.equals2D(segString->getCoordinate(segmentIndex));
}
diff --git a/src/noding/SegmentNodeList.cpp b/src/noding/SegmentNodeList.cpp
index 516b0e0..4c4d7af 100644
--- a/src/noding/SegmentNodeList.cpp
+++ b/src/noding/SegmentNodeList.cpp
@@ -53,13 +53,57 @@ static Profiler* profiler = Profiler::instance();
void
SegmentNodeList::add(const Coordinate& intPt, std::size_t segmentIndex)
{
- nodeMap.emplace(edge, intPt, segmentIndex, edge.getSegmentOctant(segmentIndex));
+ SegmentNode sn(edge, intPt, segmentIndex, edge.getSegmentOctant(segmentIndex));
+ nodeMap.push_back(sn);
+ ready = false;
}
SegmentNodeList::~SegmentNodeList()
{
}
+void SegmentNodeList::prepare() const {
+ if (!ready) {
+ std::sort(nodeMap.begin(), nodeMap.end(), [](const SegmentNode& s1, const SegmentNode& s2) {
+ return s1.compareTo(s2) < 0;
+ });
+
+ nodeMap.erase(std::unique(nodeMap.begin(), nodeMap.end(), [](const SegmentNode& s1, const SegmentNode& s2) {
+ return s1.compareTo(s2) == 0;
+ }), nodeMap.end());
+
+ ready = true;
+ }
+}
+
+SegmentNodeList::iterator
+SegmentNodeList::begin()
+{
+ prepare();
+ return nodeMap.begin();
+}
+
+SegmentNodeList::const_iterator
+SegmentNodeList::begin() const
+{
+ prepare();
+ return nodeMap.begin();
+}
+
+SegmentNodeList::iterator
+SegmentNodeList::end()
+{
+ prepare();
+ return nodeMap.end();
+}
+
+SegmentNodeList::const_iterator
+SegmentNodeList::end() const
+{
+ prepare();
+ return nodeMap.end();
+}
+
void
SegmentNodeList::addEndpoints()
{
@@ -112,10 +156,10 @@ SegmentNodeList::findCollapsesFromInsertedNodes(
// there should always be at least two entries in the list,
// since the endpoints are nodes
- iterator it = begin();
+ auto it = begin();
const SegmentNode* eiPrev = &(*it);
++it;
- for(iterator itEnd = end(); it != itEnd; ++it) {
+ for(auto itEnd = end(); it != itEnd; ++it) {
const SegmentNode* ei = &(*it);
bool isCollapsed = findCollapseIndex(*eiPrev, *ei,
collapsedVertexIndex);
commit 2cffa09cf3819a03c809eee23b69291ba05e4c39
Author: Daniel Baston <dbaston at gmail.com>
Date: Tue Dec 8 20:40:51 2020 -0500
Store SegmentNode values directly in SegmentNodeList
SegmentNodeList went to great pains to create SegmentNodes with stable
addresses so that pointers to the created SegmentNodes could be passed
to callers. However, the returned pointers were never used. This commit
simplifies SegmentNodeList by storing SegmentNodes directly in nodeMap.
diff --git a/include/geos/noding/NodedSegmentString.h b/include/geos/noding/NodedSegmentString.h
index d93bba9..27d75fb 100644
--- a/include/geos/noding/NodedSegmentString.h
+++ b/include/geos/noding/NodedSegmentString.h
@@ -111,39 +111,6 @@ public:
~NodedSegmentString() override = default;
- /** \brief
- * Adds an intersection node for a given point and segment to this segment string.
- *
- * If an intersection already exists for this exact location, the existing
- * node will be returned.
- *
- * @param intPt the location of the intersection
- * @param segmentIndex the index of the segment containing the intersection
- * @return the intersection node for the point
- */
- SegmentNode*
- addIntersectionNode(geom::Coordinate* intPt, std::size_t segmentIndex)
- {
- std::size_t normalizedSegmentIndex = segmentIndex;
-
- // normalize the intersection point location
- std::size_t nextSegIndex = normalizedSegmentIndex + 1;
- if(nextSegIndex < size()) {
- geom::Coordinate const& nextPt =
- getCoordinate(nextSegIndex);
-
- // Normalize segment index if intPt falls on vertex
- // The check for point equality is 2D only - Z values are ignored
- if(intPt->equals2D(nextPt)) {
- normalizedSegmentIndex = nextSegIndex;
- }
- }
-
- // Add the intersection point to edge intersection list.
- SegmentNode* ei = getNodeList().add(*intPt, normalizedSegmentIndex);
- return ei;
- }
-
SegmentNodeList& getNodeList();
const SegmentNodeList& getNodeList() const;
diff --git a/include/geos/noding/SegmentNode.h b/include/geos/noding/SegmentNode.h
index dba6232..88bb674 100644
--- a/include/geos/noding/SegmentNode.h
+++ b/include/geos/noding/SegmentNode.h
@@ -103,7 +103,7 @@ public:
* @return 1 this EdgeIntersection is located after the
* argument location
*/
- int compareTo(const SegmentNode& other);
+ int compareTo(const SegmentNode& other) const;
//string print() const;
};
@@ -116,6 +116,12 @@ struct GEOS_DLL SegmentNodeLT {
{
return s1->compareTo(*s2) < 0;
}
+
+ bool
+ operator()(const SegmentNode& s1, const SegmentNode& s2) const
+ {
+ return s1.compareTo(s2) < 0;
+ }
};
diff --git a/include/geos/noding/SegmentNodeList.h b/include/geos/noding/SegmentNodeList.h
index 80c46c6..4ce01c2 100644
--- a/include/geos/noding/SegmentNodeList.h
+++ b/include/geos/noding/SegmentNodeList.h
@@ -55,8 +55,7 @@ namespace noding { // geos::noding
*/
class GEOS_DLL SegmentNodeList {
private:
- std::set<SegmentNode*, SegmentNodeLT> nodeMap;
- std::deque<SegmentNode> nodeQue;
+ std::set<SegmentNode, SegmentNodeLT> nodeMap;
// the parent edge
const NodedSegmentString& edge;
@@ -131,7 +130,8 @@ public:
friend std::ostream& operator<< (std::ostream& os, const SegmentNodeList& l);
- typedef std::set<SegmentNode*, SegmentNodeLT> container;
+ using container = decltype(nodeMap);
+
typedef container::iterator iterator;
typedef container::const_iterator const_iterator;
@@ -157,23 +157,12 @@ public:
* @param intPt the intersection Coordinate, will be copied
* @param segmentIndex
*/
- SegmentNode* add(const geom::Coordinate& intPt, std::size_t segmentIndex);
+ void add(const geom::Coordinate& intPt, std::size_t segmentIndex);
- SegmentNode*
+ void
add(const geom::Coordinate* intPt, std::size_t segmentIndex)
{
- return add(*intPt, segmentIndex);
- }
-
- /*
- * returns the set of SegmentNodes
- */
- //replaces iterator()
- // TODO: obsolete this function
- std::set<SegmentNode*, SegmentNodeLT>*
- getNodes()
- {
- return &nodeMap;
+ add(*intPt, segmentIndex);
}
/// Return the number of nodes in this list
diff --git a/src/noding/SegmentNode.cpp b/src/noding/SegmentNode.cpp
index 64732df..83f663e 100644
--- a/src/noding/SegmentNode.cpp
+++ b/src/noding/SegmentNode.cpp
@@ -73,7 +73,7 @@ SegmentNode::isEndPoint(unsigned int maxSegmentIndex) const
* @return 1 this EdgeIntersection is located after the argument location
*/
int
-SegmentNode::compareTo(const SegmentNode& other)
+SegmentNode::compareTo(const SegmentNode& other) const
{
if(segmentIndex < other.segmentIndex) {
return -1;
diff --git a/src/noding/SegmentNodeList.cpp b/src/noding/SegmentNodeList.cpp
index bb52d39..516b0e0 100644
--- a/src/noding/SegmentNodeList.cpp
+++ b/src/noding/SegmentNodeList.cpp
@@ -50,25 +50,12 @@ static Profiler* profiler = Profiler::instance();
#endif
-SegmentNode*
+void
SegmentNodeList::add(const Coordinate& intPt, std::size_t segmentIndex)
{
- nodeQue.emplace_back(edge, intPt, segmentIndex, edge.getSegmentOctant(segmentIndex));
- SegmentNode* eiNew = &(nodeQue.back());
-
- std::pair<SegmentNodeList::iterator, bool> p = nodeMap.insert(eiNew);
- if(p.second) { // new SegmentNode inserted
- return eiNew;
- }
- else {
- // sanity check
- assert(eiNew->coord.equals2D(intPt));
- nodeQue.pop_back();
- return *(p.first);
- }
+ nodeMap.emplace(edge, intPt, segmentIndex, edge.getSegmentOctant(segmentIndex));
}
-
SegmentNodeList::~SegmentNodeList()
{
}
@@ -126,10 +113,10 @@ SegmentNodeList::findCollapsesFromInsertedNodes(
// there should always be at least two entries in the list,
// since the endpoints are nodes
iterator it = begin();
- SegmentNode* eiPrev = *it;
+ const SegmentNode* eiPrev = &(*it);
++it;
for(iterator itEnd = end(); it != itEnd; ++it) {
- SegmentNode* ei = *it;
+ const SegmentNode* ei = &(*it);
bool isCollapsed = findCollapseIndex(*eiPrev, *ei,
collapsedVertexIndex);
if(isCollapsed) {
@@ -185,11 +172,11 @@ SegmentNodeList::addSplitEdges(std::vector<SegmentString*>& edgeList)
// there should always be at least two entries in the list
// since the endpoints are nodes
iterator it = begin();
- SegmentNode* eiPrev = *it;
+ const SegmentNode* eiPrev = &(*it);
assert(eiPrev);
++it;
for(iterator itEnd = end(); it != itEnd; ++it) {
- SegmentNode* ei = *it;
+ const SegmentNode* ei = &(*it);
assert(ei);
if(! ei->compareTo(*eiPrev)) {
@@ -295,9 +282,9 @@ SegmentNodeList::getSplitCoordinates()
std::unique_ptr<std::vector<Coordinate>> coordList(new std::vector<Coordinate>);
// there should always be at least two entries in the list, since the endpoints are nodes
iterator it = begin();
- SegmentNode* eiPrev = *it;
+ const SegmentNode* eiPrev = &(*it);
for(iterator itEnd = end(); it != itEnd; ++it) {
- SegmentNode* ei = *it;
+ const SegmentNode* ei = &(*it);
addEdgeCoordinates(eiPrev, ei, *coordList);
eiPrev = ei;
}
@@ -323,8 +310,8 @@ operator<< (std::ostream& os, const SegmentNodeList& nlist)
{
os << "Intersections: (" << nlist.nodeMap.size() << "):" << std::endl;
- for(const SegmentNode* ei: nlist.nodeMap) {
- os << " " << *ei;
+ for(const SegmentNode& ei: nlist.nodeMap) {
+ os << " " << ei;
}
return os;
}
-----------------------------------------------------------------------
Summary of changes:
include/geos/noding/Makefile.am | 3 +-
include/geos/noding/NodedSegmentString.h | 35 +---------
include/geos/noding/SegmentNode.h | 18 +++--
.../geos/noding/SegmentNode.inl | 55 ++++-----------
include/geos/noding/SegmentNodeList.h | 73 ++++++++++----------
include/geos/noding/snapround/SnapRoundingNoder.h | 4 +-
src/noding/NodedSegmentString.cpp | 2 +-
src/noding/SegmentNode.cpp | 79 ++++------------------
src/noding/SegmentNodeList.cpp | 68 +++++++++----------
src/noding/snapround/SnapRoundingNoder.cpp | 40 ++++-------
10 files changed, 123 insertions(+), 254 deletions(-)
copy src/noding/SegmentNode.cpp => include/geos/noding/SegmentNode.inl (64%)
hooks/post-receive
--
GEOS
More information about the geos-commits
mailing list