[geos-commits] [SCM] GEOS branch master updated. e88a488c86273f95a825a3d23cb83651f73d0c9a

git at osgeo.org git at osgeo.org
Thu Jun 20 11:07:44 PDT 2019


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  e88a488c86273f95a825a3d23cb83651f73d0c9a (commit)
       via  52c722871a56d104d9d639584bf4508ae0736b04 (commit)
      from  d924cc7121cca892b1ee550b7cc6e91c6caf34bb (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 e88a488c86273f95a825a3d23cb83651f73d0c9a
Merge: d924cc7 52c7228
Author: Daniel Baston <dbaston at gmail.com>
Date:   Thu Jun 20 14:07:33 2019 -0400

    Merge branch 'geometry-component-uniqueptr'


commit 52c722871a56d104d9d639584bf4508ae0736b04
Author: Daniel Baston <dbaston at gmail.com>
Date:   Mon Jun 17 22:08:35 2019 -0400

    Remove manual memory management from GeometryCollection, Polygon
    
    Have these classes manage their components using a std::vector of
    std::unique_ptr. Avoid heap-allocating the std::vectors themselves.

diff --git a/include/geos/geom/Geometry.h b/include/geos/geom/Geometry.h
index 3bed163..d2754be 100644
--- a/include/geos/geom/Geometry.h
+++ b/include/geos/geom/Geometry.h
@@ -893,6 +893,8 @@ protected:
 
     int compare(std::vector<Geometry*> a, std::vector<Geometry*> b) const;
 
+    int compare(const std::vector<std::unique_ptr<Geometry>> & a, const std::vector<std::unique_ptr<Geometry>> & b) const;
+
     bool equal(const Coordinate& a, const Coordinate& b,
                double tolerance) const;
     int SRID;
diff --git a/include/geos/geom/GeometryCollection.h b/include/geos/geom/GeometryCollection.h
index 001d88d..b1af27c 100644
--- a/include/geos/geom/GeometryCollection.h
+++ b/include/geos/geom/GeometryCollection.h
@@ -57,9 +57,9 @@ class GEOS_DLL GeometryCollection : public virtual Geometry {
 public:
     friend class GeometryFactory;
 
-    typedef std::vector<Geometry*>::const_iterator const_iterator;
+    typedef std::vector<std::unique_ptr<Geometry>>::const_iterator const_iterator;
 
-    typedef std::vector<Geometry*>::iterator iterator;
+    typedef std::vector<std::unique_ptr<Geometry>>::iterator iterator;
 
     const_iterator begin() const;
 
@@ -107,7 +107,7 @@ public:
      */
     Dimension::DimensionType getDimension() const override;
 
-    virtual bool isDimensionStrict(Dimension::DimensionType d) const;
+    bool isDimensionStrict(Dimension::DimensionType d) const override;
 
     /// Returns coordinate dimension.
     int getCoordinateDimension() const override;
@@ -207,7 +207,7 @@ protected:
         return SORTINDEX_GEOMETRYCOLLECTION;
     };
 
-    std::vector<Geometry*>* geometries;
+    std::vector<std::unique_ptr<Geometry>> geometries;
 
     Envelope::Ptr computeEnvelopeInternal() const override;
 
diff --git a/include/geos/geom/GeometryCollection.inl b/include/geos/geom/GeometryCollection.inl
index b6df063..ecabd82 100644
--- a/include/geos/geom/GeometryCollection.inl
+++ b/include/geos/geom/GeometryCollection.inl
@@ -29,13 +29,13 @@ namespace geom { // geos::geom
 INLINE GeometryCollection::const_iterator
 GeometryCollection::begin() const
 {
-    return geometries->begin();
+    return geometries.begin();
 }
 
 INLINE GeometryCollection::const_iterator
 GeometryCollection::end() const
 {
-    return geometries->end();
+    return geometries.end();
 }
 
 
diff --git a/include/geos/geom/Polygon.h b/include/geos/geom/Polygon.h
index 45cbd4e..b4289cd 100644
--- a/include/geos/geom/Polygon.h
+++ b/include/geos/geom/Polygon.h
@@ -171,9 +171,9 @@ protected:
     Polygon(LinearRing* newShell, std::vector<LinearRing*>* newHoles,
             const GeometryFactory* newFactory);
 
-    LinearRing* shell;
+    std::unique_ptr<LinearRing> shell;
 
-    std::vector<LinearRing*>* holes;
+    std::vector<std::unique_ptr<LinearRing>> holes;
 
     Envelope::Ptr computeEnvelopeInternal() const override;
 
diff --git a/src/algorithm/PointLocator.cpp b/src/algorithm/PointLocator.cpp
index 5854f89..889e000 100644
--- a/src/algorithm/PointLocator.cpp
+++ b/src/algorithm/PointLocator.cpp
@@ -94,13 +94,9 @@ PointLocator::computeLocation(const Coordinate& p, const Geometry* geom)
         }
     }
     else if(const GeometryCollection* col = dynamic_cast<const GeometryCollection*>(geom)) {
-        for(GeometryCollection::const_iterator
-                it = col->begin(), endIt = col->end();
-                it != endIt;
-                ++it) {
-            const Geometry* g2 = *it;
-            assert(g2 != geom); // is this check really needed ?
-            computeLocation(p, g2);
+        for(const auto & g2 : *col) {
+            assert(g2.get() != geom); // is this check really needed ?
+            computeLocation(p, g2.get());
         }
     }
 
diff --git a/src/algorithm/locate/SimplePointInAreaLocator.cpp b/src/algorithm/locate/SimplePointInAreaLocator.cpp
index 8affb66..8457873 100644
--- a/src/algorithm/locate/SimplePointInAreaLocator.cpp
+++ b/src/algorithm/locate/SimplePointInAreaLocator.cpp
@@ -70,9 +70,9 @@ SimplePointInAreaLocator::locateInGeometry(const Coordinate& p, const Geometry*
         return Location::EXTERIOR;
     }
     if(const GeometryCollection* col = dynamic_cast<const GeometryCollection*>(geom)) {
-        for(auto g2 : *col) {
-            assert(g2 != geom);
-            Location loc = locateInGeometry(p, g2);
+        for(auto& g2 : *col) {
+            assert(g2.get() != geom);
+            Location loc = locateInGeometry(p, g2.get());
             if(loc != Location::EXTERIOR) {
                 return loc;
             }
diff --git a/src/geom/Geometry.cpp b/src/geom/Geometry.cpp
index a050d0e..823a11f 100644
--- a/src/geom/Geometry.cpp
+++ b/src/geom/Geometry.cpp
@@ -778,6 +778,31 @@ Geometry::compare(vector<Geometry*> a, vector<Geometry*> b) const
     return 0;
 }
 
+int
+Geometry::compare(const std::vector<std::unique_ptr<Geometry>> & a,
+        const std::vector<std::unique_ptr<Geometry>> & b) const
+{
+    size_t i = 0;
+    size_t j = 0;
+    while(i < a.size() && j < b.size()) {
+        Geometry* aGeom = a[i].get();
+        Geometry* bGeom = b[j].get();
+        int comparison = aGeom->compareTo(bGeom);
+        if(comparison != 0) {
+            return comparison;
+        }
+        i++;
+        j++;
+    }
+    if(i < a.size()) {
+        return 1;
+    }
+    if(j < b.size()) {
+        return -1;
+    }
+    return 0;
+}
+
 /**
  *  Returns the minimum distance between this Geometry
  *  and the other Geometry
diff --git a/src/geom/GeometryCollection.cpp b/src/geom/GeometryCollection.cpp
index 40b0c98..a1fcf6b 100644
--- a/src/geom/GeometryCollection.cpp
+++ b/src/geom/GeometryCollection.cpp
@@ -27,6 +27,7 @@
 #include <geos/geom/GeometryFilter.h>
 #include <geos/geom/GeometryComponentFilter.h>
 #include <geos/geom/Envelope.h>
+#include <geos/util.h>
 
 #ifndef GEOS_INLINE
 # include <geos/geom/GeometryCollection.inl>
@@ -36,51 +37,45 @@
 #include <vector>
 #include <memory>
 
-using namespace std;
-
 namespace geos {
 namespace geom { // geos::geom
 
 /*protected*/
 GeometryCollection::GeometryCollection(const GeometryCollection& gc)
     :
-    Geometry(gc)
+    Geometry(gc),
+    geometries(gc.geometries.size())
 {
-    size_t ngeoms = gc.geometries->size();
-
-    geometries = new vector<Geometry*>(ngeoms);
-    for(size_t i = 0; i < ngeoms; ++i) {
-        (*geometries)[i] = (*gc.geometries)[i]->clone().release();
+    for(size_t i = 0; i < geometries.size(); ++i) {
+        geometries[i] = gc.geometries[i]->clone();
     }
 }
 
 /*protected*/
-GeometryCollection::GeometryCollection(vector<Geometry*>* newGeoms, const GeometryFactory* factory):
+GeometryCollection::GeometryCollection(std::vector<Geometry*>* newGeoms, const GeometryFactory* factory):
     Geometry(factory)
 {
     if(newGeoms == nullptr) {
-        geometries = new vector<Geometry*>();
         return;
     }
     if(hasNullElements(newGeoms)) {
         throw  util::IllegalArgumentException("geometries must not contain null elements\n");
-        return;
     }
-    geometries = newGeoms;
+    for (const auto& geom : *newGeoms) {
+        geometries.emplace_back(geom);
+    }
+    delete newGeoms;
 
     // Set SRID for inner geoms
-    size_t ngeoms = geometries->size();
-    for(size_t i = 0; i < ngeoms; ++i) {
-        (*geometries)[i]->setSRID(getSRID());
-    }
+    setSRID(getSRID());
 }
 
 void
 GeometryCollection::setSRID(int newSRID)
 {
     Geometry::setSRID(newSRID);
-    for(size_t i = 0; i < geometries->size(); i++) {
-        (*geometries)[i]->setSRID(newSRID);
+    for(auto& g : geometries) {
+        g->setSRID(newSRID);
     }
 }
 
@@ -93,25 +88,25 @@ GeometryCollection::setSRID(int newSRID)
 std::unique_ptr<CoordinateSequence>
 GeometryCollection::getCoordinates() const
 {
-    vector<Coordinate>* coordinates = new vector<Coordinate>(getNumPoints());
+    auto coordinates = detail::make_unique<std::vector<Coordinate>>(getNumPoints());
 
-    int k = -1;
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        auto childCoordinates = (*geometries)[i]->getCoordinates();
+    size_t k = 0;
+    for(const auto& g : geometries) {
+        auto childCoordinates = g->getCoordinates(); // TODO avoid this copy
         size_t npts = childCoordinates->getSize();
         for(size_t j = 0; j < npts; ++j) {
-            k++;
             (*coordinates)[k] = childCoordinates->getAt(j);
+            k++;
         }
     }
-    return CoordinateArraySequenceFactory::instance()->create(coordinates);
+    return CoordinateArraySequenceFactory::instance()->create(coordinates.release());
 }
 
 bool
 GeometryCollection::isEmpty() const
 {
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        if(!(*geometries)[i]->isEmpty()) {
+    for(const auto& g : geometries) {
+        if(!g->isEmpty()) {
             return false;
         }
     }
@@ -122,16 +117,16 @@ Dimension::DimensionType
 GeometryCollection::getDimension() const
 {
     Dimension::DimensionType dimension = Dimension::False;
-    for(size_t i = 0, n = geometries->size(); i < n; ++i) {
-        dimension = max(dimension, (*geometries)[i]->getDimension());
+    for(const auto& g : geometries) {
+        dimension = std::max(dimension, g->getDimension());
     }
     return dimension;
 }
 
 bool
 GeometryCollection::isDimensionStrict(Dimension::DimensionType d) const {
-    return std::all_of(geometries->begin(), geometries->end(),
-            [&d](const Geometry* g) {
+    return std::all_of(geometries.begin(), geometries.end(),
+            [&d](const std::unique_ptr<Geometry> & g) {
                 return g->getDimension() == d;
             });
 }
@@ -140,8 +135,8 @@ int
 GeometryCollection::getBoundaryDimension() const
 {
     int dimension = Dimension::False;
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        dimension = max(dimension, (*geometries)[i]->getBoundaryDimension());
+    for(const auto& g : geometries) {
+        dimension = std::max(dimension, g->getBoundaryDimension());
     }
     return dimension;
 }
@@ -151,8 +146,8 @@ GeometryCollection::getCoordinateDimension() const
 {
     int dimension = 2;
 
-    for(size_t i = 0, n = geometries->size(); i < n; ++i) {
-        dimension = max(dimension, (*geometries)[i]->getCoordinateDimension());
+    for(const auto& g : geometries) {
+        dimension = std::max(dimension, g->getCoordinateDimension());
     }
     return dimension;
 }
@@ -160,26 +155,26 @@ GeometryCollection::getCoordinateDimension() const
 size_t
 GeometryCollection::getNumGeometries() const
 {
-    return geometries->size();
+    return geometries.size();
 }
 
 const Geometry*
 GeometryCollection::getGeometryN(size_t n) const
 {
-    return (*geometries)[n];
+    return geometries[n].get();
 }
 
 size_t
 GeometryCollection::getNumPoints() const
 {
     size_t numPoints = 0;
-    for(size_t i = 0, n = geometries->size(); i < n; ++i) {
-        numPoints += (*geometries)[i]->getNumPoints();
+    for(const auto& g : geometries) {
+        numPoints += g->getNumPoints();
     }
     return numPoints;
 }
 
-string
+std::string
 GeometryCollection::getGeometryType() const
 {
     return "GeometryCollection";
@@ -203,11 +198,11 @@ GeometryCollection::equalsExact(const Geometry* other, double tolerance) const
         return false;
     }
 
-    if(geometries->size() != otherCollection->geometries->size()) {
+    if(geometries.size() != otherCollection->geometries.size()) {
         return false;
     }
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        if(!((*geometries)[i]->equalsExact((*(otherCollection->geometries))[i], tolerance))) {
+    for(size_t i = 0; i < geometries.size(); ++i) {
+        if(!(geometries[i]->equalsExact(otherCollection->geometries[i].get(), tolerance))) {
             return false;
         }
     }
@@ -217,16 +212,16 @@ GeometryCollection::equalsExact(const Geometry* other, double tolerance) const
 void
 GeometryCollection::apply_rw(const CoordinateFilter* filter)
 {
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        (*geometries)[i]->apply_rw(filter);
+    for(auto& g : geometries) {
+        g->apply_rw(filter);
     }
 }
 
 void
 GeometryCollection::apply_ro(CoordinateFilter* filter) const
 {
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        (*geometries)[i]->apply_ro(filter);
+    for(const auto& g : geometries) {
+        g->apply_ro(filter);
     }
 }
 
@@ -234,8 +229,8 @@ void
 GeometryCollection::apply_ro(GeometryFilter* filter) const
 {
     filter->filter_ro(this);
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        (*geometries)[i]->apply_ro(filter);
+    for(const auto& g : geometries) {
+        g->apply_ro(filter);
     }
 }
 
@@ -243,26 +238,28 @@ void
 GeometryCollection::apply_rw(GeometryFilter* filter)
 {
     filter->filter_rw(this);
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        (*geometries)[i]->apply_rw(filter);
+    for(auto& g : geometries) {
+        g->apply_rw(filter);
     }
 }
 
 void
 GeometryCollection::normalize()
 {
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        (*geometries)[i]->normalize();
+    for(auto& g : geometries) {
+        g->normalize();
     }
-    sort(geometries->begin(), geometries->end(), GeometryGreaterThen());
+    std::sort(geometries.begin(), geometries.end(), [](const std::unique_ptr<Geometry> & a, const std::unique_ptr<Geometry> & b) {
+        return a->compareTo(b.get()) > 0;
+    });
 }
 
 Envelope::Ptr
 GeometryCollection::computeEnvelopeInternal() const
 {
     Envelope::Ptr p_envelope(new Envelope());
-    for(size_t i = 0; i < geometries->size(); i++) {
-        const Envelope* env = (*geometries)[i]->getEnvelopeInternal();
+    for(const auto& g : geometries) {
+        const Envelope* env = g->getEnvelopeInternal();
         p_envelope->expandToInclude(env);
     }
     return p_envelope;
@@ -272,15 +269,15 @@ int
 GeometryCollection::compareToSameClass(const Geometry* g) const
 {
     const GeometryCollection* gc = dynamic_cast<const GeometryCollection*>(g);
-    return compare(*geometries, *(gc->geometries));
+    return compare(geometries, gc->geometries);
 }
 
 const Coordinate*
 GeometryCollection::getCoordinate() const
 {
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        if(!(*geometries)[i]->isEmpty()) {
-            return (*geometries)[i]->getCoordinate();
+    for(const auto& g : geometries) {
+        if(!g->isEmpty()) {
+            return g->getCoordinate();
         }
     }
     return nullptr;
@@ -293,8 +290,8 @@ double
 GeometryCollection::getArea() const
 {
     double area = 0.0;
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        area += (*geometries)[i]->getArea();
+    for(const auto& g : geometries) {
+        area += g->getArea();
     }
     return area;
 }
@@ -306,8 +303,8 @@ double
 GeometryCollection::getLength() const
 {
     double sum = 0.0;
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        sum += (*geometries)[i]->getLength();
+    for(const auto& g : geometries) {
+        sum += g->getLength();
     }
     return sum;
 }
@@ -316,8 +313,11 @@ void
 GeometryCollection::apply_rw(GeometryComponentFilter* filter)
 {
     filter->filter_rw(this);
-    for(size_t i = 0; i < geometries->size() && !filter->isDone(); ++i) {
-        (*geometries)[i]->apply_rw(filter);
+    for(auto& g : geometries) {
+        if (filter->isDone()) {
+            return;
+        }
+        g->apply_rw(filter);
     }
 }
 
@@ -325,20 +325,19 @@ void
 GeometryCollection::apply_ro(GeometryComponentFilter* filter) const
 {
     filter->filter_ro(this);
-    for(size_t i = 0; i < geometries->size() && !filter->isDone(); ++i) {
-        (*geometries)[i]->apply_ro(filter);
+    for(const auto& g : geometries) {
+        if (filter->isDone()) {
+            return;
+        }
+        g->apply_ro(filter);
     }
 }
 
 void
 GeometryCollection::apply_rw(CoordinateSequenceFilter& filter)
 {
-    size_t ngeoms = geometries->size();
-    if(ngeoms == 0) {
-        return;
-    }
-    for(size_t i = 0; i < ngeoms; ++i) {
-        (*geometries)[i]->apply_rw(filter);
+    for(auto& g : geometries) {
+        g->apply_rw(filter);
         if(filter.isDone()) {
             break;
         }
@@ -351,12 +350,8 @@ GeometryCollection::apply_rw(CoordinateSequenceFilter& filter)
 void
 GeometryCollection::apply_ro(CoordinateSequenceFilter& filter) const
 {
-    size_t ngeoms = geometries->size();
-    if(ngeoms == 0) {
-        return;
-    }
-    for(size_t i = 0; i < ngeoms; ++i) {
-        (*geometries)[i]->apply_ro(filter);
+    for(const auto& g : geometries) {
+        g->apply_ro(filter);
         if(filter.isDone()) {
             break;
         }
@@ -366,13 +361,7 @@ GeometryCollection::apply_ro(CoordinateSequenceFilter& filter) const
     //if (filter.isGeometryChanged()) geometryChanged();
 }
 
-GeometryCollection::~GeometryCollection()
-{
-    for(size_t i = 0; i < geometries->size(); ++i) {
-        delete(*geometries)[i];
-    }
-    delete geometries;
-}
+GeometryCollection::~GeometryCollection() = default;
 
 GeometryTypeId
 GeometryCollection::getGeometryTypeId() const
@@ -387,12 +376,12 @@ GeometryCollection::reverse() const
         return clone();
     }
 
-    auto* reversed = new std::vector<Geometry*> {geometries->size()};
+    auto* reversed = new std::vector<Geometry*> {geometries.size()};
 
-    std::transform(geometries->begin(),
-                   geometries->end(),
+    std::transform(geometries.begin(),
+                   geometries.end(),
                    reversed->begin(),
-    [](const Geometry * g) {
+    [](const std::unique_ptr<Geometry> & g) {
         return g->reverse().release();
     });
 
diff --git a/src/geom/MultiLineString.cpp b/src/geom/MultiLineString.cpp
index f32ff30..bc909ed 100644
--- a/src/geom/MultiLineString.cpp
+++ b/src/geom/MultiLineString.cpp
@@ -77,8 +77,8 @@ MultiLineString::isClosed() const
     if(isEmpty()) {
         return false;
     }
-    for(size_t i = 0, n = geometries->size(); i < n; ++i) {
-        LineString* ls = dynamic_cast<LineString*>((*geometries)[i]);
+    for(const auto& g : geometries) {
+        LineString* ls = dynamic_cast<LineString*>(g.get());
         if(! ls->isClosed()) {
             return false;
         }
@@ -119,10 +119,10 @@ MultiLineString::reverse() const
         return clone();
     }
 
-    size_t nLines = geometries->size();
+    size_t nLines = geometries.size();
     Geometry::NonConstVect* revLines = new Geometry::NonConstVect(nLines);
     for(size_t i = 0; i < nLines; ++i) {
-        LineString* iLS = dynamic_cast<LineString*>((*geometries)[i]);
+        LineString* iLS = dynamic_cast<LineString*>(geometries[i].get());
         assert(iLS);
         (*revLines)[nLines - 1 - i] = iLS->reverse().release();
     }
diff --git a/src/geom/MultiPoint.cpp b/src/geom/MultiPoint.cpp
index ebc28f3..ba6ddb2 100644
--- a/src/geom/MultiPoint.cpp
+++ b/src/geom/MultiPoint.cpp
@@ -78,7 +78,7 @@ MultiPoint::equalsExact(const Geometry* other, double tolerance) const
 const Coordinate*
 MultiPoint::getCoordinateN(size_t n) const
 {
-    return ((*geometries)[n])->getCoordinate();
+    return geometries[n]->getCoordinate();
 }
 GeometryTypeId
 MultiPoint::getGeometryTypeId() const
diff --git a/src/geom/MultiPolygon.cpp b/src/geom/MultiPolygon.cpp
index 2d57353..cfaa121 100644
--- a/src/geom/MultiPolygon.cpp
+++ b/src/geom/MultiPolygon.cpp
@@ -72,8 +72,8 @@ MultiPolygon::getBoundary() const
         return std::unique_ptr<Geometry>(getFactory()->createMultiLineString());
     }
     vector<Geometry*>* allRings = new vector<Geometry*>();
-    for(size_t i = 0; i < geometries->size(); i++) {
-        Polygon* pg = dynamic_cast<Polygon*>((*geometries)[i]);
+    for(size_t i = 0; i < geometries.size(); i++) {
+        Polygon* pg = dynamic_cast<Polygon*>(geometries[i].get());
         assert(pg);
         auto g = pg->getBoundary();
         if(LineString* ls = dynamic_cast<LineString*>(g.get())) {
@@ -115,12 +115,12 @@ MultiPolygon::reverse() const
         return clone();
     }
 
-    auto* reversed = new std::vector<Geometry*> {geometries->size()};
+    auto* reversed = new std::vector<Geometry*> {geometries.size()};
 
-    std::transform(geometries->begin(),
-                   geometries->end(),
+    std::transform(geometries.begin(),
+                   geometries.end(),
                    reversed->begin(),
-    [](const Geometry * g) {
+    [](const std::unique_ptr<Geometry> & g) {
         return g->reverse().release();
     });
 
diff --git a/src/geom/Polygon.cpp b/src/geom/Polygon.cpp
index 99b0685..612f039 100644
--- a/src/geom/Polygon.cpp
+++ b/src/geom/Polygon.cpp
@@ -44,7 +44,6 @@
 #define GEOS_DEBUG 0
 #endif
 
-using namespace std;
 //using namespace geos::algorithm;
 
 namespace geos {
@@ -53,44 +52,38 @@ namespace geom { // geos::geom
 /*protected*/
 Polygon::Polygon(const Polygon& p)
     :
-    Geometry(p)
+    Geometry(p),
+    shell(detail::make_unique<LinearRing>(*p.shell)),
+    holes(p.holes.size())
 {
-    shell = new LinearRing(*p.shell);
-    size_t nholes = p.holes->size();
-    holes = new vector<LinearRing*>(nholes);
-    for(size_t i = 0; i < nholes; ++i) {
-        LinearRing* h = new LinearRing(*(*p.holes)[i]);
-        (*holes)[i] = h;
+    for(size_t i = 0; i < holes.size(); ++i) {
+        holes[i] = detail::make_unique<LinearRing>(*p.holes[i]);
     }
 }
 
 /*protected*/
-Polygon::Polygon(LinearRing* newShell, vector<LinearRing*>* newHoles,
+Polygon::Polygon(LinearRing* newShell, std::vector<LinearRing*>* newHoles,
                  const GeometryFactory* newFactory):
     Geometry(newFactory)
 {
     if(newShell == nullptr) {
-        shell = getFactory()->createLinearRing(nullptr);
+        shell.reset(getFactory()->createLinearRing(nullptr));
     }
     else {
         if(newHoles != nullptr && newShell->isEmpty() && hasNonEmptyElements(newHoles)) {
             throw util::IllegalArgumentException("shell is empty but holes are not");
         }
-        shell = newShell;
+        shell.reset(newShell);
     }
 
-    if(newHoles == nullptr) {
-        holes = new vector<LinearRing*>();
-    }
-    else {
+    if(newHoles != nullptr) {
         if(hasNullElements(newHoles)) {
             throw util::IllegalArgumentException("holes must not contain null elements");
         }
-        for(size_t i = 0; i < newHoles->size(); i++)
-            if((*newHoles)[i]->getGeometryTypeId() != GEOS_LINEARRING) {
-                throw util::IllegalArgumentException("holes must be LinearRings");
-            }
-        holes = newHoles;
+        for (const auto& hole : *newHoles) {
+            holes.emplace_back(hole);
+        }
+        delete newHoles;
     }
 }
 
@@ -101,7 +94,7 @@ Polygon::getCoordinates() const
         return getFactory()->getCoordinateSequenceFactory()->create();
     }
 
-    vector<Coordinate>* cl = new vector<Coordinate>;
+    std::vector<Coordinate>* cl = new std::vector<Coordinate>;
 
     // reserve space in the vector for all the polygon points
     cl->reserve(getNumPoints());
@@ -111,10 +104,8 @@ Polygon::getCoordinates() const
     shellCoords->toVector(*cl);
 
     // Add holes points
-    size_t nholes = holes->size();
-    for(size_t i = 0; i < nholes; ++i) {
-        const LinearRing* lr = (*holes)[i];
-        const CoordinateSequence* childCoords = lr->getCoordinatesRO();
+    for(const auto& hole : holes) {
+        const CoordinateSequence* childCoords = hole->getCoordinatesRO();
         childCoords->toVector(*cl);
     }
 
@@ -125,7 +116,7 @@ size_t
 Polygon::getNumPoints() const
 {
     size_t numPoints = shell->getNumPoints();
-    for(const LinearRing* lr : *holes) {
+    for(const auto& lr : holes) {
         numPoints += lr->getNumPoints();
     }
     return numPoints;
@@ -143,12 +134,11 @@ Polygon::getCoordinateDimension() const
     int dimension = 2;
 
     if(shell != nullptr) {
-        dimension = max(dimension, shell->getCoordinateDimension());
+        dimension = std::max(dimension, shell->getCoordinateDimension());
     }
 
-    size_t nholes = holes->size();
-    for(size_t i = 0; i < nholes; ++i) {
-        dimension = max(dimension, (*holes)[i]->getCoordinateDimension());
+    for(const auto& hole : holes) {
+        dimension = std::max(dimension, hole->getCoordinateDimension());
     }
 
     return dimension;
@@ -169,22 +159,22 @@ Polygon::isEmpty() const
 const LinearRing*
 Polygon::getExteriorRing() const
 {
-    return shell;
+    return shell.get();
 }
 
 size_t
 Polygon::getNumInteriorRing() const
 {
-    return holes->size();
+    return holes.size();
 }
 
 const LinearRing*
 Polygon::getInteriorRingN(size_t n) const
 {
-    return (*holes)[n];
+    return holes[n].get();
 }
 
-string
+std::string
 Polygon::getGeometryType() const
 {
     return "Polygon";
@@ -207,15 +197,15 @@ Polygon::getBoundary() const
         return std::unique_ptr<Geometry>(gf->createMultiLineString());
     }
 
-    if(! holes->size()) {
-        return std::unique_ptr<Geometry>(gf->createLineString(*shell).release());
+    if(holes.empty()) {
+        return std::unique_ptr<Geometry>(gf->createLineString(*shell));
     }
 
-    vector<Geometry*>* rings = new vector<Geometry*>(holes->size() + 1);
+    std::vector<Geometry*>* rings = new std::vector<Geometry*>(holes.size() + 1);
 
     (*rings)[0] = gf->createLineString(*shell).release();
-    for(size_t i = 0, n = holes->size(); i < n; ++i) {
-        const LinearRing* hole = (*holes)[i];
+    for(size_t i = 0, n = holes.size(); i < n; ++i) {
+        const LinearRing* hole = holes[i].get();
         assert(hole);
         LineString* ls = gf->createLineString(*hole).release();
         (*rings)[i + 1] = ls;
@@ -238,19 +228,19 @@ Polygon::equalsExact(const Geometry* other, double tolerance) const
         return false;
     }
 
-    if(!shell->equalsExact(otherPolygon->shell, tolerance)) {
+    if(!shell->equalsExact(otherPolygon->shell.get(), tolerance)) {
         return false;
     }
 
-    size_t nholes = holes->size();
+    size_t nholes = holes.size();
 
-    if(nholes != otherPolygon->holes->size()) {
+    if(nholes != otherPolygon->holes.size()) {
         return false;
     }
 
     for(size_t i = 0; i < nholes; i++) {
-        const Geometry* hole = (*holes)[i];
-        const Geometry* otherhole = (*(otherPolygon->holes))[i];
+        const LinearRing* hole = holes[i].get();
+        const LinearRing* otherhole = otherPolygon->holes[i].get();
         if(!hole->equalsExact(otherhole, tolerance)) {
             return false;
         }
@@ -263,7 +253,7 @@ void
 Polygon::apply_ro(CoordinateFilter* filter) const
 {
     shell->apply_ro(filter);
-    for(const LinearRing* lr : *holes) {
+    for(const auto& lr : holes) {
         lr->apply_ro(filter);
     }
 }
@@ -272,7 +262,7 @@ void
 Polygon::apply_rw(const CoordinateFilter* filter)
 {
     shell->apply_rw(filter);
-    for(LinearRing* lr : *holes) {
+    for(auto& lr : holes) {
         lr->apply_rw(filter);
     }
 }
@@ -298,18 +288,20 @@ Polygon::convexHull() const
 void
 Polygon::normalize()
 {
-    normalize(shell, true);
-    for(LinearRing* lr : *holes) {
-        normalize(lr, false);
+    normalize(shell.get(), true);
+    for(auto& lr : holes) {
+        normalize(lr.get(), false);
     }
-    sort(holes->begin(), holes->end(), GeometryGreaterThen());
+    std::sort(holes.begin(), holes.end(), [](const std::unique_ptr<LinearRing> & a, const std::unique_ptr<LinearRing> & b) {
+        return a->compareTo(b.get()) > 0;
+    });
 }
 
 int
 Polygon::compareToSameClass(const Geometry* g) const
 {
     const Polygon* p = dynamic_cast<const Polygon*>(g);
-    return shell->compareToSameClass(p->shell);
+    return shell->compareToSameClass(p->shell.get());
 }
 
 /*
@@ -354,10 +346,10 @@ double
 Polygon::getArea() const
 {
     double area = 0.0;
-    area += fabs(algorithm::Area::ofRing(shell->getCoordinatesRO()));
-    for(const LinearRing* lr : *holes) {
+    area += algorithm::Area::ofRing(shell->getCoordinatesRO());
+    for(const auto& lr : holes) {
         const CoordinateSequence* h = lr->getCoordinatesRO();
-        area -= fabs(algorithm::Area::ofRing(h));
+        area -= algorithm::Area::ofRing(h);
     }
     return area;
 }
@@ -372,8 +364,8 @@ Polygon::getLength() const
 {
     double len = 0.0;
     len += shell->getLength();
-    for(size_t i = 0, n = holes->size(); i < n; ++i) {
-        len += (*holes)[i]->getLength();
+    for(const auto& hole : holes) {
+        len += hole->getLength();
     }
     return len;
 }
@@ -383,8 +375,8 @@ Polygon::apply_ro(GeometryComponentFilter* filter) const
 {
     filter->filter_ro(this);
     shell->apply_ro(filter);
-    for(size_t i = 0, n = holes->size(); i < n && !filter->isDone(); ++i) {
-        (*holes)[i]->apply_ro(filter);
+    for(size_t i = 0, n = holes.size(); i < n && !filter->isDone(); ++i) {
+        holes[i]->apply_ro(filter);
     }
 }
 
@@ -393,8 +385,8 @@ Polygon::apply_rw(GeometryComponentFilter* filter)
 {
     filter->filter_rw(this);
     shell->apply_rw(filter);
-    for(size_t i = 0, n = holes->size(); i < n && !filter->isDone(); ++i) {
-        (*holes)[i]->apply_rw(filter);
+    for(size_t i = 0, n = holes.size(); i < n && !filter->isDone(); ++i) {
+        holes[i]->apply_rw(filter);
     }
 }
 
@@ -404,8 +396,8 @@ Polygon::apply_rw(CoordinateSequenceFilter& filter)
     shell->apply_rw(filter);
 
     if(! filter.isDone()) {
-        for(size_t i = 0, n = holes->size(); i < n; ++i) {
-            (*holes)[i]->apply_rw(filter);
+        for(size_t i = 0, n = holes.size(); i < n; ++i) {
+            holes[i]->apply_rw(filter);
             if(filter.isDone()) {
                 break;
             }
@@ -422,8 +414,8 @@ Polygon::apply_ro(CoordinateSequenceFilter& filter) const
     shell->apply_ro(filter);
 
     if(! filter.isDone()) {
-        for(size_t i = 0, n = holes->size(); i < n; ++i) {
-            (*holes)[i]->apply_ro(filter);
+        for(size_t i = 0, n = holes.size(); i < n; ++i) {
+            holes[i]->apply_ro(filter);
             if(filter.isDone()) {
                 break;
             }
@@ -432,14 +424,7 @@ Polygon::apply_ro(CoordinateSequenceFilter& filter) const
     //if (filter.isGeometryChanged()) geometryChanged();
 }
 
-Polygon::~Polygon()
-{
-    delete shell;
-    for(size_t i = 0, n = holes->size(); i < n; ++i) {
-        delete(*holes)[i];
-    }
-    delete holes;
-}
+Polygon::~Polygon() = default;
 
 GeometryTypeId
 Polygon::getGeometryTypeId() const
@@ -498,12 +483,12 @@ Polygon::reverse() const
     }
 
     auto* exteriorRingReversed = dynamic_cast<LinearRing*>(shell->reverse().release());
-    auto* interiorRingsReversed = new std::vector<LinearRing*> {holes->size()};
+    auto* interiorRingsReversed = new std::vector<LinearRing*> {holes.size()};
 
-    std::transform(holes->begin(),
-                   holes->end(),
+    std::transform(holes.begin(),
+                   holes.end(),
                    interiorRingsReversed->begin(),
-    [](const Geometry * g) {
+    [](const std::unique_ptr<LinearRing> & g) {
         return dynamic_cast<LinearRing*>(g->reverse().release());
     });
 
diff --git a/src/operation/IsSimpleOp.cpp b/src/operation/IsSimpleOp.cpp
index 03c1fd5..c808f8c 100644
--- a/src/operation/IsSimpleOp.cpp
+++ b/src/operation/IsSimpleOp.cpp
@@ -263,10 +263,8 @@ IsSimpleOp::computeSimple(const geom::Geometry* g)
 bool
 IsSimpleOp::isSimpleGeometryCollection(const geom::GeometryCollection* col)
 {
-    GeometryCollection::const_iterator it;
-    for(it = col->begin(); it < col->end(); ++it) {
-        const geom::Geometry* g = *it;
-        if(!computeSimple(g)) {
+    for(const auto& g : *col) {
+        if(!computeSimple(g.get())) {
             return false;
         }
     }
diff --git a/src/operation/union/CascadedPolygonUnion.cpp b/src/operation/union/CascadedPolygonUnion.cpp
index 9198242..7016f03 100644
--- a/src/operation/union/CascadedPolygonUnion.cpp
+++ b/src/operation/union/CascadedPolygonUnion.cpp
@@ -118,10 +118,8 @@ CascadedPolygonUnion::Union(const geom::MultiPolygon* multipoly)
 {
     std::vector<geom::Polygon*> polys;
 
-    typedef geom::MultiPolygon::const_iterator iterator;
-    iterator end = multipoly->end();
-    for(iterator i = multipoly->begin(); i != end; ++i) {
-        polys.push_back(dynamic_cast<geom::Polygon*>(*i));
+    for(const auto& g : *multipoly) {
+        polys.push_back(dynamic_cast<geom::Polygon*>(g.get()));
     }
 
     CascadedPolygonUnion op(&polys);
diff --git a/src/operation/valid/MakeValid.cpp b/src/operation/valid/MakeValid.cpp
index b10ea95..90f9b62 100644
--- a/src/operation/valid/MakeValid.cpp
+++ b/src/operation/valid/MakeValid.cpp
@@ -96,8 +96,8 @@ static std::unique_ptr<geom::Geometry> MakeValidMultiLine(const geom::MultiLineS
     std::vector<std::unique_ptr<geom::Geometry>> points;
     std::vector<std::unique_ptr<geom::Geometry>> lines;
 
-    for(const auto subgeom: *mls) {
-        auto line = dynamic_cast<const geom::LineString*>(subgeom);
+    for(const auto& subgeom: *mls) {
+        auto line = dynamic_cast<const geom::LineString*>(subgeom.get());
         assert(line);
         auto validSubGeom = MakeValidLine(line);
         if( !validSubGeom || validSubGeom->isEmpty() ) {
@@ -111,7 +111,7 @@ static std::unique_ptr<geom::Geometry> MakeValidMultiLine(const geom::MultiLineS
             lines.emplace_back(std::move(validSubGeom));
         } else if( validLineType == GEOS_MULTILINESTRING ) {
             auto mlsValid = dynamic_cast<const geom::MultiLineString*>(validSubGeom.get());
-            for(const auto subgeomMlsValid: *mlsValid) {
+            for(const auto& subgeomMlsValid: *mlsValid) {
                 lines.emplace_back(subgeomMlsValid->clone());
             }
         } else {
@@ -290,9 +290,9 @@ static std::unique_ptr<geom::Geometry> MakeValidCollection(const geom::GeometryC
 {
     auto validGeoms = new std::vector<geom::Geometry*>();
     try {
-        for( auto geom: *coll )
+        for(const auto& geom: *coll )
         {
-            validGeoms->push_back(MakeValid().build(geom).release());
+            validGeoms->push_back(MakeValid().build(geom.get()).release());
         }
         return std::unique_ptr<geom::Geometry>(
             GeometryFactory::create()->createGeometryCollection(validGeoms));

-----------------------------------------------------------------------

Summary of changes:
 include/geos/geom/Geometry.h                      |   2 +
 include/geos/geom/GeometryCollection.h            |   8 +-
 include/geos/geom/GeometryCollection.inl          |   4 +-
 include/geos/geom/Polygon.h                       |   4 +-
 src/algorithm/PointLocator.cpp                    |  10 +-
 src/algorithm/locate/SimplePointInAreaLocator.cpp |   6 +-
 src/geom/Geometry.cpp                             |  25 ++++
 src/geom/GeometryCollection.cpp                   | 169 ++++++++++------------
 src/geom/MultiLineString.cpp                      |   8 +-
 src/geom/MultiPoint.cpp                           |   2 +-
 src/geom/MultiPolygon.cpp                         |  12 +-
 src/geom/Polygon.cpp                              | 137 ++++++++----------
 src/operation/IsSimpleOp.cpp                      |   6 +-
 src/operation/union/CascadedPolygonUnion.cpp      |   6 +-
 src/operation/valid/MakeValid.cpp                 |  10 +-
 15 files changed, 201 insertions(+), 208 deletions(-)


hooks/post-receive
-- 
GEOS


More information about the geos-commits mailing list