<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2//EN">
<HTML>
<HEAD>
<META HTTP-EQUIV="Content-Type" CONTENT="text/html; charset=iso-8859-1">
<META NAME="Generator" CONTENT="MS Exchange Server version 6.5.7652.24">
<TITLE>More Cascade Union Adventures</TITLE>
</HEAD>
<BODY>
<!-- Converted from text/plain format -->

<P><FONT SIZE=2>Martin,<BR>
<BR>
PostGIS just may beat JTS by cheating a little.  I think I have managed to up one on Kevin's solution by cheating.  One of the PostgreSQL developers pointed out to me that array_append is highly inefficient and testing out the st_geom_accum - that suffers from similar issues.  Watch these tests.  I tested on OpenJump too and got 55 second response.  Of course that was not a fair test since my workstation does not have PostgreSQL on it.  I'll have to wait till later when I'm at a box that has both PostgreSQL and OpenJump installed to do a fair comparison.<BR>
<BR>
I also remarked out the sorting I was doing because it didn't seem to be consistently better in all cases.<BR>
---THE TESTS ---<BR>
--   231,312 ms = 3.85 mins - SELECT 231312/1000.00/60<BR>
SELECT ST_CascadeUnion(the_geom)<BR>
FROM (SELECT * FROM sample_poly) As foo;<BR>
<BR>
--44,453 ms = 45 secs = wow! SELECT 44453/1000.00<BR>
SELECT st_unitecascade_garray_sort(ARRAY(SELECT the_geom FROM sample_poly));<BR>
<BR>
-- 77,078 ms, 75124 ms = 1.26 min<BR>
SELECT ST_NumGeometries(ST_Union(the_geom)) AS the_geom<BR>
FROM (<BR>
   SELECT min(id) AS id, ST_Union(the_geom) AS the_geom<BR>
   FROM (<BR>
     SELECT min(id) AS id, ST_Union(the_geom) AS the_geom<BR>
     FROM (<BR>
       SELECT min(id) AS id, ST_Union(the_geom) AS the_geom<BR>
       FROM (<BR>
         SELECT min(id) AS id, ST_Union(the_geom) AS the_geom<BR>
         FROM (SELECT * FROM sample_poly) As foo<BR>
         GROUP BY round(id/10)<BR>
         ORDER BY id) AS tmp1<BR>
       GROUP BY round(id/100)<BR>
       ORDER BY id) AS tmp2<BR>
     GROUP BY round(id/1000)<BR>
     ORDER BY id) AS tmp3<BR>
   GROUP BY round(id/10000)<BR>
   ORDER BY id) AS tmp4<BR>
GROUP BY round(id/100000);<BR>
<BR>
<BR>
-----THE CODE ---<BR>
<BR>
CREATE OR REPLACE FUNCTION st_unitecascade_garray(geometry[], iter int,<BR>
startcount int)<BR>
  RETURNS geometry AS<BR>
$$<BR>
SELECT CASE WHEN array_upper($1,1) < 5 OR  array_upper($1,1) BETWEEN 0<BR>
AND ln($3 + 1)/ln($2 + 1) THEN st_unite_garray($1) ELSE<BR>
        st_unitecascade_garray(ARRAY(SELECT st_unite_garray($1[i:least(i<BR>
+ CAST(ln($3 + 1)/ln($2 + 1) As int) - 1,array_upper($1,1))]) As geom<BR>
FROM generate_series(1, array_upper($1,1), CAST(ln($3 + 1)/ln($2 + 1) As<BR>
int)) As i), $2 + 1, $3) END<BR>
<BR>
$$<BR>
  LANGUAGE 'sql' IMMUTABLE;<BR>
<BR>
CREATE OR REPLACE FUNCTION st_unitecascade_garray_sort(geometry[])<BR>
  RETURNS geometry AS<BR>
$$<BR>
        SELECT CASE WHEN array_upper($1,1) < 10  THEN<BR>
st_unite_garray($1) ELSE<BR>
                st_unitecascade_garray(ARRAY(SELECT ($1)[s] FROM<BR>
generate_series(1, array_upper($1, 1)) AS s<BR>
                        --ORDER BY ST_SnapToGrid(ST_Centroid(($1)[s]),0.1)<BR>
) , 2, array_upper($1,1)) END;<BR>
$$<BR>
  LANGUAGE 'sql' IMMUTABLE;<BR>
<BR>
--DROP AGGREGATE st_cascadeunion(geometry);<BR>
<BR>
CREATE AGGREGATE st_cascadeunion(geometry) (<BR>
  SFUNC=st_geom_accum,<BR>
  STYPE=geometry[],<BR>
  FINALFUNC=st_unitecascade_garray_sort<BR>
);<BR>
<BR>
<BR>
<BR>
<BR>
--BEGIN TESTS --<BR>
CREATE INDEX idx_sample_poly_the_geom<BR>
  ON sample_poly<BR>
  USING gist<BR>
  (the_geom);<BR>
<BR>
 <BR>
ALTER TABLE sample_poly CLUSTER ON idx_sample_poly_the_geom;<BR>
CLUSTER sample_poly;<BR>
<BR>
<BR>
vacuum analyze sample_poly;<BR>
<BR>
<BR>
Thanks,<BR>
Regina<BR>
<BR>
<BR>
<BR>
<BR>
<BR>
<BR>
<BR>
<BR>
<BR>
<BR>
</FONT>
</P>

</BODY>
</HTML>
<HTML><BODY><P><hr size=1></P>
<P><STRONG>
The substance of this message, including any attachments, may be confidential, legally privileged and/or exempt from disclosure pursuant to Massachusetts law. It is intended solely for the addressee. If you received this in error, please contact the sender and delete the material from any computer.
</STRONG></P></BODY></HTML>

<P><hr size=1></P>
<P><STRONG><font size="2" color="339900"> Help make the earth a greener place. If at all possible resist printing this email and join us in saving paper. </p> <p> </font></STRONG></P>