]> granicus.if.org Git - postgresql/commitdiff
Change planner to use the current true disk file size as its estimate of
authorTom Lane <tgl@sss.pgh.pa.us>
Wed, 1 Dec 2004 19:00:56 +0000 (19:00 +0000)
committerTom Lane <tgl@sss.pgh.pa.us>
Wed, 1 Dec 2004 19:00:56 +0000 (19:00 +0000)
a relation's number of blocks, rather than the possibly-obsolete value
in pg_class.relpages.  Scale the value in pg_class.reltuples correspondingly
to arrive at a hopefully more accurate number of rows.  When pg_class
contains 0/0, estimate a tuple width from the column datatypes and divide
that into current file size to estimate number of rows.  This improved
methodology allows us to jettison the ancient hacks that put bogus default
values into pg_class when a table is first created.  Also, per a suggestion
from Simon, make VACUUM (but not VACUUM FULL or ANALYZE) adjust the value
it puts into pg_class.reltuples to try to represent the mean tuple density
instead of the minimal density that actually prevails just after VACUUM.
These changes alter the plans selected for certain regression tests, so
update the expected files accordingly.  (I removed join_1.out because
it's not clear if it still applies; we can add back any variant versions
as they are shown to be needed.)

18 files changed:
doc/src/sgml/catalogs.sgml
doc/src/sgml/diskusage.sgml
doc/src/sgml/perform.sgml
doc/src/sgml/release.sgml
src/backend/access/nbtree/nbtree.c
src/backend/catalog/heap.c
src/backend/catalog/index.c
src/backend/commands/vacuum.c
src/backend/commands/vacuumlazy.c
src/backend/optimizer/util/plancat.c
src/backend/optimizer/util/relnode.c
src/include/access/genam.h
src/include/nodes/relation.h
src/test/regress/expected/case.out
src/test/regress/expected/inherit.out
src/test/regress/expected/join.out
src/test/regress/expected/join_1.out [deleted file]
src/test/regress/expected/polymorphism.out

index f7335323fb46df80bab6cfcff759a631f9d5ce94..92382c620a50c07e595e98bcddf4c11bdcce623f 100644 (file)
@@ -1,6 +1,6 @@
 <!--
  Documentation of the system catalogs, directed toward PostgreSQL developers
- $PostgreSQL: pgsql/doc/src/sgml/catalogs.sgml,v 2.92 2004/11/15 06:32:13 neilc Exp $
+ $PostgreSQL: pgsql/doc/src/sgml/catalogs.sgml,v 2.93 2004/12/01 19:00:27 tgl Exp $
  -->
 
 <chapter id="catalogs">
       <entry><type>int4</type></entry>
       <entry></entry>
       <entry>
-       Size of the on-disk representation of this table in pages (size
+       Size of the on-disk representation of this table in pages (of size
        <symbol>BLCKSZ</symbol>).
        This is only an estimate used by the planner.
        It is updated by <command>VACUUM</command>,
-       <command>ANALYZE</command>, and <command>CREATE INDEX</command>.
+       <command>ANALYZE</command>, and a few DDL commands
+       such as <command>CREATE INDEX</command>.
       </entry>
      </row>
 
        Number of rows in the table.
        This is only an estimate used by the planner.
        It is updated by <command>VACUUM</command>,
-       <command>ANALYZE</command>, and <command>CREATE INDEX</command>.
+       <command>ANALYZE</command>, and a few DDL commands
+       such as <command>CREATE INDEX</command>.
       </entry>
      </row>
 
index ce09f7bc9788b19563633f534c7f15ffe80d1ad6..215519bc2704e1be7f81eb503206b7b69467121e 100644 (file)
@@ -1,5 +1,5 @@
 <!--
-$PostgreSQL: pgsql/doc/src/sgml/diskusage.sgml,v 1.11 2004/06/21 04:06:03 tgl Exp $
+$PostgreSQL: pgsql/doc/src/sgml/diskusage.sgml,v 1.12 2004/12/01 19:00:27 tgl Exp $
 -->
 
 <chapter id="diskusage">
@@ -7,11 +7,7 @@ $PostgreSQL: pgsql/doc/src/sgml/diskusage.sgml,v 1.11 2004/06/21 04:06:03 tgl Ex
 
  <para>
   This chapter discusses how to monitor the disk usage of a
-  <productname>PostgreSQL</> database system.  In the current
-  release, the database administrator does not have much control over
-  the on-disk storage layout, so this chapter is mostly informative
-  and can give you some ideas how to manage the disk usage with
-  operating system tools.
+  <productname>PostgreSQL</> database system.
  </para>
 
  <sect1 id="disk-usage">
@@ -23,11 +19,12 @@ $PostgreSQL: pgsql/doc/src/sgml/diskusage.sgml,v 1.11 2004/06/21 04:06:03 tgl Ex
 
   <para>
    Each table has a primary heap disk file where most of the data is
-   stored. To store long column values, there is also a
-   <acronym>TOAST</> file associated with the table, named based on the
-   table's OID (actually <literal>pg_class.relfilenode</>), and an index on the
-   <acronym>TOAST</> table. There also may be indexes associated with
-   the base table.
+   stored. If the table has any columns with potentially-wide values,
+   there is also a <acronym>TOAST</> file associated with the table,
+   which is used to store values too wide to fit comfortably in the main
+   table.  There will be one index on the
+   <acronym>TOAST</> table, if present. There may also be indexes associated
+   with the base table.
   </para>
 
   <para>
@@ -45,18 +42,24 @@ SELECT relfilenode, relpages FROM pg_class WHERE relname = 'customer';
        16806 |       60
 (1 row)
 </programlisting>
-   Each page is typically 8 kilobytes. (Remember, <literal>relpages</>
-   is only updated by <command>VACUUM</> and <command>ANALYZE</>.)
+   Each page is typically 8 kilobytes. (Remember, <structfield>relpages</>
+   is only updated by <command>VACUUM</>, <command>ANALYZE</>, and
+   a few DDL commands such as <command>CREATE INDEX</>.)  The
+   <structfield>relfilenode</> value is of interest if you want to examine
+   the table's disk file directly.
   </para>
 
   <para>
    To show the space used by <acronym>TOAST</> tables, use a query
-   like the following, substituting the <literal>relfilenode</literal>
-   number of the heap (determined by the query above):
+   like the following:
 <programlisting>
 SELECT relname, relpages
-    FROM pg_class
-    WHERE relname = 'pg_toast_16806' OR relname = 'pg_toast_16806_index'
+    FROM pg_class,
+         (SELECT reltoastrelid FROM pg_class
+          WHERE relname = 'customer') ss
+    WHERE oid = ss.reltoastrelid
+       OR oid = (SELECT reltoastidxid FROM pg_class
+                 WHERE oid = ss.reltoastrelid)
     ORDER BY relname;
 
        relname        | relpages 
@@ -74,7 +77,7 @@ SELECT c2.relname, c2.relpages
     WHERE c.relname = 'customer'
         AND c.oid = i.indrelid
         AND c2.oid = i.indexrelid
-        ORDER BY c2.relname;
+    ORDER BY c2.relname;
 
        relname        | relpages 
 ----------------------+----------
@@ -113,13 +116,10 @@ SELECT relname, relpages FROM pg_class ORDER BY relpages DESC;
 
   <para>
    The most important disk monitoring task of a database administrator
-   is to make sure the disk doesn't grow full.  A filled data disk may
-   result in subsequent corruption of database indexes, but not of the
-   tables themselves. If the WAL files are on the same disk (as
-   is the case for a default configuration) then a filled disk during
-   database initialization may result in corrupted or incomplete WAL
-   files. This failure condition is detected and the database server
-   will refuse to start up.
+   is to make sure the disk doesn't grow full.  A filled data disk will
+   not result in data corruption, but it may well prevent useful activity
+   from occurring. If the disk holding the WAL files grows full, database
+   server panic and consequent shutdown may occur.
   </para>
 
   <para>
index 6c23adb81b74ded7c47eb2cd301fad65d2024a0e..687d322812059e77e87748534bf835c6ad4518b5 100644 (file)
@@ -1,5 +1,5 @@
 <!--
-$PostgreSQL: pgsql/doc/src/sgml/perform.sgml,v 1.47 2004/11/15 06:32:14 neilc Exp $
+$PostgreSQL: pgsql/doc/src/sgml/perform.sgml,v 1.48 2004/12/01 19:00:27 tgl Exp $
 -->
 
  <chapter id="performance-tips">
@@ -389,14 +389,15 @@ SELECT relname, relkind, reltuples, relpages FROM pg_class WHERE relname LIKE 't
   <para>
    For efficiency reasons, <structfield>reltuples</structfield> 
    and <structfield>relpages</structfield> are not updated on-the-fly,
-   and so they usually contain only approximate values (which is good
-   enough for the planner's purposes).  They are initialized with dummy
-   values (presently 1000 and 10 respectively) when a table is created.
-   They are updated by certain commands, presently <command>VACUUM</>,
-   <command>ANALYZE</>, and <command>CREATE INDEX</>.  A stand-alone
+   and so they usually contain somewhat out-of-date values.
+   They are updated by <command>VACUUM</>, <command>ANALYZE</>, and a
+   few DDL commands such as <command>CREATE INDEX</>.  A stand-alone
    <command>ANALYZE</>, that is one not part of <command>VACUUM</>,
    generates an approximate <structfield>reltuples</structfield> value
-   since it does not read every row of the table.
+   since it does not read every row of the table.  The planner
+   will scale the values it finds in <structname>pg_class</structname>
+   to match the current physical table size, thus obtaining a closer
+   approximation.
   </para>
 
   <indexterm>
index 391f9d06c59935111dcaac37fd6d46d848eb0926..3a597810398725353b978ccddf47eabe64cdac4d 100644 (file)
@@ -1,5 +1,5 @@
 <!--
-$PostgreSQL: pgsql/doc/src/sgml/release.sgml,v 1.314 2004/11/27 21:56:04 petere Exp $
+$PostgreSQL: pgsql/doc/src/sgml/release.sgml,v 1.315 2004/12/01 19:00:27 tgl Exp $
 -->
 
 <appendix id="release">
@@ -527,6 +527,24 @@ $PostgreSQL: pgsql/doc/src/sgml/release.sgml,v 1.314 2004/11/27 21:56:04 petere
      </para>
     </listitem>
 
+    <listitem>
+     <para>
+      Use dynamically-generated table size estimates while planning (Tom)
+     </para>
+     <para>
+      The optimizer now uses a table's current actual size on disk as its
+      estimate of the number of blocks in the table, and it makes an estimate
+      of the number of rows in the table based on the current size on disk.
+      Formerly, the
+      <structname>pg_class</structname>.<structfield>relpages</structfield>
+      and
+      <structname>pg_class</structname>.<structfield>reltuples</structfield>
+      fields were used as-is, but these values might be quite out-of-date,
+      leading to poor choices of plans.  They are now treated only as an
+      indication of the table's density (rows per page).
+     </para>
+    </listitem>
+
     <listitem>
      <para>
       Improved index usage with <literal>OR</> clauses (Tom)
index 771ff6cbe7c13d4ccdc6e63009ee17dfb9b0b5e7..b36153d0d57fa968e1aad72de91e87951437e2de 100644 (file)
@@ -12,7 +12,7 @@
  * Portions Copyright (c) 1994, Regents of the University of California
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/access/nbtree/nbtree.c,v 1.122 2004/11/17 03:13:38 neilc Exp $
+ *       $PostgreSQL: pgsql/src/backend/access/nbtree/nbtree.c,v 1.123 2004/12/01 19:00:37 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -785,6 +785,10 @@ btvacuumcleanup(PG_FUNCTION_ARGS)
                         * Do the physical truncation.
                         */
                        RelationTruncate(rel, new_pages);
+
+                       /* update statistics */
+                       stats->pages_removed = num_pages - new_pages;
+
                        num_pages = new_pages;
                }
        }
index f5ec158d7a0811857432e6c298babc36e4953541..e99646d0bc3feb742329fd927dd0a90ab4c5fa30 100644 (file)
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/catalog/heap.c,v 1.276 2004/08/31 17:10:36 tgl Exp $
+ *       $PostgreSQL: pgsql/src/backend/catalog/heap.c,v 1.277 2004/12/01 19:00:39 tgl Exp $
  *
  *
  * INTERFACE ROUTINES
@@ -607,37 +607,22 @@ AddNewRelationTuple(Relation pg_class_desc,
         */
        new_rel_reltup = new_rel_desc->rd_rel;
 
-       /*
-        * Here we insert bogus estimates of the size of the new relation. In
-        * reality, of course, the new relation has 0 tuples and pages, and if
-        * we were tracking these statistics accurately then we'd set the
-        * fields that way.  But at present the stats will be updated only by
-        * VACUUM or CREATE INDEX, and the user might insert a lot of tuples
-        * before he gets around to doing either of those.      So, instead of
-        * saying the relation is empty, we insert guesstimates.  The point is
-        * to keep the optimizer from making really stupid choices on
-        * never-yet-vacuumed tables; so the estimates need only be large
-        * enough to discourage the optimizer from using nested-loop plans.
-        * With this hack, nested-loop plans will be preferred only after the
-        * table has been proven to be small by VACUUM or CREATE INDEX.
-        * Maintaining the stats on-the-fly would solve the problem more
-        * cleanly, but the overhead of that would likely cost more than it'd
-        * save. (NOTE: CREATE INDEX inserts the same bogus estimates if it
-        * finds the relation has 0 rows and pages. See index.c.)
-        */
        switch (relkind)
        {
                case RELKIND_RELATION:
                case RELKIND_INDEX:
                case RELKIND_TOASTVALUE:
-                       new_rel_reltup->relpages = 10;          /* bogus estimates */
-                       new_rel_reltup->reltuples = 1000;
+                       /* The relation is real, but as yet empty */
+                       new_rel_reltup->relpages = 0;
+                       new_rel_reltup->reltuples = 0;
                        break;
                case RELKIND_SEQUENCE:
+                       /* Sequences always have a known size */
                        new_rel_reltup->relpages = 1;
                        new_rel_reltup->reltuples = 1;
                        break;
-               default:                                /* views, etc */
+               default:
+                       /* Views, etc, have no disk storage */
                        new_rel_reltup->relpages = 0;
                        new_rel_reltup->reltuples = 0;
                        break;
index 19fc60b6c8898bfcd7f76ab54841f8c8646b3b93..d61fd274b619bd497fd1ae753b18aa53379cb982 100644 (file)
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/catalog/index.c,v 1.241 2004/10/15 22:39:53 tgl Exp $
+ *       $PostgreSQL: pgsql/src/backend/catalog/index.c,v 1.242 2004/12/01 19:00:39 tgl Exp $
  *
  *
  * INTERFACE ROUTINES
 #include "catalog/index.h"
 #include "catalog/indexing.h"
 #include "catalog/pg_constraint.h"
-#include "catalog/pg_index.h"
 #include "catalog/pg_opclass.h"
-#include "catalog/pg_proc.h"
 #include "catalog/pg_type.h"
 #include "executor/executor.h"
 #include "miscadmin.h"
 #include "optimizer/clauses.h"
-#include "optimizer/prep.h"
 #include "parser/parse_expr.h"
-#include "parser/parse_func.h"
 #include "storage/sinval.h"
 #include "storage/smgr.h"
 #include "utils/builtins.h"
-#include "utils/catcache.h"
 #include "utils/fmgroids.h"
 #include "utils/inval.h"
 #include "utils/lsyscache.h"
 #include "utils/syscache.h"
 
 
-/*
- * macros used in guessing how many tuples are on a page.
- */
-#define AVG_ATTR_SIZE 8
-#define NTUPLES_PER_PAGE(natts) \
-       ((BLCKSZ - MAXALIGN(sizeof(PageHeaderData))) / \
-       ((natts) * AVG_ATTR_SIZE + MAXALIGN(sizeof(HeapTupleHeaderData))))
-
 /* non-export function prototypes */
 static TupleDesc ConstructTupleDescriptor(Relation heapRelation,
                                                 IndexInfo *indexInfo,
@@ -1153,6 +1140,8 @@ setNewRelfilenode(Relation relation)
 
        /* update the pg_class row */
        rd_rel->relfilenode = newrelfilenode;
+       rd_rel->relpages = 0;           /* it's empty until further notice */
+       rd_rel->reltuples = 0;
        simple_heap_update(pg_class, &tuple->t_self, tuple);
        CatalogUpdateIndexes(pg_class, tuple);
 
@@ -1170,7 +1159,7 @@ setNewRelfilenode(Relation relation)
  *
  * Update pg_class' relpages and reltuples statistics for the given relation
  * (which can be either a table or an index).  Note that this is not used
- * in the context of VACUUM.
+ * in the context of VACUUM, only CREATE INDEX.
  * ----------------
  */
 void
@@ -1209,7 +1198,8 @@ UpdateStats(Oid relid, double reltuples)
         * Find the tuple to update in pg_class.  Normally we make a copy of
         * the tuple using the syscache, modify it, and apply heap_update. But
         * in bootstrap mode we can't use heap_update, so we cheat and
-        * overwrite the tuple in-place.
+        * overwrite the tuple in-place.  (Note: as of PG 8.0 this isn't called
+        * during bootstrap, but leave the code here for possible future use.)
         *
         * We also must cheat if reindexing pg_class itself, because the target
         * index may presently not be part of the set of indexes that
@@ -1245,45 +1235,14 @@ UpdateStats(Oid relid, double reltuples)
                elog(ERROR, "could not find tuple for relation %u", relid);
        rd_rel = (Form_pg_class) GETSTRUCT(tuple);
 
-       /*
-        * Figure values to insert.
-        *
-        * If we found zero tuples in the scan, do NOT believe it; instead put a
-        * bogus estimate into the statistics fields.  Otherwise, the common
-        * pattern "CREATE TABLE; CREATE INDEX; insert data" leaves the table
-        * with zero size statistics until a VACUUM is done.  The optimizer
-        * will generate very bad plans if the stats claim the table is empty
-        * when it is actually sizable.  See also CREATE TABLE in heap.c.
-        *
-        * Note: this path is also taken during bootstrap, because bootstrap.c
-        * passes reltuples = 0 after loading a table.  We have to estimate
-        * some number for reltuples based on the actual number of pages.
-        */
-       relpages = RelationGetNumberOfBlocks(whichRel);
-
-       if (reltuples == 0)
-       {
-               if (relpages == 0)
-               {
-                       /* Bogus defaults for a virgin table, same as heap.c */
-                       reltuples = 1000;
-                       relpages = 10;
-               }
-               else if (whichRel->rd_rel->relkind == RELKIND_INDEX && relpages <= 2)
-               {
-                       /* Empty index, leave bogus defaults in place */
-                       reltuples = 1000;
-               }
-               else
-                       reltuples = ((double) relpages) * NTUPLES_PER_PAGE(whichRel->rd_rel->relnatts);
-       }
-
        /*
         * Update statistics in pg_class, if they changed.      (Avoiding an
         * unnecessary update is not just a tiny performance improvement; it
         * also reduces the window wherein concurrent CREATE INDEX commands
         * may conflict.)
         */
+       relpages = RelationGetNumberOfBlocks(whichRel);
+
        if (rd_rel->relpages != (int32) relpages ||
                rd_rel->reltuples != (float4) reltuples)
        {
index 3d0c6e0e996d65bf04cf069cd7c1b013d02549f9..941e0d36e667a3bfc57c96e448c519b0913733bc 100644 (file)
@@ -13,7 +13,7 @@
  *
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/commands/vacuum.c,v 1.295 2004/10/15 22:39:56 tgl Exp $
+ *       $PostgreSQL: pgsql/src/backend/commands/vacuum.c,v 1.296 2004/12/01 19:00:41 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -646,7 +646,7 @@ vac_update_relstats(Oid relid, BlockNumber num_pages, double num_tuples,
        /* overwrite the existing statistics in the tuple */
        pgcform = (Form_pg_class) GETSTRUCT(&rtup);
        pgcform->relpages = (int32) num_pages;
-       pgcform->reltuples = num_tuples;
+       pgcform->reltuples = (float4) num_tuples;
        pgcform->relhasindex = hasindex;
 
        /*
index ff78ea00d1cd9635bf72a47e7d63c0b35b87a8d1..f18e0f92f62045a7c7688a7cb2da711539bf52d2 100644 (file)
  *
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/commands/vacuumlazy.c,v 1.48 2004/10/25 15:42:02 tgl Exp $
+ *       $PostgreSQL: pgsql/src/backend/commands/vacuumlazy.c,v 1.49 2004/12/01 19:00:42 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
 #include "postgres.h"
 
+#include <math.h>
+
 #include "access/genam.h"
 #include "access/heapam.h"
 #include "access/xlog.h"
@@ -67,6 +69,8 @@ typedef struct LVRelStats
        /* Overall statistics about rel */
        BlockNumber rel_pages;
        double          rel_tuples;
+       BlockNumber     pages_removed;
+       double          tuples_deleted;
        BlockNumber nonempty_pages; /* actually, last nonempty page + 1 */
        Size            threshold;              /* minimum interesting free space */
        /* List of TIDs of tuples we intend to delete */
@@ -94,12 +98,19 @@ static void lazy_scan_heap(Relation onerel, LVRelStats *vacrelstats,
                           Relation *Irel, int nindexes);
 static void lazy_vacuum_heap(Relation onerel, LVRelStats *vacrelstats);
 static void lazy_scan_index(Relation indrel, LVRelStats *vacrelstats);
-static void lazy_vacuum_index(Relation indrel, LVRelStats *vacrelstats);
+static void lazy_vacuum_index(Relation indrel,
+                                                         double *index_tups_vacuumed,
+                                                         BlockNumber *index_pages_removed,
+                                                         LVRelStats *vacrelstats);
 static int lazy_vacuum_page(Relation onerel, BlockNumber blkno, Buffer buffer,
                                 int tupindex, LVRelStats *vacrelstats);
 static void lazy_truncate_heap(Relation onerel, LVRelStats *vacrelstats);
 static BlockNumber count_nondeletable_pages(Relation onerel,
                                                 LVRelStats *vacrelstats);
+static void lazy_update_relstats(Relation rel, BlockNumber num_pages,
+                                                                BlockNumber pages_removed,
+                                                                double num_tuples, double tuples_removed,
+                                                                bool hasindex);
 static void lazy_space_alloc(LVRelStats *vacrelstats, BlockNumber relblocks);
 static void lazy_record_dead_tuple(LVRelStats *vacrelstats,
                                           ItemPointer itemptr);
@@ -169,8 +180,10 @@ lazy_vacuum_rel(Relation onerel, VacuumStmt *vacstmt)
        lazy_update_fsm(onerel, vacrelstats);
 
        /* Update statistics in pg_class */
-       vac_update_relstats(RelationGetRelid(onerel), vacrelstats->rel_pages,
-                                               vacrelstats->rel_tuples, hasindex);
+       lazy_update_relstats(onerel, vacrelstats->rel_pages,
+                                                vacrelstats->pages_removed,
+                                                vacrelstats->rel_tuples, vacrelstats->tuples_deleted,
+                                                hasindex);
 }
 
 
@@ -195,6 +208,9 @@ lazy_scan_heap(Relation onerel, LVRelStats *vacrelstats,
                                tups_vacuumed,
                                nkeep,
                                nunused;
+       double     *index_tups_vacuumed;
+       BlockNumber *index_pages_removed;
+       bool            did_vacuum_index = false;
        int                     i;
        VacRUsage       ru0;
 
@@ -209,6 +225,16 @@ lazy_scan_heap(Relation onerel, LVRelStats *vacrelstats,
        empty_pages = 0;
        num_tuples = tups_vacuumed = nkeep = nunused = 0;
 
+       /*
+        * Because index vacuuming is done in multiple passes, we have to keep
+        * track of the total number of rows and pages removed from each index.
+        * index_tups_vacuumed[i] is the number removed so far from the i'th
+        * index.  (For partial indexes this could well be different from
+        * tups_vacuumed.)  Likewise for index_pages_removed[i].
+        */
+       index_tups_vacuumed = (double *) palloc0(nindexes * sizeof(double));
+       index_pages_removed = (BlockNumber *) palloc0(nindexes * sizeof(BlockNumber));
+
        nblocks = RelationGetNumberOfBlocks(onerel);
        vacrelstats->rel_pages = nblocks;
        vacrelstats->nonempty_pages = 0;
@@ -238,7 +264,11 @@ lazy_scan_heap(Relation onerel, LVRelStats *vacrelstats,
                {
                        /* Remove index entries */
                        for (i = 0; i < nindexes; i++)
-                               lazy_vacuum_index(Irel[i], vacrelstats);
+                               lazy_vacuum_index(Irel[i],
+                                                                 &index_tups_vacuumed[i],
+                                                                 &index_pages_removed[i],
+                                                                 vacrelstats);
+                       did_vacuum_index = true;
                        /* Remove tuples from heap */
                        lazy_vacuum_heap(onerel, vacrelstats);
                        /* Forget the now-vacuumed tuples, and press on */
@@ -400,6 +430,7 @@ lazy_scan_heap(Relation onerel, LVRelStats *vacrelstats,
 
        /* save stats for use later */
        vacrelstats->rel_tuples = num_tuples;
+       vacrelstats->tuples_deleted = tups_vacuumed;
 
        /* If any tuples need to be deleted, perform final vacuum cycle */
        /* XXX put a threshold on min number of tuples here? */
@@ -407,11 +438,14 @@ lazy_scan_heap(Relation onerel, LVRelStats *vacrelstats,
        {
                /* Remove index entries */
                for (i = 0; i < nindexes; i++)
-                       lazy_vacuum_index(Irel[i], vacrelstats);
+                       lazy_vacuum_index(Irel[i],
+                                                         &index_tups_vacuumed[i],
+                                                         &index_pages_removed[i],
+                                                         vacrelstats);
                /* Remove tuples from heap */
                lazy_vacuum_heap(onerel, vacrelstats);
        }
-       else
+       else if (!did_vacuum_index)
        {
                /* Must do post-vacuum cleanup and statistics update anyway */
                for (i = 0; i < nindexes; i++)
@@ -588,9 +622,9 @@ lazy_scan_index(Relation indrel, LVRelStats *vacrelstats)
                return;
 
        /* now update statistics in pg_class */
-       vac_update_relstats(RelationGetRelid(indrel),
-                                               stats->num_pages, stats->num_index_tuples,
-                                               false);
+       lazy_update_relstats(indrel, stats->num_pages, stats->pages_removed,
+                                                stats->num_index_tuples, stats->tuples_removed,
+                                                false);
 
        ereport(elevel,
           (errmsg("index \"%s\" now contains %.0f row versions in %u pages",
@@ -611,11 +645,17 @@ lazy_scan_index(Relation indrel, LVRelStats *vacrelstats)
  *             Delete all the index entries pointing to tuples listed in
  *             vacrelstats->dead_tuples.
  *
+ *             Increment *index_tups_vacuumed by the number of index entries
+ *             removed, and *index_pages_removed by the number of pages removed.
+ *
  *             Finally, we arrange to update the index relation's statistics in
  *             pg_class.
  */
 static void
-lazy_vacuum_index(Relation indrel, LVRelStats *vacrelstats)
+lazy_vacuum_index(Relation indrel,
+                                 double *index_tups_vacuumed,
+                                 BlockNumber *index_pages_removed,
+                                 LVRelStats *vacrelstats)
 {
        IndexBulkDeleteResult *stats;
        IndexVacuumCleanupInfo vcinfo;
@@ -652,10 +692,14 @@ lazy_vacuum_index(Relation indrel, LVRelStats *vacrelstats)
        if (!stats)
                return;
 
+       /* accumulate total removed over multiple index-cleaning cycles */
+       *index_tups_vacuumed += stats->tuples_removed;
+       *index_pages_removed += stats->pages_removed;
+
        /* now update statistics in pg_class */
-       vac_update_relstats(RelationGetRelid(indrel),
-                                               stats->num_pages, stats->num_index_tuples,
-                                               false);
+       lazy_update_relstats(indrel, stats->num_pages, *index_pages_removed,
+                                                stats->num_index_tuples, *index_tups_vacuumed,
+                                                false);
 
        ereport(elevel,
           (errmsg("index \"%s\" now contains %.0f row versions in %u pages",
@@ -741,8 +785,6 @@ lazy_truncate_heap(Relation onerel, LVRelStats *vacrelstats)
         * Do the physical truncation.
         */
        RelationTruncate(onerel, new_rel_pages);
-       vacrelstats->rel_pages = new_rel_pages;         /* save new number of
-                                                                                                * blocks */
 
        /*
         * Drop free-space info for removed blocks; these must not get entered
@@ -763,6 +805,10 @@ lazy_truncate_heap(Relation onerel, LVRelStats *vacrelstats)
        /* We destroyed the heap ordering, so mark array unordered */
        vacrelstats->fs_is_heap = false;
 
+       /* update statistics */
+       vacrelstats->rel_pages = new_rel_pages;
+       vacrelstats->pages_removed = old_rel_pages - new_rel_pages;
+
        /*
         * We keep the exclusive lock until commit (perhaps not necessary)?
         */
@@ -886,6 +932,51 @@ count_nondeletable_pages(Relation onerel, LVRelStats *vacrelstats)
        return vacrelstats->nonempty_pages;
 }
 
+/*
+ * lazy_update_relstats - update pg_class statistics for a table or index
+ *
+ * We always want to set relpages to an accurate value.  However, for lazy
+ * VACUUM it seems best to set reltuples to the average of the number of
+ * rows before vacuuming and the number after vacuuming, rather than just
+ * using the number after vacuuming.  This will result in the best average
+ * performance in a steady-state situation where VACUUMs are performed
+ * regularly on a table of roughly constant size, assuming that the physical
+ * number of pages in the table stays about the same throughout.  (Note that
+ * we do not apply the same logic to VACUUM FULL, because it repacks the table
+ * and thereby boosts the tuple density.)
+ *
+ * An important point is that when the table size has decreased a lot during
+ * vacuuming, the old reltuples count might give an overestimate of the tuple
+ * density.  We handle this by scaling down the old reltuples count by the
+ * fraction by which the table has shortened before we merge it with the
+ * new reltuples count.  In particular this means that when relpages goes to
+ * zero, reltuples will immediately go to zero as well, causing the planner
+ * to fall back on other estimation procedures as the table grows again.
+ *
+ * Because we do this math independently for the table and the indexes, it's
+ * quite possible to end up with an index's reltuples different from the
+ * table's, which is silly except in the case of partial indexes.  We don't
+ * worry too much about that here; the planner contains filtering logic to
+ * ensure it only uses sane estimates.
+ */
+static void
+lazy_update_relstats(Relation rel, BlockNumber num_pages,
+                                        BlockNumber pages_removed,
+                                        double num_tuples, double tuples_removed,
+                                        bool hasindex)
+{
+       double  old_num_tuples;
+
+       old_num_tuples = num_tuples + tuples_removed;
+       if (pages_removed > 0)
+               old_num_tuples *= (double) num_pages / (double) (num_pages + pages_removed);
+       if (old_num_tuples > num_tuples)
+               num_tuples = ceil((num_tuples + old_num_tuples) * 0.5);
+
+       vac_update_relstats(RelationGetRelid(rel), num_pages, num_tuples,
+                                               hasindex);
+}
+
 /*
  * lazy_space_alloc - space allocation decisions for lazy vacuum
  *
index ed76fe8fb8cb6091d397439f81a893bdcf5c630d..b4f42ac12355a0dc931b831e7ae5467470df067c 100644 (file)
@@ -9,7 +9,7 @@
  *
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/optimizer/util/plancat.c,v 1.97 2004/10/01 17:11:50 tgl Exp $
+ *       $PostgreSQL: pgsql/src/backend/optimizer/util/plancat.c,v 1.98 2004/12/01 19:00:43 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
 #include "miscadmin.h"
 
 
+static void estimate_rel_size(Relation rel, int32 *attr_widths,
+                                                         BlockNumber *pages, double *tuples);
+
+
 /*
  * get_relation_info -
  *       Retrieves catalog information for a given relation.
  *     indexlist       list of IndexOptInfos for relation's indexes
  *     pages           number of pages
  *     tuples          number of tuples
+ *
+ * Also, initialize the attr_needed[] and attr_widths[] arrays.  In most
+ * cases these are left as zeroes, but sometimes we need to compute attr
+ * widths here, and we may as well cache the results for costsize.c.
  */
 void
 get_relation_info(Oid relationObjectId, RelOptInfo *rel)
@@ -64,6 +72,18 @@ get_relation_info(Oid relationObjectId, RelOptInfo *rel)
        rel->min_attr = FirstLowInvalidHeapAttributeNumber + 1;
        rel->max_attr = RelationGetNumberOfAttributes(relation);
 
+       Assert(rel->max_attr >= rel->min_attr);
+       rel->attr_needed = (Relids *)
+               palloc0((rel->max_attr - rel->min_attr + 1) * sizeof(Relids));
+       rel->attr_widths = (int32 *)
+               palloc0((rel->max_attr - rel->min_attr + 1) * sizeof(int32));
+
+       /*
+        * Estimate relation size.
+        */
+       estimate_rel_size(relation, rel->attr_widths - rel->min_attr,
+                                         &rel->pages, &rel->tuples);
+
        /*
         * Make list of indexes.  Ignore indexes on system catalogs if told
         * to.
@@ -121,8 +141,6 @@ get_relation_info(Oid relationObjectId, RelOptInfo *rel)
                        }
 
                        info->relam = indexRelation->rd_rel->relam;
-                       info->pages = indexRelation->rd_rel->relpages;
-                       info->tuples = indexRelation->rd_rel->reltuples;
                        info->amcostestimate = index_cost_estimator(indexRelation);
 
                        /*
@@ -156,6 +174,26 @@ get_relation_info(Oid relationObjectId, RelOptInfo *rel)
                        info->predOK = false;           /* set later in indxpath.c */
                        info->unique = index->indisunique;
 
+                       /*
+                        * Estimate the index size.  If it's not a partial index, we
+                        * lock the number-of-tuples estimate to equal the parent table;
+                        * if it is partial then we have to use the same methods as we
+                        * would for a table, except we can be sure that the index is
+                        * not larger than the table.
+                        */
+                       if (info->indpred == NIL)
+                       {
+                               info->pages = RelationGetNumberOfBlocks(indexRelation);
+                               info->tuples = rel->tuples;
+                       }
+                       else
+                       {
+                               estimate_rel_size(indexRelation, NULL,
+                                                                 &info->pages, &info->tuples);
+                               if (info->tuples > rel->tuples)
+                                       info->tuples = rel->tuples;
+                       }
+
                        /* initialize cached join info to empty */
                        info->outer_relids = NULL;
                        info->inner_paths = NIL;
@@ -170,13 +208,110 @@ get_relation_info(Oid relationObjectId, RelOptInfo *rel)
 
        rel->indexlist = indexinfos;
 
-       rel->pages = relation->rd_rel->relpages;
-       rel->tuples = relation->rd_rel->reltuples;
-
        /* XXX keep the lock here? */
        heap_close(relation, AccessShareLock);
 }
 
+/*
+ * estimate_rel_size - estimate # pages and # tuples in a table or index
+ *
+ * If attr_widths isn't NULL, it points to the zero-index entry of the
+ * relation's attr_width[] cache; we fill this in if we have need to compute
+ * the attribute widths for estimation purposes.
+ */
+static void
+estimate_rel_size(Relation rel, int32 *attr_widths,
+                                 BlockNumber *pages, double *tuples)
+{
+       BlockNumber     curpages;
+       BlockNumber     relpages;
+       double          reltuples;
+       double          density;
+
+       switch (rel->rd_rel->relkind)
+       {
+               case RELKIND_RELATION:
+               case RELKIND_INDEX:
+               case RELKIND_TOASTVALUE:
+                       /* it has storage, ok to call the smgr */
+                       *pages = curpages = RelationGetNumberOfBlocks(rel);
+                       /* quick exit if rel is clearly empty */
+                       if (curpages == 0)
+                       {
+                               *tuples = 0;
+                               break;
+                       }
+                       /* coerce values in pg_class to more desirable types */
+                       relpages = (BlockNumber) rel->rd_rel->relpages;
+                       reltuples = (double) rel->rd_rel->reltuples;
+                       /*
+                        * If it's an index, discount the metapage.  This is a kluge
+                        * because it assumes more than it ought to about index contents;
+                        * it's reasonably OK for btrees but a bit suspect otherwise.
+                        */
+                       if (rel->rd_rel->relkind == RELKIND_INDEX &&
+                               relpages > 0)
+                       {
+                               curpages--;
+                               relpages--;
+                       }
+                       /* estimate number of tuples from previous tuple density */
+                       if (relpages > 0)
+                               density = reltuples / (double) relpages;
+                       else
+                       {
+                               /*
+                                * When we have no data because the relation was truncated,
+                                * estimate tuple width from attribute datatypes.  We assume
+                                * here that the pages are completely full, which is OK for
+                                * tables (since they've presumably not been VACUUMed yet)
+                                * but is probably an overestimate for indexes.  Fortunately
+                                * get_relation_info() can clamp the overestimate to the
+                                * parent table's size.
+                                */
+                               int32   tuple_width = 0;
+                               int             i;
+
+                               for (i = 1; i <= RelationGetNumberOfAttributes(rel); i++)
+                               {
+                                       Form_pg_attribute att = rel->rd_att->attrs[i - 1];
+                                       int32           item_width;
+
+                                       if (att->attisdropped)
+                                               continue;
+                                       /* This should match set_rel_width() in costsize.c */
+                                       item_width = get_attavgwidth(RelationGetRelid(rel), i);
+                                       if (item_width <= 0)
+                                       {
+                                               item_width = get_typavgwidth(att->atttypid,
+                                                                                                        att->atttypmod);
+                                               Assert(item_width > 0);
+                                       }
+                                       if (attr_widths != NULL)
+                                               attr_widths[i] = item_width;
+                                       tuple_width += item_width;
+                               }
+                               tuple_width = MAXALIGN(tuple_width);
+                               tuple_width += MAXALIGN(sizeof(HeapTupleHeaderData));
+                               tuple_width += sizeof(ItemPointerData);
+                               /* note: integer division is intentional here */
+                               density = (BLCKSZ - sizeof(PageHeaderData)) / tuple_width;
+                       }
+                       *tuples = rint(density * (double) curpages);
+                       break;
+               case RELKIND_SEQUENCE:
+                       /* Sequences always have a known size */
+                       *pages = 1;
+                       *tuples = 1;
+                       break;
+               default:
+                       /* else it has no disk storage; probably shouldn't get here? */
+                       *pages = 0;
+                       *tuples = 0;
+                       break;
+       }
+}
+
 /*
  * build_physical_tlist
  *
index bdef23fc26cbd7a837bce918c20e2e2018985a6c..a612de8df4356cbc14302e30b0a5812486f90238 100644 (file)
@@ -8,7 +8,7 @@
  *
  *
  * IDENTIFICATION
- *       $PostgreSQL: pgsql/src/backend/optimizer/util/relnode.c,v 1.62 2004/08/29 05:06:44 momjian Exp $
+ *       $PostgreSQL: pgsql/src/backend/optimizer/util/relnode.c,v 1.63 2004/12/01 19:00:43 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -159,10 +159,14 @@ make_base_rel(Query *root, int relid)
                        break;
                case RTE_SUBQUERY:
                case RTE_FUNCTION:
-                       /* Subquery or function --- need only set up attr range */
+                       /* Subquery or function --- set up attr range and arrays */
                        /* Note: 0 is included in range to support whole-row Vars */
                        rel->min_attr = 0;
                        rel->max_attr = list_length(rte->eref->colnames);
+                       rel->attr_needed = (Relids *)
+                               palloc0((rel->max_attr - rel->min_attr + 1) * sizeof(Relids));
+                       rel->attr_widths = (int32 *)
+                               palloc0((rel->max_attr - rel->min_attr + 1) * sizeof(int32));
                        break;
                default:
                        elog(ERROR, "unrecognized RTE kind: %d",
@@ -170,12 +174,6 @@ make_base_rel(Query *root, int relid)
                        break;
        }
 
-       Assert(rel->max_attr >= rel->min_attr);
-       rel->attr_needed = (Relids *)
-               palloc0((rel->max_attr - rel->min_attr + 1) * sizeof(Relids));
-       rel->attr_widths = (int32 *)
-               palloc0((rel->max_attr - rel->min_attr + 1) * sizeof(int32));
-
        return rel;
 }
 
index 01874b1fd622243f249a2ad09561f9feee4028da..bfbebb6ca4d1faf05aa6c70472c2d5b911e00bc6 100644 (file)
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2004, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $PostgreSQL: pgsql/src/include/access/genam.h,v 1.45 2004/08/29 04:13:03 momjian Exp $
+ * $PostgreSQL: pgsql/src/include/access/genam.h,v 1.46 2004/12/01 19:00:45 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
  * an index AM could choose to have bulk-delete return a larger struct
  * of which this is just the first field; this provides a way for bulk-delete
  * to communicate additional private data to vacuum-cleanup.
+ *
+ * Note: pages_removed is the amount by which the index physically shrank,
+ * if any (ie the change in its total size on disk).  pages_deleted and
+ * pages_free refer to free space within the index file.
  */
 typedef struct IndexBulkDeleteResult
 {
        BlockNumber num_pages;          /* pages remaining in index */
+       BlockNumber pages_removed;      /* # removed by bulk-delete operation */
        double          num_index_tuples;               /* tuples remaining */
        double          tuples_removed; /* # removed by bulk-delete operation */
        BlockNumber pages_deleted;      /* # unused pages in index */
index 8d0d6a60ba2f0fe4760961c3b7786ac444b8dd7a..c07f8e1f962925e40d0c02c3cdf708fbb1dc17ef 100644 (file)
@@ -7,7 +7,7 @@
  * Portions Copyright (c) 1996-2004, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $PostgreSQL: pgsql/src/include/nodes/relation.h,v 1.100 2004/11/26 21:08:35 tgl Exp $
+ * $PostgreSQL: pgsql/src/include/nodes/relation.h,v 1.101 2004/12/01 19:00:53 tgl Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -255,7 +255,7 @@ typedef struct IndexOptInfo
        Oid                     indexoid;               /* OID of the index relation */
 
        /* statistics from pg_class */
-       long            pages;                  /* number of disk pages in index */
+       BlockNumber     pages;                  /* number of disk pages in index */
        double          tuples;                 /* number of index tuples in index */
 
        /* index descriptor information */
index 409a5a536aa0feabf8d85990b911073cea0ea8b7..e0b94fff6a163db875cd979f588ce13b9b4f2ee5 100644 (file)
@@ -157,28 +157,28 @@ SELECT COALESCE(a.f, b.i, b.j)
  coalesce 
 ----------
      10.1
-     10.1
-     10.1
-     10.1
-     10.1
-     10.1
-     20.2
-     20.2
-     20.2
      20.2
-     20.2
-     20.2
-    -30.3
-    -30.3
-    -30.3
-    -30.3
-    -30.3
     -30.3
         1
+     10.1
+     20.2
+    -30.3
         2
+     10.1
+     20.2
+    -30.3
         3
+     10.1
+     20.2
+    -30.3
         2
+     10.1
+     20.2
+    -30.3
         1
+     10.1
+     20.2
+    -30.3
        -6
 (24 rows)
 
@@ -197,28 +197,28 @@ SELECT '' AS Five, NULLIF(a.i,b.i) AS "NULLIF(a.i,b.i)",
  five | NULLIF(a.i,b.i) | NULLIF(b.i,4) 
 ------+-----------------+---------------
       |                 |             1
-      |               1 |             2
-      |               1 |             3
-      |               1 |             2
-      |                 |             1
-      |               1 |              
       |               2 |             1
-      |                 |             2
-      |               2 |             3
-      |                 |             2
-      |               2 |             1
-      |               2 |              
       |               3 |             1
-      |               3 |             2
-      |                 |             3
-      |               3 |             2
-      |               3 |             1
-      |               3 |              
       |               4 |             1
+      |               1 |             2
+      |                 |             2
+      |               3 |             2
       |               4 |             2
+      |               1 |             3
+      |               2 |             3
+      |                 |             3
       |               4 |             3
+      |               1 |             2
+      |                 |             2
+      |               3 |             2
       |               4 |             2
+      |                 |             1
+      |               2 |             1
+      |               3 |             1
       |               4 |             1
+      |               1 |              
+      |               2 |              
+      |               3 |              
       |               4 |              
 (24 rows)
 
index e1205a9b001eea69868b4fdacf47dac4df118f86..a04da28e16a8f1a5bdb971321e54e71bf688c0b5 100644 (file)
@@ -561,13 +561,13 @@ SELECT relname, bar.* FROM bar, pg_class where bar.tableoid = pg_class.oid;
  relname | f1 | f2  
 ---------+----+-----
  bar     |  4 |   4
- bar     |  1 | 101
- bar     |  2 | 102
  bar     |  3 | 103
+ bar     |  2 | 102
+ bar     |  1 | 101
  bar2    |  4 |   4
- bar2    |  1 | 101
- bar2    |  2 | 102
  bar2    |  3 | 103
+ bar2    |  2 | 102
+ bar2    |  1 | 101
 (8 rows)
 
 /* Test inheritance of structure (LIKE) */
index 471e149b8c79a6ed46da9dae0fcbdae42b50892f..ec708f77660c98dbf13f292374619418f3600d5f 100644 (file)
@@ -214,13 +214,13 @@ SELECT '' AS "xxx", t1.a, t2.e
   WHERE t1.a = t2.d;
  xxx | a | e  
 -----+---+----
-     | 0 |   
      | 1 | -1
      | 2 |  2
-     | 2 |  4
      | 3 | -3
+     | 2 |  4
      | 5 | -5
      | 5 | -5
+     | 0 |   
 (7 rows)
 
 --
@@ -660,895 +660,895 @@ SELECT '' AS "xxx", *
  xxx | i | j |   t   | i | k  | i | k  
 -----+---+---+-------+---+----+---+----
      | 1 | 4 | one   | 1 | -1 | 1 | -1
-     | 2 | 3 | two   | 1 | -1 | 1 | -1
-     | 3 | 2 | three | 1 | -1 | 1 | -1
-     | 4 | 1 | four  | 1 | -1 | 1 | -1
-     | 5 | 0 | five  | 1 | -1 | 1 | -1
-     | 6 | 6 | six   | 1 | -1 | 1 | -1
-     | 7 | 7 | seven | 1 | -1 | 1 | -1
-     | 8 | 8 | eight | 1 | -1 | 1 | -1
-     | 0 |   | zero  | 1 | -1 | 1 | -1
-     |   |   | null  | 1 | -1 | 1 | -1
-     |   | 0 | zero  | 1 | -1 | 1 | -1
      | 1 | 4 | one   | 1 | -1 | 2 |  2
-     | 2 | 3 | two   | 1 | -1 | 2 |  2
-     | 3 | 2 | three | 1 | -1 | 2 |  2
-     | 4 | 1 | four  | 1 | -1 | 2 |  2
-     | 5 | 0 | five  | 1 | -1 | 2 |  2
-     | 6 | 6 | six   | 1 | -1 | 2 |  2
-     | 7 | 7 | seven | 1 | -1 | 2 |  2
-     | 8 | 8 | eight | 1 | -1 | 2 |  2
-     | 0 |   | zero  | 1 | -1 | 2 |  2
-     |   |   | null  | 1 | -1 | 2 |  2
-     |   | 0 | zero  | 1 | -1 | 2 |  2
      | 1 | 4 | one   | 1 | -1 | 3 | -3
-     | 2 | 3 | two   | 1 | -1 | 3 | -3
-     | 3 | 2 | three | 1 | -1 | 3 | -3
-     | 4 | 1 | four  | 1 | -1 | 3 | -3
-     | 5 | 0 | five  | 1 | -1 | 3 | -3
-     | 6 | 6 | six   | 1 | -1 | 3 | -3
-     | 7 | 7 | seven | 1 | -1 | 3 | -3
-     | 8 | 8 | eight | 1 | -1 | 3 | -3
-     | 0 |   | zero  | 1 | -1 | 3 | -3
-     |   |   | null  | 1 | -1 | 3 | -3
-     |   | 0 | zero  | 1 | -1 | 3 | -3
      | 1 | 4 | one   | 1 | -1 | 2 |  4
-     | 2 | 3 | two   | 1 | -1 | 2 |  4
-     | 3 | 2 | three | 1 | -1 | 2 |  4
-     | 4 | 1 | four  | 1 | -1 | 2 |  4
-     | 5 | 0 | five  | 1 | -1 | 2 |  4
-     | 6 | 6 | six   | 1 | -1 | 2 |  4
-     | 7 | 7 | seven | 1 | -1 | 2 |  4
-     | 8 | 8 | eight | 1 | -1 | 2 |  4
-     | 0 |   | zero  | 1 | -1 | 2 |  4
-     |   |   | null  | 1 | -1 | 2 |  4
-     |   | 0 | zero  | 1 | -1 | 2 |  4
      | 1 | 4 | one   | 1 | -1 | 5 | -5
-     | 2 | 3 | two   | 1 | -1 | 5 | -5
-     | 3 | 2 | three | 1 | -1 | 5 | -5
-     | 4 | 1 | four  | 1 | -1 | 5 | -5
-     | 5 | 0 | five  | 1 | -1 | 5 | -5
-     | 6 | 6 | six   | 1 | -1 | 5 | -5
-     | 7 | 7 | seven | 1 | -1 | 5 | -5
-     | 8 | 8 | eight | 1 | -1 | 5 | -5
-     | 0 |   | zero  | 1 | -1 | 5 | -5
-     |   |   | null  | 1 | -1 | 5 | -5
-     |   | 0 | zero  | 1 | -1 | 5 | -5
      | 1 | 4 | one   | 1 | -1 | 5 | -5
-     | 2 | 3 | two   | 1 | -1 | 5 | -5
-     | 3 | 2 | three | 1 | -1 | 5 | -5
-     | 4 | 1 | four  | 1 | -1 | 5 | -5
-     | 5 | 0 | five  | 1 | -1 | 5 | -5
-     | 6 | 6 | six   | 1 | -1 | 5 | -5
-     | 7 | 7 | seven | 1 | -1 | 5 | -5
-     | 8 | 8 | eight | 1 | -1 | 5 | -5
-     | 0 |   | zero  | 1 | -1 | 5 | -5
-     |   |   | null  | 1 | -1 | 5 | -5
-     |   | 0 | zero  | 1 | -1 | 5 | -5
      | 1 | 4 | one   | 1 | -1 | 0 |   
-     | 2 | 3 | two   | 1 | -1 | 0 |   
-     | 3 | 2 | three | 1 | -1 | 0 |   
-     | 4 | 1 | four  | 1 | -1 | 0 |   
-     | 5 | 0 | five  | 1 | -1 | 0 |   
-     | 6 | 6 | six   | 1 | -1 | 0 |   
-     | 7 | 7 | seven | 1 | -1 | 0 |   
-     | 8 | 8 | eight | 1 | -1 | 0 |   
-     | 0 |   | zero  | 1 | -1 | 0 |   
-     |   |   | null  | 1 | -1 | 0 |   
-     |   | 0 | zero  | 1 | -1 | 0 |   
      | 1 | 4 | one   | 1 | -1 |   |   
-     | 2 | 3 | two   | 1 | -1 |   |   
-     | 3 | 2 | three | 1 | -1 |   |   
-     | 4 | 1 | four  | 1 | -1 |   |   
-     | 5 | 0 | five  | 1 | -1 |   |   
-     | 6 | 6 | six   | 1 | -1 |   |   
-     | 7 | 7 | seven | 1 | -1 |   |   
-     | 8 | 8 | eight | 1 | -1 |   |   
-     | 0 |   | zero  | 1 | -1 |   |   
-     |   |   | null  | 1 | -1 |   |   
-     |   | 0 | zero  | 1 | -1 |   |   
      | 1 | 4 | one   | 1 | -1 |   |  0
-     | 2 | 3 | two   | 1 | -1 |   |  0
-     | 3 | 2 | three | 1 | -1 |   |  0
-     | 4 | 1 | four  | 1 | -1 |   |  0
-     | 5 | 0 | five  | 1 | -1 |   |  0
-     | 6 | 6 | six   | 1 | -1 |   |  0
-     | 7 | 7 | seven | 1 | -1 |   |  0
-     | 8 | 8 | eight | 1 | -1 |   |  0
-     | 0 |   | zero  | 1 | -1 |   |  0
-     |   |   | null  | 1 | -1 |   |  0
-     |   | 0 | zero  | 1 | -1 |   |  0
      | 1 | 4 | one   | 2 |  2 | 1 | -1
-     | 2 | 3 | two   | 2 |  2 | 1 | -1
-     | 3 | 2 | three | 2 |  2 | 1 | -1
-     | 4 | 1 | four  | 2 |  2 | 1 | -1
-     | 5 | 0 | five  | 2 |  2 | 1 | -1
-     | 6 | 6 | six   | 2 |  2 | 1 | -1
-     | 7 | 7 | seven | 2 |  2 | 1 | -1
-     | 8 | 8 | eight | 2 |  2 | 1 | -1
-     | 0 |   | zero  | 2 |  2 | 1 | -1
-     |   |   | null  | 2 |  2 | 1 | -1
-     |   | 0 | zero  | 2 |  2 | 1 | -1
      | 1 | 4 | one   | 2 |  2 | 2 |  2
-     | 2 | 3 | two   | 2 |  2 | 2 |  2
-     | 3 | 2 | three | 2 |  2 | 2 |  2
-     | 4 | 1 | four  | 2 |  2 | 2 |  2
-     | 5 | 0 | five  | 2 |  2 | 2 |  2
-     | 6 | 6 | six   | 2 |  2 | 2 |  2
-     | 7 | 7 | seven | 2 |  2 | 2 |  2
-     | 8 | 8 | eight | 2 |  2 | 2 |  2
-     | 0 |   | zero  | 2 |  2 | 2 |  2
-     |   |   | null  | 2 |  2 | 2 |  2
-     |   | 0 | zero  | 2 |  2 | 2 |  2
      | 1 | 4 | one   | 2 |  2 | 3 | -3
-     | 2 | 3 | two   | 2 |  2 | 3 | -3
-     | 3 | 2 | three | 2 |  2 | 3 | -3
-     | 4 | 1 | four  | 2 |  2 | 3 | -3
-     | 5 | 0 | five  | 2 |  2 | 3 | -3
-     | 6 | 6 | six   | 2 |  2 | 3 | -3
-     | 7 | 7 | seven | 2 |  2 | 3 | -3
-     | 8 | 8 | eight | 2 |  2 | 3 | -3
-     | 0 |   | zero  | 2 |  2 | 3 | -3
-     |   |   | null  | 2 |  2 | 3 | -3
-     |   | 0 | zero  | 2 |  2 | 3 | -3
      | 1 | 4 | one   | 2 |  2 | 2 |  4
-     | 2 | 3 | two   | 2 |  2 | 2 |  4
-     | 3 | 2 | three | 2 |  2 | 2 |  4
-     | 4 | 1 | four  | 2 |  2 | 2 |  4
-     | 5 | 0 | five  | 2 |  2 | 2 |  4
-     | 6 | 6 | six   | 2 |  2 | 2 |  4
-     | 7 | 7 | seven | 2 |  2 | 2 |  4
-     | 8 | 8 | eight | 2 |  2 | 2 |  4
-     | 0 |   | zero  | 2 |  2 | 2 |  4
-     |   |   | null  | 2 |  2 | 2 |  4
-     |   | 0 | zero  | 2 |  2 | 2 |  4
      | 1 | 4 | one   | 2 |  2 | 5 | -5
-     | 2 | 3 | two   | 2 |  2 | 5 | -5
-     | 3 | 2 | three | 2 |  2 | 5 | -5
-     | 4 | 1 | four  | 2 |  2 | 5 | -5
-     | 5 | 0 | five  | 2 |  2 | 5 | -5
-     | 6 | 6 | six   | 2 |  2 | 5 | -5
-     | 7 | 7 | seven | 2 |  2 | 5 | -5
-     | 8 | 8 | eight | 2 |  2 | 5 | -5
-     | 0 |   | zero  | 2 |  2 | 5 | -5
-     |   |   | null  | 2 |  2 | 5 | -5
-     |   | 0 | zero  | 2 |  2 | 5 | -5
      | 1 | 4 | one   | 2 |  2 | 5 | -5
-     | 2 | 3 | two   | 2 |  2 | 5 | -5
-     | 3 | 2 | three | 2 |  2 | 5 | -5
-     | 4 | 1 | four  | 2 |  2 | 5 | -5
-     | 5 | 0 | five  | 2 |  2 | 5 | -5
-     | 6 | 6 | six   | 2 |  2 | 5 | -5
-     | 7 | 7 | seven | 2 |  2 | 5 | -5
-     | 8 | 8 | eight | 2 |  2 | 5 | -5
-     | 0 |   | zero  | 2 |  2 | 5 | -5
-     |   |   | null  | 2 |  2 | 5 | -5
-     |   | 0 | zero  | 2 |  2 | 5 | -5
      | 1 | 4 | one   | 2 |  2 | 0 |   
-     | 2 | 3 | two   | 2 |  2 | 0 |   
-     | 3 | 2 | three | 2 |  2 | 0 |   
-     | 4 | 1 | four  | 2 |  2 | 0 |   
-     | 5 | 0 | five  | 2 |  2 | 0 |   
-     | 6 | 6 | six   | 2 |  2 | 0 |   
-     | 7 | 7 | seven | 2 |  2 | 0 |   
-     | 8 | 8 | eight | 2 |  2 | 0 |   
-     | 0 |   | zero  | 2 |  2 | 0 |   
-     |   |   | null  | 2 |  2 | 0 |   
-     |   | 0 | zero  | 2 |  2 | 0 |   
      | 1 | 4 | one   | 2 |  2 |   |   
-     | 2 | 3 | two   | 2 |  2 |   |   
-     | 3 | 2 | three | 2 |  2 |   |   
-     | 4 | 1 | four  | 2 |  2 |   |   
-     | 5 | 0 | five  | 2 |  2 |   |   
-     | 6 | 6 | six   | 2 |  2 |   |   
-     | 7 | 7 | seven | 2 |  2 |   |   
-     | 8 | 8 | eight | 2 |  2 |   |   
-     | 0 |   | zero  | 2 |  2 |   |   
-     |   |   | null  | 2 |  2 |   |   
-     |   | 0 | zero  | 2 |  2 |   |   
      | 1 | 4 | one   | 2 |  2 |   |  0
-     | 2 | 3 | two   | 2 |  2 |   |  0
-     | 3 | 2 | three | 2 |  2 |   |  0
-     | 4 | 1 | four  | 2 |  2 |   |  0
-     | 5 | 0 | five  | 2 |  2 |   |  0
-     | 6 | 6 | six   | 2 |  2 |   |  0
-     | 7 | 7 | seven | 2 |  2 |   |  0
-     | 8 | 8 | eight | 2 |  2 |   |  0
-     | 0 |   | zero  | 2 |  2 |   |  0
-     |   |   | null  | 2 |  2 |   |  0
-     |   | 0 | zero  | 2 |  2 |   |  0
      | 1 | 4 | one   | 3 | -3 | 1 | -1
-     | 2 | 3 | two   | 3 | -3 | 1 | -1
-     | 3 | 2 | three | 3 | -3 | 1 | -1
-     | 4 | 1 | four  | 3 | -3 | 1 | -1
-     | 5 | 0 | five  | 3 | -3 | 1 | -1
-     | 6 | 6 | six   | 3 | -3 | 1 | -1
-     | 7 | 7 | seven | 3 | -3 | 1 | -1
-     | 8 | 8 | eight | 3 | -3 | 1 | -1
-     | 0 |   | zero  | 3 | -3 | 1 | -1
-     |   |   | null  | 3 | -3 | 1 | -1
-     |   | 0 | zero  | 3 | -3 | 1 | -1
      | 1 | 4 | one   | 3 | -3 | 2 |  2
-     | 2 | 3 | two   | 3 | -3 | 2 |  2
-     | 3 | 2 | three | 3 | -3 | 2 |  2
-     | 4 | 1 | four  | 3 | -3 | 2 |  2
-     | 5 | 0 | five  | 3 | -3 | 2 |  2
-     | 6 | 6 | six   | 3 | -3 | 2 |  2
-     | 7 | 7 | seven | 3 | -3 | 2 |  2
-     | 8 | 8 | eight | 3 | -3 | 2 |  2
-     | 0 |   | zero  | 3 | -3 | 2 |  2
-     |   |   | null  | 3 | -3 | 2 |  2
-     |   | 0 | zero  | 3 | -3 | 2 |  2
      | 1 | 4 | one   | 3 | -3 | 3 | -3
-     | 2 | 3 | two   | 3 | -3 | 3 | -3
-     | 3 | 2 | three | 3 | -3 | 3 | -3
-     | 4 | 1 | four  | 3 | -3 | 3 | -3
-     | 5 | 0 | five  | 3 | -3 | 3 | -3
-     | 6 | 6 | six   | 3 | -3 | 3 | -3
-     | 7 | 7 | seven | 3 | -3 | 3 | -3
-     | 8 | 8 | eight | 3 | -3 | 3 | -3
-     | 0 |   | zero  | 3 | -3 | 3 | -3
-     |   |   | null  | 3 | -3 | 3 | -3
-     |   | 0 | zero  | 3 | -3 | 3 | -3
      | 1 | 4 | one   | 3 | -3 | 2 |  4
-     | 2 | 3 | two   | 3 | -3 | 2 |  4
-     | 3 | 2 | three | 3 | -3 | 2 |  4
-     | 4 | 1 | four  | 3 | -3 | 2 |  4
-     | 5 | 0 | five  | 3 | -3 | 2 |  4
-     | 6 | 6 | six   | 3 | -3 | 2 |  4
-     | 7 | 7 | seven | 3 | -3 | 2 |  4
-     | 8 | 8 | eight | 3 | -3 | 2 |  4
-     | 0 |   | zero  | 3 | -3 | 2 |  4
-     |   |   | null  | 3 | -3 | 2 |  4
-     |   | 0 | zero  | 3 | -3 | 2 |  4
      | 1 | 4 | one   | 3 | -3 | 5 | -5
-     | 2 | 3 | two   | 3 | -3 | 5 | -5
-     | 3 | 2 | three | 3 | -3 | 5 | -5
-     | 4 | 1 | four  | 3 | -3 | 5 | -5
-     | 5 | 0 | five  | 3 | -3 | 5 | -5
-     | 6 | 6 | six   | 3 | -3 | 5 | -5
-     | 7 | 7 | seven | 3 | -3 | 5 | -5
-     | 8 | 8 | eight | 3 | -3 | 5 | -5
-     | 0 |   | zero  | 3 | -3 | 5 | -5
-     |   |   | null  | 3 | -3 | 5 | -5
-     |   | 0 | zero  | 3 | -3 | 5 | -5
      | 1 | 4 | one   | 3 | -3 | 5 | -5
-     | 2 | 3 | two   | 3 | -3 | 5 | -5
-     | 3 | 2 | three | 3 | -3 | 5 | -5
-     | 4 | 1 | four  | 3 | -3 | 5 | -5
-     | 5 | 0 | five  | 3 | -3 | 5 | -5
-     | 6 | 6 | six   | 3 | -3 | 5 | -5
-     | 7 | 7 | seven | 3 | -3 | 5 | -5
-     | 8 | 8 | eight | 3 | -3 | 5 | -5
-     | 0 |   | zero  | 3 | -3 | 5 | -5
-     |   |   | null  | 3 | -3 | 5 | -5
-     |   | 0 | zero  | 3 | -3 | 5 | -5
      | 1 | 4 | one   | 3 | -3 | 0 |   
-     | 2 | 3 | two   | 3 | -3 | 0 |   
-     | 3 | 2 | three | 3 | -3 | 0 |   
-     | 4 | 1 | four  | 3 | -3 | 0 |   
-     | 5 | 0 | five  | 3 | -3 | 0 |   
-     | 6 | 6 | six   | 3 | -3 | 0 |   
-     | 7 | 7 | seven | 3 | -3 | 0 |   
-     | 8 | 8 | eight | 3 | -3 | 0 |   
-     | 0 |   | zero  | 3 | -3 | 0 |   
-     |   |   | null  | 3 | -3 | 0 |   
-     |   | 0 | zero  | 3 | -3 | 0 |   
      | 1 | 4 | one   | 3 | -3 |   |   
-     | 2 | 3 | two   | 3 | -3 |   |   
-     | 3 | 2 | three | 3 | -3 |   |   
+     | 1 | 4 | one   | 3 | -3 |   |  0
+     | 1 | 4 | one   | 2 |  4 | 1 | -1
+     | 1 | 4 | one   | 2 |  4 | 2 |  2
+     | 1 | 4 | one   | 2 |  4 | 3 | -3
+     | 1 | 4 | one   | 2 |  4 | 2 |  4
+     | 1 | 4 | one   | 2 |  4 | 5 | -5
+     | 1 | 4 | one   | 2 |  4 | 5 | -5
+     | 1 | 4 | one   | 2 |  4 | 0 |   
+     | 1 | 4 | one   | 2 |  4 |   |   
+     | 1 | 4 | one   | 2 |  4 |   |  0
+     | 1 | 4 | one   | 5 | -5 | 1 | -1
+     | 1 | 4 | one   | 5 | -5 | 2 |  2
+     | 1 | 4 | one   | 5 | -5 | 3 | -3
+     | 1 | 4 | one   | 5 | -5 | 2 |  4
+     | 1 | 4 | one   | 5 | -5 | 5 | -5
+     | 1 | 4 | one   | 5 | -5 | 5 | -5
+     | 1 | 4 | one   | 5 | -5 | 0 |   
+     | 1 | 4 | one   | 5 | -5 |   |   
+     | 1 | 4 | one   | 5 | -5 |   |  0
+     | 1 | 4 | one   | 5 | -5 | 1 | -1
+     | 1 | 4 | one   | 5 | -5 | 2 |  2
+     | 1 | 4 | one   | 5 | -5 | 3 | -3
+     | 1 | 4 | one   | 5 | -5 | 2 |  4
+     | 1 | 4 | one   | 5 | -5 | 5 | -5
+     | 1 | 4 | one   | 5 | -5 | 5 | -5
+     | 1 | 4 | one   | 5 | -5 | 0 |   
+     | 1 | 4 | one   | 5 | -5 |   |   
+     | 1 | 4 | one   | 5 | -5 |   |  0
+     | 1 | 4 | one   | 0 |    | 1 | -1
+     | 1 | 4 | one   | 0 |    | 2 |  2
+     | 1 | 4 | one   | 0 |    | 3 | -3
+     | 1 | 4 | one   | 0 |    | 2 |  4
+     | 1 | 4 | one   | 0 |    | 5 | -5
+     | 1 | 4 | one   | 0 |    | 5 | -5
+     | 1 | 4 | one   | 0 |    | 0 |   
+     | 1 | 4 | one   | 0 |    |   |   
+     | 1 | 4 | one   | 0 |    |   |  0
+     | 1 | 4 | one   |   |    | 1 | -1
+     | 1 | 4 | one   |   |    | 2 |  2
+     | 1 | 4 | one   |   |    | 3 | -3
+     | 1 | 4 | one   |   |    | 2 |  4
+     | 1 | 4 | one   |   |    | 5 | -5
+     | 1 | 4 | one   |   |    | 5 | -5
+     | 1 | 4 | one   |   |    | 0 |   
+     | 1 | 4 | one   |   |    |   |   
+     | 1 | 4 | one   |   |    |   |  0
+     | 1 | 4 | one   |   |  0 | 1 | -1
+     | 1 | 4 | one   |   |  0 | 2 |  2
+     | 1 | 4 | one   |   |  0 | 3 | -3
+     | 1 | 4 | one   |   |  0 | 2 |  4
+     | 1 | 4 | one   |   |  0 | 5 | -5
+     | 1 | 4 | one   |   |  0 | 5 | -5
+     | 1 | 4 | one   |   |  0 | 0 |   
+     | 1 | 4 | one   |   |  0 |   |   
+     | 1 | 4 | one   |   |  0 |   |  0
+     | 2 | 3 | two   | 1 | -1 | 1 | -1
+     | 2 | 3 | two   | 1 | -1 | 2 |  2
+     | 2 | 3 | two   | 1 | -1 | 3 | -3
+     | 2 | 3 | two   | 1 | -1 | 2 |  4
+     | 2 | 3 | two   | 1 | -1 | 5 | -5
+     | 2 | 3 | two   | 1 | -1 | 5 | -5
+     | 2 | 3 | two   | 1 | -1 | 0 |   
+     | 2 | 3 | two   | 1 | -1 |   |   
+     | 2 | 3 | two   | 1 | -1 |   |  0
+     | 2 | 3 | two   | 2 |  2 | 1 | -1
+     | 2 | 3 | two   | 2 |  2 | 2 |  2
+     | 2 | 3 | two   | 2 |  2 | 3 | -3
+     | 2 | 3 | two   | 2 |  2 | 2 |  4
+     | 2 | 3 | two   | 2 |  2 | 5 | -5
+     | 2 | 3 | two   | 2 |  2 | 5 | -5
+     | 2 | 3 | two   | 2 |  2 | 0 |   
+     | 2 | 3 | two   | 2 |  2 |   |   
+     | 2 | 3 | two   | 2 |  2 |   |  0
+     | 2 | 3 | two   | 3 | -3 | 1 | -1
+     | 2 | 3 | two   | 3 | -3 | 2 |  2
+     | 2 | 3 | two   | 3 | -3 | 3 | -3
+     | 2 | 3 | two   | 3 | -3 | 2 |  4
+     | 2 | 3 | two   | 3 | -3 | 5 | -5
+     | 2 | 3 | two   | 3 | -3 | 5 | -5
+     | 2 | 3 | two   | 3 | -3 | 0 |   
+     | 2 | 3 | two   | 3 | -3 |   |   
+     | 2 | 3 | two   | 3 | -3 |   |  0
+     | 2 | 3 | two   | 2 |  4 | 1 | -1
+     | 2 | 3 | two   | 2 |  4 | 2 |  2
+     | 2 | 3 | two   | 2 |  4 | 3 | -3
+     | 2 | 3 | two   | 2 |  4 | 2 |  4
+     | 2 | 3 | two   | 2 |  4 | 5 | -5
+     | 2 | 3 | two   | 2 |  4 | 5 | -5
+     | 2 | 3 | two   | 2 |  4 | 0 |   
+     | 2 | 3 | two   | 2 |  4 |   |   
+     | 2 | 3 | two   | 2 |  4 |   |  0
+     | 2 | 3 | two   | 5 | -5 | 1 | -1
+     | 2 | 3 | two   | 5 | -5 | 2 |  2
+     | 2 | 3 | two   | 5 | -5 | 3 | -3
+     | 2 | 3 | two   | 5 | -5 | 2 |  4
+     | 2 | 3 | two   | 5 | -5 | 5 | -5
+     | 2 | 3 | two   | 5 | -5 | 5 | -5
+     | 2 | 3 | two   | 5 | -5 | 0 |   
+     | 2 | 3 | two   | 5 | -5 |   |   
+     | 2 | 3 | two   | 5 | -5 |   |  0
+     | 2 | 3 | two   | 5 | -5 | 1 | -1
+     | 2 | 3 | two   | 5 | -5 | 2 |  2
+     | 2 | 3 | two   | 5 | -5 | 3 | -3
+     | 2 | 3 | two   | 5 | -5 | 2 |  4
+     | 2 | 3 | two   | 5 | -5 | 5 | -5
+     | 2 | 3 | two   | 5 | -5 | 5 | -5
+     | 2 | 3 | two   | 5 | -5 | 0 |   
+     | 2 | 3 | two   | 5 | -5 |   |   
+     | 2 | 3 | two   | 5 | -5 |   |  0
+     | 2 | 3 | two   | 0 |    | 1 | -1
+     | 2 | 3 | two   | 0 |    | 2 |  2
+     | 2 | 3 | two   | 0 |    | 3 | -3
+     | 2 | 3 | two   | 0 |    | 2 |  4
+     | 2 | 3 | two   | 0 |    | 5 | -5
+     | 2 | 3 | two   | 0 |    | 5 | -5
+     | 2 | 3 | two   | 0 |    | 0 |   
+     | 2 | 3 | two   | 0 |    |   |   
+     | 2 | 3 | two   | 0 |    |   |  0
+     | 2 | 3 | two   |   |    | 1 | -1
+     | 2 | 3 | two   |   |    | 2 |  2
+     | 2 | 3 | two   |   |    | 3 | -3
+     | 2 | 3 | two   |   |    | 2 |  4
+     | 2 | 3 | two   |   |    | 5 | -5
+     | 2 | 3 | two   |   |    | 5 | -5
+     | 2 | 3 | two   |   |    | 0 |   
+     | 2 | 3 | two   |   |    |   |   
+     | 2 | 3 | two   |   |    |   |  0
+     | 2 | 3 | two   |   |  0 | 1 | -1
+     | 2 | 3 | two   |   |  0 | 2 |  2
+     | 2 | 3 | two   |   |  0 | 3 | -3
+     | 2 | 3 | two   |   |  0 | 2 |  4
+     | 2 | 3 | two   |   |  0 | 5 | -5
+     | 2 | 3 | two   |   |  0 | 5 | -5
+     | 2 | 3 | two   |   |  0 | 0 |   
+     | 2 | 3 | two   |   |  0 |   |   
+     | 2 | 3 | two   |   |  0 |   |  0
+     | 3 | 2 | three | 1 | -1 | 1 | -1
+     | 3 | 2 | three | 1 | -1 | 2 |  2
+     | 3 | 2 | three | 1 | -1 | 3 | -3
+     | 3 | 2 | three | 1 | -1 | 2 |  4
+     | 3 | 2 | three | 1 | -1 | 5 | -5
+     | 3 | 2 | three | 1 | -1 | 5 | -5
+     | 3 | 2 | three | 1 | -1 | 0 |   
+     | 3 | 2 | three | 1 | -1 |   |   
+     | 3 | 2 | three | 1 | -1 |   |  0
+     | 3 | 2 | three | 2 |  2 | 1 | -1
+     | 3 | 2 | three | 2 |  2 | 2 |  2
+     | 3 | 2 | three | 2 |  2 | 3 | -3
+     | 3 | 2 | three | 2 |  2 | 2 |  4
+     | 3 | 2 | three | 2 |  2 | 5 | -5
+     | 3 | 2 | three | 2 |  2 | 5 | -5
+     | 3 | 2 | three | 2 |  2 | 0 |   
+     | 3 | 2 | three | 2 |  2 |   |   
+     | 3 | 2 | three | 2 |  2 |   |  0
+     | 3 | 2 | three | 3 | -3 | 1 | -1
+     | 3 | 2 | three | 3 | -3 | 2 |  2
+     | 3 | 2 | three | 3 | -3 | 3 | -3
+     | 3 | 2 | three | 3 | -3 | 2 |  4
+     | 3 | 2 | three | 3 | -3 | 5 | -5
+     | 3 | 2 | three | 3 | -3 | 5 | -5
+     | 3 | 2 | three | 3 | -3 | 0 |   
+     | 3 | 2 | three | 3 | -3 |   |   
+     | 3 | 2 | three | 3 | -3 |   |  0
+     | 3 | 2 | three | 2 |  4 | 1 | -1
+     | 3 | 2 | three | 2 |  4 | 2 |  2
+     | 3 | 2 | three | 2 |  4 | 3 | -3
+     | 3 | 2 | three | 2 |  4 | 2 |  4
+     | 3 | 2 | three | 2 |  4 | 5 | -5
+     | 3 | 2 | three | 2 |  4 | 5 | -5
+     | 3 | 2 | three | 2 |  4 | 0 |   
+     | 3 | 2 | three | 2 |  4 |   |   
+     | 3 | 2 | three | 2 |  4 |   |  0
+     | 3 | 2 | three | 5 | -5 | 1 | -1
+     | 3 | 2 | three | 5 | -5 | 2 |  2
+     | 3 | 2 | three | 5 | -5 | 3 | -3
+     | 3 | 2 | three | 5 | -5 | 2 |  4
+     | 3 | 2 | three | 5 | -5 | 5 | -5
+     | 3 | 2 | three | 5 | -5 | 5 | -5
+     | 3 | 2 | three | 5 | -5 | 0 |   
+     | 3 | 2 | three | 5 | -5 |   |   
+     | 3 | 2 | three | 5 | -5 |   |  0
+     | 3 | 2 | three | 5 | -5 | 1 | -1
+     | 3 | 2 | three | 5 | -5 | 2 |  2
+     | 3 | 2 | three | 5 | -5 | 3 | -3
+     | 3 | 2 | three | 5 | -5 | 2 |  4
+     | 3 | 2 | three | 5 | -5 | 5 | -5
+     | 3 | 2 | three | 5 | -5 | 5 | -5
+     | 3 | 2 | three | 5 | -5 | 0 |   
+     | 3 | 2 | three | 5 | -5 |   |   
+     | 3 | 2 | three | 5 | -5 |   |  0
+     | 3 | 2 | three | 0 |    | 1 | -1
+     | 3 | 2 | three | 0 |    | 2 |  2
+     | 3 | 2 | three | 0 |    | 3 | -3
+     | 3 | 2 | three | 0 |    | 2 |  4
+     | 3 | 2 | three | 0 |    | 5 | -5
+     | 3 | 2 | three | 0 |    | 5 | -5
+     | 3 | 2 | three | 0 |    | 0 |   
+     | 3 | 2 | three | 0 |    |   |   
+     | 3 | 2 | three | 0 |    |   |  0
+     | 3 | 2 | three |   |    | 1 | -1
+     | 3 | 2 | three |   |    | 2 |  2
+     | 3 | 2 | three |   |    | 3 | -3
+     | 3 | 2 | three |   |    | 2 |  4
+     | 3 | 2 | three |   |    | 5 | -5
+     | 3 | 2 | three |   |    | 5 | -5
+     | 3 | 2 | three |   |    | 0 |   
+     | 3 | 2 | three |   |    |   |   
+     | 3 | 2 | three |   |    |   |  0
+     | 3 | 2 | three |   |  0 | 1 | -1
+     | 3 | 2 | three |   |  0 | 2 |  2
+     | 3 | 2 | three |   |  0 | 3 | -3
+     | 3 | 2 | three |   |  0 | 2 |  4
+     | 3 | 2 | three |   |  0 | 5 | -5
+     | 3 | 2 | three |   |  0 | 5 | -5
+     | 3 | 2 | three |   |  0 | 0 |   
+     | 3 | 2 | three |   |  0 |   |   
+     | 3 | 2 | three |   |  0 |   |  0
+     | 4 | 1 | four  | 1 | -1 | 1 | -1
+     | 4 | 1 | four  | 1 | -1 | 2 |  2
+     | 4 | 1 | four  | 1 | -1 | 3 | -3
+     | 4 | 1 | four  | 1 | -1 | 2 |  4
+     | 4 | 1 | four  | 1 | -1 | 5 | -5
+     | 4 | 1 | four  | 1 | -1 | 5 | -5
+     | 4 | 1 | four  | 1 | -1 | 0 |   
+     | 4 | 1 | four  | 1 | -1 |   |   
+     | 4 | 1 | four  | 1 | -1 |   |  0
+     | 4 | 1 | four  | 2 |  2 | 1 | -1
+     | 4 | 1 | four  | 2 |  2 | 2 |  2
+     | 4 | 1 | four  | 2 |  2 | 3 | -3
+     | 4 | 1 | four  | 2 |  2 | 2 |  4
+     | 4 | 1 | four  | 2 |  2 | 5 | -5
+     | 4 | 1 | four  | 2 |  2 | 5 | -5
+     | 4 | 1 | four  | 2 |  2 | 0 |   
+     | 4 | 1 | four  | 2 |  2 |   |   
+     | 4 | 1 | four  | 2 |  2 |   |  0
+     | 4 | 1 | four  | 3 | -3 | 1 | -1
+     | 4 | 1 | four  | 3 | -3 | 2 |  2
+     | 4 | 1 | four  | 3 | -3 | 3 | -3
+     | 4 | 1 | four  | 3 | -3 | 2 |  4
+     | 4 | 1 | four  | 3 | -3 | 5 | -5
+     | 4 | 1 | four  | 3 | -3 | 5 | -5
+     | 4 | 1 | four  | 3 | -3 | 0 |   
      | 4 | 1 | four  | 3 | -3 |   |   
+     | 4 | 1 | four  | 3 | -3 |   |  0
+     | 4 | 1 | four  | 2 |  4 | 1 | -1
+     | 4 | 1 | four  | 2 |  4 | 2 |  2
+     | 4 | 1 | four  | 2 |  4 | 3 | -3
+     | 4 | 1 | four  | 2 |  4 | 2 |  4
+     | 4 | 1 | four  | 2 |  4 | 5 | -5
+     | 4 | 1 | four  | 2 |  4 | 5 | -5
+     | 4 | 1 | four  | 2 |  4 | 0 |   
+     | 4 | 1 | four  | 2 |  4 |   |   
+     | 4 | 1 | four  | 2 |  4 |   |  0
+     | 4 | 1 | four  | 5 | -5 | 1 | -1
+     | 4 | 1 | four  | 5 | -5 | 2 |  2
+     | 4 | 1 | four  | 5 | -5 | 3 | -3
+     | 4 | 1 | four  | 5 | -5 | 2 |  4
+     | 4 | 1 | four  | 5 | -5 | 5 | -5
+     | 4 | 1 | four  | 5 | -5 | 5 | -5
+     | 4 | 1 | four  | 5 | -5 | 0 |   
+     | 4 | 1 | four  | 5 | -5 |   |   
+     | 4 | 1 | four  | 5 | -5 |   |  0
+     | 4 | 1 | four  | 5 | -5 | 1 | -1
+     | 4 | 1 | four  | 5 | -5 | 2 |  2
+     | 4 | 1 | four  | 5 | -5 | 3 | -3
+     | 4 | 1 | four  | 5 | -5 | 2 |  4
+     | 4 | 1 | four  | 5 | -5 | 5 | -5
+     | 4 | 1 | four  | 5 | -5 | 5 | -5
+     | 4 | 1 | four  | 5 | -5 | 0 |   
+     | 4 | 1 | four  | 5 | -5 |   |   
+     | 4 | 1 | four  | 5 | -5 |   |  0
+     | 4 | 1 | four  | 0 |    | 1 | -1
+     | 4 | 1 | four  | 0 |    | 2 |  2
+     | 4 | 1 | four  | 0 |    | 3 | -3
+     | 4 | 1 | four  | 0 |    | 2 |  4
+     | 4 | 1 | four  | 0 |    | 5 | -5
+     | 4 | 1 | four  | 0 |    | 5 | -5
+     | 4 | 1 | four  | 0 |    | 0 |   
+     | 4 | 1 | four  | 0 |    |   |   
+     | 4 | 1 | four  | 0 |    |   |  0
+     | 4 | 1 | four  |   |    | 1 | -1
+     | 4 | 1 | four  |   |    | 2 |  2
+     | 4 | 1 | four  |   |    | 3 | -3
+     | 4 | 1 | four  |   |    | 2 |  4
+     | 4 | 1 | four  |   |    | 5 | -5
+     | 4 | 1 | four  |   |    | 5 | -5
+     | 4 | 1 | four  |   |    | 0 |   
+     | 4 | 1 | four  |   |    |   |   
+     | 4 | 1 | four  |   |    |   |  0
+     | 4 | 1 | four  |   |  0 | 1 | -1
+     | 4 | 1 | four  |   |  0 | 2 |  2
+     | 4 | 1 | four  |   |  0 | 3 | -3
+     | 4 | 1 | four  |   |  0 | 2 |  4
+     | 4 | 1 | four  |   |  0 | 5 | -5
+     | 4 | 1 | four  |   |  0 | 5 | -5
+     | 4 | 1 | four  |   |  0 | 0 |   
+     | 4 | 1 | four  |   |  0 |   |   
+     | 4 | 1 | four  |   |  0 |   |  0
+     | 5 | 0 | five  | 1 | -1 | 1 | -1
+     | 5 | 0 | five  | 1 | -1 | 2 |  2
+     | 5 | 0 | five  | 1 | -1 | 3 | -3
+     | 5 | 0 | five  | 1 | -1 | 2 |  4
+     | 5 | 0 | five  | 1 | -1 | 5 | -5
+     | 5 | 0 | five  | 1 | -1 | 5 | -5
+     | 5 | 0 | five  | 1 | -1 | 0 |   
+     | 5 | 0 | five  | 1 | -1 |   |   
+     | 5 | 0 | five  | 1 | -1 |   |  0
+     | 5 | 0 | five  | 2 |  2 | 1 | -1
+     | 5 | 0 | five  | 2 |  2 | 2 |  2
+     | 5 | 0 | five  | 2 |  2 | 3 | -3
+     | 5 | 0 | five  | 2 |  2 | 2 |  4
+     | 5 | 0 | five  | 2 |  2 | 5 | -5
+     | 5 | 0 | five  | 2 |  2 | 5 | -5
+     | 5 | 0 | five  | 2 |  2 | 0 |   
+     | 5 | 0 | five  | 2 |  2 |   |   
+     | 5 | 0 | five  | 2 |  2 |   |  0
+     | 5 | 0 | five  | 3 | -3 | 1 | -1
+     | 5 | 0 | five  | 3 | -3 | 2 |  2
+     | 5 | 0 | five  | 3 | -3 | 3 | -3
+     | 5 | 0 | five  | 3 | -3 | 2 |  4
+     | 5 | 0 | five  | 3 | -3 | 5 | -5
+     | 5 | 0 | five  | 3 | -3 | 5 | -5
+     | 5 | 0 | five  | 3 | -3 | 0 |   
      | 5 | 0 | five  | 3 | -3 |   |   
+     | 5 | 0 | five  | 3 | -3 |   |  0
+     | 5 | 0 | five  | 2 |  4 | 1 | -1
+     | 5 | 0 | five  | 2 |  4 | 2 |  2
+     | 5 | 0 | five  | 2 |  4 | 3 | -3
+     | 5 | 0 | five  | 2 |  4 | 2 |  4
+     | 5 | 0 | five  | 2 |  4 | 5 | -5
+     | 5 | 0 | five  | 2 |  4 | 5 | -5
+     | 5 | 0 | five  | 2 |  4 | 0 |   
+     | 5 | 0 | five  | 2 |  4 |   |   
+     | 5 | 0 | five  | 2 |  4 |   |  0
+     | 5 | 0 | five  | 5 | -5 | 1 | -1
+     | 5 | 0 | five  | 5 | -5 | 2 |  2
+     | 5 | 0 | five  | 5 | -5 | 3 | -3
+     | 5 | 0 | five  | 5 | -5 | 2 |  4
+     | 5 | 0 | five  | 5 | -5 | 5 | -5
+     | 5 | 0 | five  | 5 | -5 | 5 | -5
+     | 5 | 0 | five  | 5 | -5 | 0 |   
+     | 5 | 0 | five  | 5 | -5 |   |   
+     | 5 | 0 | five  | 5 | -5 |   |  0
+     | 5 | 0 | five  | 5 | -5 | 1 | -1
+     | 5 | 0 | five  | 5 | -5 | 2 |  2
+     | 5 | 0 | five  | 5 | -5 | 3 | -3
+     | 5 | 0 | five  | 5 | -5 | 2 |  4
+     | 5 | 0 | five  | 5 | -5 | 5 | -5
+     | 5 | 0 | five  | 5 | -5 | 5 | -5
+     | 5 | 0 | five  | 5 | -5 | 0 |   
+     | 5 | 0 | five  | 5 | -5 |   |   
+     | 5 | 0 | five  | 5 | -5 |   |  0
+     | 5 | 0 | five  | 0 |    | 1 | -1
+     | 5 | 0 | five  | 0 |    | 2 |  2
+     | 5 | 0 | five  | 0 |    | 3 | -3
+     | 5 | 0 | five  | 0 |    | 2 |  4
+     | 5 | 0 | five  | 0 |    | 5 | -5
+     | 5 | 0 | five  | 0 |    | 5 | -5
+     | 5 | 0 | five  | 0 |    | 0 |   
+     | 5 | 0 | five  | 0 |    |   |   
+     | 5 | 0 | five  | 0 |    |   |  0
+     | 5 | 0 | five  |   |    | 1 | -1
+     | 5 | 0 | five  |   |    | 2 |  2
+     | 5 | 0 | five  |   |    | 3 | -3
+     | 5 | 0 | five  |   |    | 2 |  4
+     | 5 | 0 | five  |   |    | 5 | -5
+     | 5 | 0 | five  |   |    | 5 | -5
+     | 5 | 0 | five  |   |    | 0 |   
+     | 5 | 0 | five  |   |    |   |   
+     | 5 | 0 | five  |   |    |   |  0
+     | 5 | 0 | five  |   |  0 | 1 | -1
+     | 5 | 0 | five  |   |  0 | 2 |  2
+     | 5 | 0 | five  |   |  0 | 3 | -3
+     | 5 | 0 | five  |   |  0 | 2 |  4
+     | 5 | 0 | five  |   |  0 | 5 | -5
+     | 5 | 0 | five  |   |  0 | 5 | -5
+     | 5 | 0 | five  |   |  0 | 0 |   
+     | 5 | 0 | five  |   |  0 |   |   
+     | 5 | 0 | five  |   |  0 |   |  0
+     | 6 | 6 | six   | 1 | -1 | 1 | -1
+     | 6 | 6 | six   | 1 | -1 | 2 |  2
+     | 6 | 6 | six   | 1 | -1 | 3 | -3
+     | 6 | 6 | six   | 1 | -1 | 2 |  4
+     | 6 | 6 | six   | 1 | -1 | 5 | -5
+     | 6 | 6 | six   | 1 | -1 | 5 | -5
+     | 6 | 6 | six   | 1 | -1 | 0 |   
+     | 6 | 6 | six   | 1 | -1 |   |   
+     | 6 | 6 | six   | 1 | -1 |   |  0
+     | 6 | 6 | six   | 2 |  2 | 1 | -1
+     | 6 | 6 | six   | 2 |  2 | 2 |  2
+     | 6 | 6 | six   | 2 |  2 | 3 | -3
+     | 6 | 6 | six   | 2 |  2 | 2 |  4
+     | 6 | 6 | six   | 2 |  2 | 5 | -5
+     | 6 | 6 | six   | 2 |  2 | 5 | -5
+     | 6 | 6 | six   | 2 |  2 | 0 |   
+     | 6 | 6 | six   | 2 |  2 |   |   
+     | 6 | 6 | six   | 2 |  2 |   |  0
+     | 6 | 6 | six   | 3 | -3 | 1 | -1
+     | 6 | 6 | six   | 3 | -3 | 2 |  2
+     | 6 | 6 | six   | 3 | -3 | 3 | -3
+     | 6 | 6 | six   | 3 | -3 | 2 |  4
+     | 6 | 6 | six   | 3 | -3 | 5 | -5
+     | 6 | 6 | six   | 3 | -3 | 5 | -5
+     | 6 | 6 | six   | 3 | -3 | 0 |   
      | 6 | 6 | six   | 3 | -3 |   |   
+     | 6 | 6 | six   | 3 | -3 |   |  0
+     | 6 | 6 | six   | 2 |  4 | 1 | -1
+     | 6 | 6 | six   | 2 |  4 | 2 |  2
+     | 6 | 6 | six   | 2 |  4 | 3 | -3
+     | 6 | 6 | six   | 2 |  4 | 2 |  4
+     | 6 | 6 | six   | 2 |  4 | 5 | -5
+     | 6 | 6 | six   | 2 |  4 | 5 | -5
+     | 6 | 6 | six   | 2 |  4 | 0 |   
+     | 6 | 6 | six   | 2 |  4 |   |   
+     | 6 | 6 | six   | 2 |  4 |   |  0
+     | 6 | 6 | six   | 5 | -5 | 1 | -1
+     | 6 | 6 | six   | 5 | -5 | 2 |  2
+     | 6 | 6 | six   | 5 | -5 | 3 | -3
+     | 6 | 6 | six   | 5 | -5 | 2 |  4
+     | 6 | 6 | six   | 5 | -5 | 5 | -5
+     | 6 | 6 | six   | 5 | -5 | 5 | -5
+     | 6 | 6 | six   | 5 | -5 | 0 |   
+     | 6 | 6 | six   | 5 | -5 |   |   
+     | 6 | 6 | six   | 5 | -5 |   |  0
+     | 6 | 6 | six   | 5 | -5 | 1 | -1
+     | 6 | 6 | six   | 5 | -5 | 2 |  2
+     | 6 | 6 | six   | 5 | -5 | 3 | -3
+     | 6 | 6 | six   | 5 | -5 | 2 |  4
+     | 6 | 6 | six   | 5 | -5 | 5 | -5
+     | 6 | 6 | six   | 5 | -5 | 5 | -5
+     | 6 | 6 | six   | 5 | -5 | 0 |   
+     | 6 | 6 | six   | 5 | -5 |   |   
+     | 6 | 6 | six   | 5 | -5 |   |  0
+     | 6 | 6 | six   | 0 |    | 1 | -1
+     | 6 | 6 | six   | 0 |    | 2 |  2
+     | 6 | 6 | six   | 0 |    | 3 | -3
+     | 6 | 6 | six   | 0 |    | 2 |  4
+     | 6 | 6 | six   | 0 |    | 5 | -5
+     | 6 | 6 | six   | 0 |    | 5 | -5
+     | 6 | 6 | six   | 0 |    | 0 |   
+     | 6 | 6 | six   | 0 |    |   |   
+     | 6 | 6 | six   | 0 |    |   |  0
+     | 6 | 6 | six   |   |    | 1 | -1
+     | 6 | 6 | six   |   |    | 2 |  2
+     | 6 | 6 | six   |   |    | 3 | -3
+     | 6 | 6 | six   |   |    | 2 |  4
+     | 6 | 6 | six   |   |    | 5 | -5
+     | 6 | 6 | six   |   |    | 5 | -5
+     | 6 | 6 | six   |   |    | 0 |   
+     | 6 | 6 | six   |   |    |   |   
+     | 6 | 6 | six   |   |    |   |  0
+     | 6 | 6 | six   |   |  0 | 1 | -1
+     | 6 | 6 | six   |   |  0 | 2 |  2
+     | 6 | 6 | six   |   |  0 | 3 | -3
+     | 6 | 6 | six   |   |  0 | 2 |  4
+     | 6 | 6 | six   |   |  0 | 5 | -5
+     | 6 | 6 | six   |   |  0 | 5 | -5
+     | 6 | 6 | six   |   |  0 | 0 |   
+     | 6 | 6 | six   |   |  0 |   |   
+     | 6 | 6 | six   |   |  0 |   |  0
+     | 7 | 7 | seven | 1 | -1 | 1 | -1
+     | 7 | 7 | seven | 1 | -1 | 2 |  2
+     | 7 | 7 | seven | 1 | -1 | 3 | -3
+     | 7 | 7 | seven | 1 | -1 | 2 |  4
+     | 7 | 7 | seven | 1 | -1 | 5 | -5
+     | 7 | 7 | seven | 1 | -1 | 5 | -5
+     | 7 | 7 | seven | 1 | -1 | 0 |   
+     | 7 | 7 | seven | 1 | -1 |   |   
+     | 7 | 7 | seven | 1 | -1 |   |  0
+     | 7 | 7 | seven | 2 |  2 | 1 | -1
+     | 7 | 7 | seven | 2 |  2 | 2 |  2
+     | 7 | 7 | seven | 2 |  2 | 3 | -3
+     | 7 | 7 | seven | 2 |  2 | 2 |  4
+     | 7 | 7 | seven | 2 |  2 | 5 | -5
+     | 7 | 7 | seven | 2 |  2 | 5 | -5
+     | 7 | 7 | seven | 2 |  2 | 0 |   
+     | 7 | 7 | seven | 2 |  2 |   |   
+     | 7 | 7 | seven | 2 |  2 |   |  0
+     | 7 | 7 | seven | 3 | -3 | 1 | -1
+     | 7 | 7 | seven | 3 | -3 | 2 |  2
+     | 7 | 7 | seven | 3 | -3 | 3 | -3
+     | 7 | 7 | seven | 3 | -3 | 2 |  4
+     | 7 | 7 | seven | 3 | -3 | 5 | -5
+     | 7 | 7 | seven | 3 | -3 | 5 | -5
+     | 7 | 7 | seven | 3 | -3 | 0 |   
      | 7 | 7 | seven | 3 | -3 |   |   
+     | 7 | 7 | seven | 3 | -3 |   |  0
+     | 7 | 7 | seven | 2 |  4 | 1 | -1
+     | 7 | 7 | seven | 2 |  4 | 2 |  2
+     | 7 | 7 | seven | 2 |  4 | 3 | -3
+     | 7 | 7 | seven | 2 |  4 | 2 |  4
+     | 7 | 7 | seven | 2 |  4 | 5 | -5
+     | 7 | 7 | seven | 2 |  4 | 5 | -5
+     | 7 | 7 | seven | 2 |  4 | 0 |   
+     | 7 | 7 | seven | 2 |  4 |   |   
+     | 7 | 7 | seven | 2 |  4 |   |  0
+     | 7 | 7 | seven | 5 | -5 | 1 | -1
+     | 7 | 7 | seven | 5 | -5 | 2 |  2
+     | 7 | 7 | seven | 5 | -5 | 3 | -3
+     | 7 | 7 | seven | 5 | -5 | 2 |  4
+     | 7 | 7 | seven | 5 | -5 | 5 | -5
+     | 7 | 7 | seven | 5 | -5 | 5 | -5
+     | 7 | 7 | seven | 5 | -5 | 0 |   
+     | 7 | 7 | seven | 5 | -5 |   |   
+     | 7 | 7 | seven | 5 | -5 |   |  0
+     | 7 | 7 | seven | 5 | -5 | 1 | -1
+     | 7 | 7 | seven | 5 | -5 | 2 |  2
+     | 7 | 7 | seven | 5 | -5 | 3 | -3
+     | 7 | 7 | seven | 5 | -5 | 2 |  4
+     | 7 | 7 | seven | 5 | -5 | 5 | -5
+     | 7 | 7 | seven | 5 | -5 | 5 | -5
+     | 7 | 7 | seven | 5 | -5 | 0 |   
+     | 7 | 7 | seven | 5 | -5 |   |   
+     | 7 | 7 | seven | 5 | -5 |   |  0
+     | 7 | 7 | seven | 0 |    | 1 | -1
+     | 7 | 7 | seven | 0 |    | 2 |  2
+     | 7 | 7 | seven | 0 |    | 3 | -3
+     | 7 | 7 | seven | 0 |    | 2 |  4
+     | 7 | 7 | seven | 0 |    | 5 | -5
+     | 7 | 7 | seven | 0 |    | 5 | -5
+     | 7 | 7 | seven | 0 |    | 0 |   
+     | 7 | 7 | seven | 0 |    |   |   
+     | 7 | 7 | seven | 0 |    |   |  0
+     | 7 | 7 | seven |   |    | 1 | -1
+     | 7 | 7 | seven |   |    | 2 |  2
+     | 7 | 7 | seven |   |    | 3 | -3
+     | 7 | 7 | seven |   |    | 2 |  4
+     | 7 | 7 | seven |   |    | 5 | -5
+     | 7 | 7 | seven |   |    | 5 | -5
+     | 7 | 7 | seven |   |    | 0 |   
+     | 7 | 7 | seven |   |    |   |   
+     | 7 | 7 | seven |   |    |   |  0
+     | 7 | 7 | seven |   |  0 | 1 | -1
+     | 7 | 7 | seven |   |  0 | 2 |  2
+     | 7 | 7 | seven |   |  0 | 3 | -3
+     | 7 | 7 | seven |   |  0 | 2 |  4
+     | 7 | 7 | seven |   |  0 | 5 | -5
+     | 7 | 7 | seven |   |  0 | 5 | -5
+     | 7 | 7 | seven |   |  0 | 0 |   
+     | 7 | 7 | seven |   |  0 |   |   
+     | 7 | 7 | seven |   |  0 |   |  0
+     | 8 | 8 | eight | 1 | -1 | 1 | -1
+     | 8 | 8 | eight | 1 | -1 | 2 |  2
+     | 8 | 8 | eight | 1 | -1 | 3 | -3
+     | 8 | 8 | eight | 1 | -1 | 2 |  4
+     | 8 | 8 | eight | 1 | -1 | 5 | -5
+     | 8 | 8 | eight | 1 | -1 | 5 | -5
+     | 8 | 8 | eight | 1 | -1 | 0 |   
+     | 8 | 8 | eight | 1 | -1 |   |   
+     | 8 | 8 | eight | 1 | -1 |   |  0
+     | 8 | 8 | eight | 2 |  2 | 1 | -1
+     | 8 | 8 | eight | 2 |  2 | 2 |  2
+     | 8 | 8 | eight | 2 |  2 | 3 | -3
+     | 8 | 8 | eight | 2 |  2 | 2 |  4
+     | 8 | 8 | eight | 2 |  2 | 5 | -5
+     | 8 | 8 | eight | 2 |  2 | 5 | -5
+     | 8 | 8 | eight | 2 |  2 | 0 |   
+     | 8 | 8 | eight | 2 |  2 |   |   
+     | 8 | 8 | eight | 2 |  2 |   |  0
+     | 8 | 8 | eight | 3 | -3 | 1 | -1
+     | 8 | 8 | eight | 3 | -3 | 2 |  2
+     | 8 | 8 | eight | 3 | -3 | 3 | -3
+     | 8 | 8 | eight | 3 | -3 | 2 |  4
+     | 8 | 8 | eight | 3 | -3 | 5 | -5
+     | 8 | 8 | eight | 3 | -3 | 5 | -5
+     | 8 | 8 | eight | 3 | -3 | 0 |   
      | 8 | 8 | eight | 3 | -3 |   |   
+     | 8 | 8 | eight | 3 | -3 |   |  0
+     | 8 | 8 | eight | 2 |  4 | 1 | -1
+     | 8 | 8 | eight | 2 |  4 | 2 |  2
+     | 8 | 8 | eight | 2 |  4 | 3 | -3
+     | 8 | 8 | eight | 2 |  4 | 2 |  4
+     | 8 | 8 | eight | 2 |  4 | 5 | -5
+     | 8 | 8 | eight | 2 |  4 | 5 | -5
+     | 8 | 8 | eight | 2 |  4 | 0 |   
+     | 8 | 8 | eight | 2 |  4 |   |   
+     | 8 | 8 | eight | 2 |  4 |   |  0
+     | 8 | 8 | eight | 5 | -5 | 1 | -1
+     | 8 | 8 | eight | 5 | -5 | 2 |  2
+     | 8 | 8 | eight | 5 | -5 | 3 | -3
+     | 8 | 8 | eight | 5 | -5 | 2 |  4
+     | 8 | 8 | eight | 5 | -5 | 5 | -5
+     | 8 | 8 | eight | 5 | -5 | 5 | -5
+     | 8 | 8 | eight | 5 | -5 | 0 |   
+     | 8 | 8 | eight | 5 | -5 |   |   
+     | 8 | 8 | eight | 5 | -5 |   |  0
+     | 8 | 8 | eight | 5 | -5 | 1 | -1
+     | 8 | 8 | eight | 5 | -5 | 2 |  2
+     | 8 | 8 | eight | 5 | -5 | 3 | -3
+     | 8 | 8 | eight | 5 | -5 | 2 |  4
+     | 8 | 8 | eight | 5 | -5 | 5 | -5
+     | 8 | 8 | eight | 5 | -5 | 5 | -5
+     | 8 | 8 | eight | 5 | -5 | 0 |   
+     | 8 | 8 | eight | 5 | -5 |   |   
+     | 8 | 8 | eight | 5 | -5 |   |  0
+     | 8 | 8 | eight | 0 |    | 1 | -1
+     | 8 | 8 | eight | 0 |    | 2 |  2
+     | 8 | 8 | eight | 0 |    | 3 | -3
+     | 8 | 8 | eight | 0 |    | 2 |  4
+     | 8 | 8 | eight | 0 |    | 5 | -5
+     | 8 | 8 | eight | 0 |    | 5 | -5
+     | 8 | 8 | eight | 0 |    | 0 |   
+     | 8 | 8 | eight | 0 |    |   |   
+     | 8 | 8 | eight | 0 |    |   |  0
+     | 8 | 8 | eight |   |    | 1 | -1
+     | 8 | 8 | eight |   |    | 2 |  2
+     | 8 | 8 | eight |   |    | 3 | -3
+     | 8 | 8 | eight |   |    | 2 |  4
+     | 8 | 8 | eight |   |    | 5 | -5
+     | 8 | 8 | eight |   |    | 5 | -5
+     | 8 | 8 | eight |   |    | 0 |   
+     | 8 | 8 | eight |   |    |   |   
+     | 8 | 8 | eight |   |    |   |  0
+     | 8 | 8 | eight |   |  0 | 1 | -1
+     | 8 | 8 | eight |   |  0 | 2 |  2
+     | 8 | 8 | eight |   |  0 | 3 | -3
+     | 8 | 8 | eight |   |  0 | 2 |  4
+     | 8 | 8 | eight |   |  0 | 5 | -5
+     | 8 | 8 | eight |   |  0 | 5 | -5
+     | 8 | 8 | eight |   |  0 | 0 |   
+     | 8 | 8 | eight |   |  0 |   |   
+     | 8 | 8 | eight |   |  0 |   |  0
+     | 0 |   | zero  | 1 | -1 | 1 | -1
+     | 0 |   | zero  | 1 | -1 | 2 |  2
+     | 0 |   | zero  | 1 | -1 | 3 | -3
+     | 0 |   | zero  | 1 | -1 | 2 |  4
+     | 0 |   | zero  | 1 | -1 | 5 | -5
+     | 0 |   | zero  | 1 | -1 | 5 | -5
+     | 0 |   | zero  | 1 | -1 | 0 |   
+     | 0 |   | zero  | 1 | -1 |   |   
+     | 0 |   | zero  | 1 | -1 |   |  0
+     | 0 |   | zero  | 2 |  2 | 1 | -1
+     | 0 |   | zero  | 2 |  2 | 2 |  2
+     | 0 |   | zero  | 2 |  2 | 3 | -3
+     | 0 |   | zero  | 2 |  2 | 2 |  4
+     | 0 |   | zero  | 2 |  2 | 5 | -5
+     | 0 |   | zero  | 2 |  2 | 5 | -5
+     | 0 |   | zero  | 2 |  2 | 0 |   
+     | 0 |   | zero  | 2 |  2 |   |   
+     | 0 |   | zero  | 2 |  2 |   |  0
+     | 0 |   | zero  | 3 | -3 | 1 | -1
+     | 0 |   | zero  | 3 | -3 | 2 |  2
+     | 0 |   | zero  | 3 | -3 | 3 | -3
+     | 0 |   | zero  | 3 | -3 | 2 |  4
+     | 0 |   | zero  | 3 | -3 | 5 | -5
+     | 0 |   | zero  | 3 | -3 | 5 | -5
+     | 0 |   | zero  | 3 | -3 | 0 |   
      | 0 |   | zero  | 3 | -3 |   |   
-     |   |   | null  | 3 | -3 |   |   
-     |   | 0 | zero  | 3 | -3 |   |   
-     | 1 | 4 | one   | 3 | -3 |   |  0
-     | 2 | 3 | two   | 3 | -3 |   |  0
-     | 3 | 2 | three | 3 | -3 |   |  0
-     | 4 | 1 | four  | 3 | -3 |   |  0
-     | 5 | 0 | five  | 3 | -3 |   |  0
-     | 6 | 6 | six   | 3 | -3 |   |  0
-     | 7 | 7 | seven | 3 | -3 |   |  0
-     | 8 | 8 | eight | 3 | -3 |   |  0
      | 0 |   | zero  | 3 | -3 |   |  0
-     |   |   | null  | 3 | -3 |   |  0
-     |   | 0 | zero  | 3 | -3 |   |  0
-     | 1 | 4 | one   | 2 |  4 | 1 | -1
-     | 2 | 3 | two   | 2 |  4 | 1 | -1
-     | 3 | 2 | three | 2 |  4 | 1 | -1
-     | 4 | 1 | four  | 2 |  4 | 1 | -1
-     | 5 | 0 | five  | 2 |  4 | 1 | -1
-     | 6 | 6 | six   | 2 |  4 | 1 | -1
-     | 7 | 7 | seven | 2 |  4 | 1 | -1
-     | 8 | 8 | eight | 2 |  4 | 1 | -1
      | 0 |   | zero  | 2 |  4 | 1 | -1
-     |   |   | null  | 2 |  4 | 1 | -1
-     |   | 0 | zero  | 2 |  4 | 1 | -1
-     | 1 | 4 | one   | 2 |  4 | 2 |  2
-     | 2 | 3 | two   | 2 |  4 | 2 |  2
-     | 3 | 2 | three | 2 |  4 | 2 |  2
-     | 4 | 1 | four  | 2 |  4 | 2 |  2
-     | 5 | 0 | five  | 2 |  4 | 2 |  2
-     | 6 | 6 | six   | 2 |  4 | 2 |  2
-     | 7 | 7 | seven | 2 |  4 | 2 |  2
-     | 8 | 8 | eight | 2 |  4 | 2 |  2
      | 0 |   | zero  | 2 |  4 | 2 |  2
-     |   |   | null  | 2 |  4 | 2 |  2
-     |   | 0 | zero  | 2 |  4 | 2 |  2
-     | 1 | 4 | one   | 2 |  4 | 3 | -3
-     | 2 | 3 | two   | 2 |  4 | 3 | -3
-     | 3 | 2 | three | 2 |  4 | 3 | -3
-     | 4 | 1 | four  | 2 |  4 | 3 | -3
-     | 5 | 0 | five  | 2 |  4 | 3 | -3
-     | 6 | 6 | six   | 2 |  4 | 3 | -3
-     | 7 | 7 | seven | 2 |  4 | 3 | -3
-     | 8 | 8 | eight | 2 |  4 | 3 | -3
      | 0 |   | zero  | 2 |  4 | 3 | -3
-     |   |   | null  | 2 |  4 | 3 | -3
-     |   | 0 | zero  | 2 |  4 | 3 | -3
-     | 1 | 4 | one   | 2 |  4 | 2 |  4
-     | 2 | 3 | two   | 2 |  4 | 2 |  4
-     | 3 | 2 | three | 2 |  4 | 2 |  4
-     | 4 | 1 | four  | 2 |  4 | 2 |  4
-     | 5 | 0 | five  | 2 |  4 | 2 |  4
-     | 6 | 6 | six   | 2 |  4 | 2 |  4
-     | 7 | 7 | seven | 2 |  4 | 2 |  4
-     | 8 | 8 | eight | 2 |  4 | 2 |  4
      | 0 |   | zero  | 2 |  4 | 2 |  4
-     |   |   | null  | 2 |  4 | 2 |  4
-     |   | 0 | zero  | 2 |  4 | 2 |  4
-     | 1 | 4 | one   | 2 |  4 | 5 | -5
-     | 2 | 3 | two   | 2 |  4 | 5 | -5
-     | 3 | 2 | three | 2 |  4 | 5 | -5
-     | 4 | 1 | four  | 2 |  4 | 5 | -5
-     | 5 | 0 | five  | 2 |  4 | 5 | -5
-     | 6 | 6 | six   | 2 |  4 | 5 | -5
-     | 7 | 7 | seven | 2 |  4 | 5 | -5
-     | 8 | 8 | eight | 2 |  4 | 5 | -5
      | 0 |   | zero  | 2 |  4 | 5 | -5
-     |   |   | null  | 2 |  4 | 5 | -5
-     |   | 0 | zero  | 2 |  4 | 5 | -5
-     | 1 | 4 | one   | 2 |  4 | 5 | -5
-     | 2 | 3 | two   | 2 |  4 | 5 | -5
-     | 3 | 2 | three | 2 |  4 | 5 | -5
-     | 4 | 1 | four  | 2 |  4 | 5 | -5
-     | 5 | 0 | five  | 2 |  4 | 5 | -5
-     | 6 | 6 | six   | 2 |  4 | 5 | -5
-     | 7 | 7 | seven | 2 |  4 | 5 | -5
-     | 8 | 8 | eight | 2 |  4 | 5 | -5
      | 0 |   | zero  | 2 |  4 | 5 | -5
-     |   |   | null  | 2 |  4 | 5 | -5
-     |   | 0 | zero  | 2 |  4 | 5 | -5
-     | 1 | 4 | one   | 2 |  4 | 0 |   
-     | 2 | 3 | two   | 2 |  4 | 0 |   
-     | 3 | 2 | three | 2 |  4 | 0 |   
-     | 4 | 1 | four  | 2 |  4 | 0 |   
-     | 5 | 0 | five  | 2 |  4 | 0 |   
-     | 6 | 6 | six   | 2 |  4 | 0 |   
-     | 7 | 7 | seven | 2 |  4 | 0 |   
-     | 8 | 8 | eight | 2 |  4 | 0 |   
      | 0 |   | zero  | 2 |  4 | 0 |   
+     | 0 |   | zero  | 2 |  4 |   |   
+     | 0 |   | zero  | 2 |  4 |   |  0
+     | 0 |   | zero  | 5 | -5 | 1 | -1
+     | 0 |   | zero  | 5 | -5 | 2 |  2
+     | 0 |   | zero  | 5 | -5 | 3 | -3
+     | 0 |   | zero  | 5 | -5 | 2 |  4
+     | 0 |   | zero  | 5 | -5 | 5 | -5
+     | 0 |   | zero  | 5 | -5 | 5 | -5
+     | 0 |   | zero  | 5 | -5 | 0 |   
+     | 0 |   | zero  | 5 | -5 |   |   
+     | 0 |   | zero  | 5 | -5 |   |  0
+     | 0 |   | zero  | 5 | -5 | 1 | -1
+     | 0 |   | zero  | 5 | -5 | 2 |  2
+     | 0 |   | zero  | 5 | -5 | 3 | -3
+     | 0 |   | zero  | 5 | -5 | 2 |  4
+     | 0 |   | zero  | 5 | -5 | 5 | -5
+     | 0 |   | zero  | 5 | -5 | 5 | -5
+     | 0 |   | zero  | 5 | -5 | 0 |   
+     | 0 |   | zero  | 5 | -5 |   |   
+     | 0 |   | zero  | 5 | -5 |   |  0
+     | 0 |   | zero  | 0 |    | 1 | -1
+     | 0 |   | zero  | 0 |    | 2 |  2
+     | 0 |   | zero  | 0 |    | 3 | -3
+     | 0 |   | zero  | 0 |    | 2 |  4
+     | 0 |   | zero  | 0 |    | 5 | -5
+     | 0 |   | zero  | 0 |    | 5 | -5
+     | 0 |   | zero  | 0 |    | 0 |   
+     | 0 |   | zero  | 0 |    |   |   
+     | 0 |   | zero  | 0 |    |   |  0
+     | 0 |   | zero  |   |    | 1 | -1
+     | 0 |   | zero  |   |    | 2 |  2
+     | 0 |   | zero  |   |    | 3 | -3
+     | 0 |   | zero  |   |    | 2 |  4
+     | 0 |   | zero  |   |    | 5 | -5
+     | 0 |   | zero  |   |    | 5 | -5
+     | 0 |   | zero  |   |    | 0 |   
+     | 0 |   | zero  |   |    |   |   
+     | 0 |   | zero  |   |    |   |  0
+     | 0 |   | zero  |   |  0 | 1 | -1
+     | 0 |   | zero  |   |  0 | 2 |  2
+     | 0 |   | zero  |   |  0 | 3 | -3
+     | 0 |   | zero  |   |  0 | 2 |  4
+     | 0 |   | zero  |   |  0 | 5 | -5
+     | 0 |   | zero  |   |  0 | 5 | -5
+     | 0 |   | zero  |   |  0 | 0 |   
+     | 0 |   | zero  |   |  0 |   |   
+     | 0 |   | zero  |   |  0 |   |  0
+     |   |   | null  | 1 | -1 | 1 | -1
+     |   |   | null  | 1 | -1 | 2 |  2
+     |   |   | null  | 1 | -1 | 3 | -3
+     |   |   | null  | 1 | -1 | 2 |  4
+     |   |   | null  | 1 | -1 | 5 | -5
+     |   |   | null  | 1 | -1 | 5 | -5
+     |   |   | null  | 1 | -1 | 0 |   
+     |   |   | null  | 1 | -1 |   |   
+     |   |   | null  | 1 | -1 |   |  0
+     |   |   | null  | 2 |  2 | 1 | -1
+     |   |   | null  | 2 |  2 | 2 |  2
+     |   |   | null  | 2 |  2 | 3 | -3
+     |   |   | null  | 2 |  2 | 2 |  4
+     |   |   | null  | 2 |  2 | 5 | -5
+     |   |   | null  | 2 |  2 | 5 | -5
+     |   |   | null  | 2 |  2 | 0 |   
+     |   |   | null  | 2 |  2 |   |   
+     |   |   | null  | 2 |  2 |   |  0
+     |   |   | null  | 3 | -3 | 1 | -1
+     |   |   | null  | 3 | -3 | 2 |  2
+     |   |   | null  | 3 | -3 | 3 | -3
+     |   |   | null  | 3 | -3 | 2 |  4
+     |   |   | null  | 3 | -3 | 5 | -5
+     |   |   | null  | 3 | -3 | 5 | -5
+     |   |   | null  | 3 | -3 | 0 |   
+     |   |   | null  | 3 | -3 |   |   
+     |   |   | null  | 3 | -3 |   |  0
+     |   |   | null  | 2 |  4 | 1 | -1
+     |   |   | null  | 2 |  4 | 2 |  2
+     |   |   | null  | 2 |  4 | 3 | -3
+     |   |   | null  | 2 |  4 | 2 |  4
+     |   |   | null  | 2 |  4 | 5 | -5
+     |   |   | null  | 2 |  4 | 5 | -5
      |   |   | null  | 2 |  4 | 0 |   
+     |   |   | null  | 2 |  4 |   |   
+     |   |   | null  | 2 |  4 |   |  0
+     |   |   | null  | 5 | -5 | 1 | -1
+     |   |   | null  | 5 | -5 | 2 |  2
+     |   |   | null  | 5 | -5 | 3 | -3
+     |   |   | null  | 5 | -5 | 2 |  4
+     |   |   | null  | 5 | -5 | 5 | -5
+     |   |   | null  | 5 | -5 | 5 | -5
+     |   |   | null  | 5 | -5 | 0 |   
+     |   |   | null  | 5 | -5 |   |   
+     |   |   | null  | 5 | -5 |   |  0
+     |   |   | null  | 5 | -5 | 1 | -1
+     |   |   | null  | 5 | -5 | 2 |  2
+     |   |   | null  | 5 | -5 | 3 | -3
+     |   |   | null  | 5 | -5 | 2 |  4
+     |   |   | null  | 5 | -5 | 5 | -5
+     |   |   | null  | 5 | -5 | 5 | -5
+     |   |   | null  | 5 | -5 | 0 |   
+     |   |   | null  | 5 | -5 |   |   
+     |   |   | null  | 5 | -5 |   |  0
+     |   |   | null  | 0 |    | 1 | -1
+     |   |   | null  | 0 |    | 2 |  2
+     |   |   | null  | 0 |    | 3 | -3
+     |   |   | null  | 0 |    | 2 |  4
+     |   |   | null  | 0 |    | 5 | -5
+     |   |   | null  | 0 |    | 5 | -5
+     |   |   | null  | 0 |    | 0 |   
+     |   |   | null  | 0 |    |   |   
+     |   |   | null  | 0 |    |   |  0
+     |   |   | null  |   |    | 1 | -1
+     |   |   | null  |   |    | 2 |  2
+     |   |   | null  |   |    | 3 | -3
+     |   |   | null  |   |    | 2 |  4
+     |   |   | null  |   |    | 5 | -5
+     |   |   | null  |   |    | 5 | -5
+     |   |   | null  |   |    | 0 |   
+     |   |   | null  |   |    |   |   
+     |   |   | null  |   |    |   |  0
+     |   |   | null  |   |  0 | 1 | -1
+     |   |   | null  |   |  0 | 2 |  2
+     |   |   | null  |   |  0 | 3 | -3
+     |   |   | null  |   |  0 | 2 |  4
+     |   |   | null  |   |  0 | 5 | -5
+     |   |   | null  |   |  0 | 5 | -5
+     |   |   | null  |   |  0 | 0 |   
+     |   |   | null  |   |  0 |   |   
+     |   |   | null  |   |  0 |   |  0
+     |   | 0 | zero  | 1 | -1 | 1 | -1
+     |   | 0 | zero  | 1 | -1 | 2 |  2
+     |   | 0 | zero  | 1 | -1 | 3 | -3
+     |   | 0 | zero  | 1 | -1 | 2 |  4
+     |   | 0 | zero  | 1 | -1 | 5 | -5
+     |   | 0 | zero  | 1 | -1 | 5 | -5
+     |   | 0 | zero  | 1 | -1 | 0 |   
+     |   | 0 | zero  | 1 | -1 |   |   
+     |   | 0 | zero  | 1 | -1 |   |  0
+     |   | 0 | zero  | 2 |  2 | 1 | -1
+     |   | 0 | zero  | 2 |  2 | 2 |  2
+     |   | 0 | zero  | 2 |  2 | 3 | -3
+     |   | 0 | zero  | 2 |  2 | 2 |  4
+     |   | 0 | zero  | 2 |  2 | 5 | -5
+     |   | 0 | zero  | 2 |  2 | 5 | -5
+     |   | 0 | zero  | 2 |  2 | 0 |   
+     |   | 0 | zero  | 2 |  2 |   |   
+     |   | 0 | zero  | 2 |  2 |   |  0
+     |   | 0 | zero  | 3 | -3 | 1 | -1
+     |   | 0 | zero  | 3 | -3 | 2 |  2
+     |   | 0 | zero  | 3 | -3 | 3 | -3
+     |   | 0 | zero  | 3 | -3 | 2 |  4
+     |   | 0 | zero  | 3 | -3 | 5 | -5
+     |   | 0 | zero  | 3 | -3 | 5 | -5
+     |   | 0 | zero  | 3 | -3 | 0 |   
+     |   | 0 | zero  | 3 | -3 |   |   
+     |   | 0 | zero  | 3 | -3 |   |  0
+     |   | 0 | zero  | 2 |  4 | 1 | -1
+     |   | 0 | zero  | 2 |  4 | 2 |  2
+     |   | 0 | zero  | 2 |  4 | 3 | -3
+     |   | 0 | zero  | 2 |  4 | 2 |  4
+     |   | 0 | zero  | 2 |  4 | 5 | -5
+     |   | 0 | zero  | 2 |  4 | 5 | -5
      |   | 0 | zero  | 2 |  4 | 0 |   
-     | 1 | 4 | one   | 2 |  4 |   |   
-     | 2 | 3 | two   | 2 |  4 |   |   
-     | 3 | 2 | three | 2 |  4 |   |   
-     | 4 | 1 | four  | 2 |  4 |   |   
-     | 5 | 0 | five  | 2 |  4 |   |   
-     | 6 | 6 | six   | 2 |  4 |   |   
-     | 7 | 7 | seven | 2 |  4 |   |   
-     | 8 | 8 | eight | 2 |  4 |   |   
-     | 0 |   | zero  | 2 |  4 |   |   
-     |   |   | null  | 2 |  4 |   |   
      |   | 0 | zero  | 2 |  4 |   |   
-     | 1 | 4 | one   | 2 |  4 |   |  0
-     | 2 | 3 | two   | 2 |  4 |   |  0
-     | 3 | 2 | three | 2 |  4 |   |  0
-     | 4 | 1 | four  | 2 |  4 |   |  0
-     | 5 | 0 | five  | 2 |  4 |   |  0
-     | 6 | 6 | six   | 2 |  4 |   |  0
-     | 7 | 7 | seven | 2 |  4 |   |  0
-     | 8 | 8 | eight | 2 |  4 |   |  0
-     | 0 |   | zero  | 2 |  4 |   |  0
-     |   |   | null  | 2 |  4 |   |  0
      |   | 0 | zero  | 2 |  4 |   |  0
-     | 1 | 4 | one   | 5 | -5 | 1 | -1
-     | 2 | 3 | two   | 5 | -5 | 1 | -1
-     | 3 | 2 | three | 5 | -5 | 1 | -1
-     | 4 | 1 | four  | 5 | -5 | 1 | -1
-     | 5 | 0 | five  | 5 | -5 | 1 | -1
-     | 6 | 6 | six   | 5 | -5 | 1 | -1
-     | 7 | 7 | seven | 5 | -5 | 1 | -1
-     | 8 | 8 | eight | 5 | -5 | 1 | -1
-     | 0 |   | zero  | 5 | -5 | 1 | -1
-     |   |   | null  | 5 | -5 | 1 | -1
      |   | 0 | zero  | 5 | -5 | 1 | -1
-     | 1 | 4 | one   | 5 | -5 | 2 |  2
-     | 2 | 3 | two   | 5 | -5 | 2 |  2
-     | 3 | 2 | three | 5 | -5 | 2 |  2
-     | 4 | 1 | four  | 5 | -5 | 2 |  2
-     | 5 | 0 | five  | 5 | -5 | 2 |  2
-     | 6 | 6 | six   | 5 | -5 | 2 |  2
-     | 7 | 7 | seven | 5 | -5 | 2 |  2
-     | 8 | 8 | eight | 5 | -5 | 2 |  2
-     | 0 |   | zero  | 5 | -5 | 2 |  2
-     |   |   | null  | 5 | -5 | 2 |  2
      |   | 0 | zero  | 5 | -5 | 2 |  2
-     | 1 | 4 | one   | 5 | -5 | 3 | -3
-     | 2 | 3 | two   | 5 | -5 | 3 | -3
-     | 3 | 2 | three | 5 | -5 | 3 | -3
-     | 4 | 1 | four  | 5 | -5 | 3 | -3
-     | 5 | 0 | five  | 5 | -5 | 3 | -3
-     | 6 | 6 | six   | 5 | -5 | 3 | -3
-     | 7 | 7 | seven | 5 | -5 | 3 | -3
-     | 8 | 8 | eight | 5 | -5 | 3 | -3
-     | 0 |   | zero  | 5 | -5 | 3 | -3
-     |   |   | null  | 5 | -5 | 3 | -3
      |   | 0 | zero  | 5 | -5 | 3 | -3
-     | 1 | 4 | one   | 5 | -5 | 2 |  4
-     | 2 | 3 | two   | 5 | -5 | 2 |  4
-     | 3 | 2 | three | 5 | -5 | 2 |  4
-     | 4 | 1 | four  | 5 | -5 | 2 |  4
-     | 5 | 0 | five  | 5 | -5 | 2 |  4
-     | 6 | 6 | six   | 5 | -5 | 2 |  4
-     | 7 | 7 | seven | 5 | -5 | 2 |  4
-     | 8 | 8 | eight | 5 | -5 | 2 |  4
-     | 0 |   | zero  | 5 | -5 | 2 |  4
-     |   |   | null  | 5 | -5 | 2 |  4
      |   | 0 | zero  | 5 | -5 | 2 |  4
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
      |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
      |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 0 |   
-     | 2 | 3 | two   | 5 | -5 | 0 |   
-     | 3 | 2 | three | 5 | -5 | 0 |   
-     | 4 | 1 | four  | 5 | -5 | 0 |   
-     | 5 | 0 | five  | 5 | -5 | 0 |   
-     | 6 | 6 | six   | 5 | -5 | 0 |   
-     | 7 | 7 | seven | 5 | -5 | 0 |   
-     | 8 | 8 | eight | 5 | -5 | 0 |   
-     | 0 |   | zero  | 5 | -5 | 0 |   
-     |   |   | null  | 5 | -5 | 0 |   
      |   | 0 | zero  | 5 | -5 | 0 |   
-     | 1 | 4 | one   | 5 | -5 |   |   
-     | 2 | 3 | two   | 5 | -5 |   |   
-     | 3 | 2 | three | 5 | -5 |   |   
-     | 4 | 1 | four  | 5 | -5 |   |   
-     | 5 | 0 | five  | 5 | -5 |   |   
-     | 6 | 6 | six   | 5 | -5 |   |   
-     | 7 | 7 | seven | 5 | -5 |   |   
-     | 8 | 8 | eight | 5 | -5 |   |   
-     | 0 |   | zero  | 5 | -5 |   |   
-     |   |   | null  | 5 | -5 |   |   
      |   | 0 | zero  | 5 | -5 |   |   
-     | 1 | 4 | one   | 5 | -5 |   |  0
-     | 2 | 3 | two   | 5 | -5 |   |  0
-     | 3 | 2 | three | 5 | -5 |   |  0
-     | 4 | 1 | four  | 5 | -5 |   |  0
-     | 5 | 0 | five  | 5 | -5 |   |  0
-     | 6 | 6 | six   | 5 | -5 |   |  0
-     | 7 | 7 | seven | 5 | -5 |   |  0
-     | 8 | 8 | eight | 5 | -5 |   |  0
-     | 0 |   | zero  | 5 | -5 |   |  0
-     |   |   | null  | 5 | -5 |   |  0
      |   | 0 | zero  | 5 | -5 |   |  0
-     | 1 | 4 | one   | 5 | -5 | 1 | -1
-     | 2 | 3 | two   | 5 | -5 | 1 | -1
-     | 3 | 2 | three | 5 | -5 | 1 | -1
-     | 4 | 1 | four  | 5 | -5 | 1 | -1
-     | 5 | 0 | five  | 5 | -5 | 1 | -1
-     | 6 | 6 | six   | 5 | -5 | 1 | -1
-     | 7 | 7 | seven | 5 | -5 | 1 | -1
-     | 8 | 8 | eight | 5 | -5 | 1 | -1
-     | 0 |   | zero  | 5 | -5 | 1 | -1
-     |   |   | null  | 5 | -5 | 1 | -1
      |   | 0 | zero  | 5 | -5 | 1 | -1
-     | 1 | 4 | one   | 5 | -5 | 2 |  2
-     | 2 | 3 | two   | 5 | -5 | 2 |  2
-     | 3 | 2 | three | 5 | -5 | 2 |  2
-     | 4 | 1 | four  | 5 | -5 | 2 |  2
-     | 5 | 0 | five  | 5 | -5 | 2 |  2
-     | 6 | 6 | six   | 5 | -5 | 2 |  2
-     | 7 | 7 | seven | 5 | -5 | 2 |  2
-     | 8 | 8 | eight | 5 | -5 | 2 |  2
-     | 0 |   | zero  | 5 | -5 | 2 |  2
-     |   |   | null  | 5 | -5 | 2 |  2
      |   | 0 | zero  | 5 | -5 | 2 |  2
-     | 1 | 4 | one   | 5 | -5 | 3 | -3
-     | 2 | 3 | two   | 5 | -5 | 3 | -3
-     | 3 | 2 | three | 5 | -5 | 3 | -3
-     | 4 | 1 | four  | 5 | -5 | 3 | -3
-     | 5 | 0 | five  | 5 | -5 | 3 | -3
-     | 6 | 6 | six   | 5 | -5 | 3 | -3
-     | 7 | 7 | seven | 5 | -5 | 3 | -3
-     | 8 | 8 | eight | 5 | -5 | 3 | -3
-     | 0 |   | zero  | 5 | -5 | 3 | -3
-     |   |   | null  | 5 | -5 | 3 | -3
      |   | 0 | zero  | 5 | -5 | 3 | -3
-     | 1 | 4 | one   | 5 | -5 | 2 |  4
-     | 2 | 3 | two   | 5 | -5 | 2 |  4
-     | 3 | 2 | three | 5 | -5 | 2 |  4
-     | 4 | 1 | four  | 5 | -5 | 2 |  4
-     | 5 | 0 | five  | 5 | -5 | 2 |  4
-     | 6 | 6 | six   | 5 | -5 | 2 |  4
-     | 7 | 7 | seven | 5 | -5 | 2 |  4
-     | 8 | 8 | eight | 5 | -5 | 2 |  4
-     | 0 |   | zero  | 5 | -5 | 2 |  4
-     |   |   | null  | 5 | -5 | 2 |  4
      |   | 0 | zero  | 5 | -5 | 2 |  4
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
      |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
      |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 0 |   
-     | 2 | 3 | two   | 5 | -5 | 0 |   
-     | 3 | 2 | three | 5 | -5 | 0 |   
-     | 4 | 1 | four  | 5 | -5 | 0 |   
-     | 5 | 0 | five  | 5 | -5 | 0 |   
-     | 6 | 6 | six   | 5 | -5 | 0 |   
-     | 7 | 7 | seven | 5 | -5 | 0 |   
-     | 8 | 8 | eight | 5 | -5 | 0 |   
-     | 0 |   | zero  | 5 | -5 | 0 |   
-     |   |   | null  | 5 | -5 | 0 |   
      |   | 0 | zero  | 5 | -5 | 0 |   
-     | 1 | 4 | one   | 5 | -5 |   |   
-     | 2 | 3 | two   | 5 | -5 |   |   
-     | 3 | 2 | three | 5 | -5 |   |   
-     | 4 | 1 | four  | 5 | -5 |   |   
-     | 5 | 0 | five  | 5 | -5 |   |   
-     | 6 | 6 | six   | 5 | -5 |   |   
-     | 7 | 7 | seven | 5 | -5 |   |   
-     | 8 | 8 | eight | 5 | -5 |   |   
-     | 0 |   | zero  | 5 | -5 |   |   
-     |   |   | null  | 5 | -5 |   |   
      |   | 0 | zero  | 5 | -5 |   |   
-     | 1 | 4 | one   | 5 | -5 |   |  0
-     | 2 | 3 | two   | 5 | -5 |   |  0
-     | 3 | 2 | three | 5 | -5 |   |  0
-     | 4 | 1 | four  | 5 | -5 |   |  0
-     | 5 | 0 | five  | 5 | -5 |   |  0
-     | 6 | 6 | six   | 5 | -5 |   |  0
-     | 7 | 7 | seven | 5 | -5 |   |  0
-     | 8 | 8 | eight | 5 | -5 |   |  0
-     | 0 |   | zero  | 5 | -5 |   |  0
-     |   |   | null  | 5 | -5 |   |  0
      |   | 0 | zero  | 5 | -5 |   |  0
-     | 1 | 4 | one   | 0 |    | 1 | -1
-     | 2 | 3 | two   | 0 |    | 1 | -1
-     | 3 | 2 | three | 0 |    | 1 | -1
-     | 4 | 1 | four  | 0 |    | 1 | -1
-     | 5 | 0 | five  | 0 |    | 1 | -1
-     | 6 | 6 | six   | 0 |    | 1 | -1
-     | 7 | 7 | seven | 0 |    | 1 | -1
-     | 8 | 8 | eight | 0 |    | 1 | -1
-     | 0 |   | zero  | 0 |    | 1 | -1
-     |   |   | null  | 0 |    | 1 | -1
      |   | 0 | zero  | 0 |    | 1 | -1
-     | 1 | 4 | one   | 0 |    | 2 |  2
-     | 2 | 3 | two   | 0 |    | 2 |  2
-     | 3 | 2 | three | 0 |    | 2 |  2
-     | 4 | 1 | four  | 0 |    | 2 |  2
-     | 5 | 0 | five  | 0 |    | 2 |  2
-     | 6 | 6 | six   | 0 |    | 2 |  2
-     | 7 | 7 | seven | 0 |    | 2 |  2
-     | 8 | 8 | eight | 0 |    | 2 |  2
-     | 0 |   | zero  | 0 |    | 2 |  2
-     |   |   | null  | 0 |    | 2 |  2
      |   | 0 | zero  | 0 |    | 2 |  2
-     | 1 | 4 | one   | 0 |    | 3 | -3
-     | 2 | 3 | two   | 0 |    | 3 | -3
-     | 3 | 2 | three | 0 |    | 3 | -3
-     | 4 | 1 | four  | 0 |    | 3 | -3
-     | 5 | 0 | five  | 0 |    | 3 | -3
-     | 6 | 6 | six   | 0 |    | 3 | -3
-     | 7 | 7 | seven | 0 |    | 3 | -3
-     | 8 | 8 | eight | 0 |    | 3 | -3
-     | 0 |   | zero  | 0 |    | 3 | -3
-     |   |   | null  | 0 |    | 3 | -3
      |   | 0 | zero  | 0 |    | 3 | -3
-     | 1 | 4 | one   | 0 |    | 2 |  4
-     | 2 | 3 | two   | 0 |    | 2 |  4
-     | 3 | 2 | three | 0 |    | 2 |  4
-     | 4 | 1 | four  | 0 |    | 2 |  4
-     | 5 | 0 | five  | 0 |    | 2 |  4
-     | 6 | 6 | six   | 0 |    | 2 |  4
-     | 7 | 7 | seven | 0 |    | 2 |  4
-     | 8 | 8 | eight | 0 |    | 2 |  4
-     | 0 |   | zero  | 0 |    | 2 |  4
-     |   |   | null  | 0 |    | 2 |  4
      |   | 0 | zero  | 0 |    | 2 |  4
-     | 1 | 4 | one   | 0 |    | 5 | -5
-     | 2 | 3 | two   | 0 |    | 5 | -5
-     | 3 | 2 | three | 0 |    | 5 | -5
-     | 4 | 1 | four  | 0 |    | 5 | -5
-     | 5 | 0 | five  | 0 |    | 5 | -5
-     | 6 | 6 | six   | 0 |    | 5 | -5
-     | 7 | 7 | seven | 0 |    | 5 | -5
-     | 8 | 8 | eight | 0 |    | 5 | -5
-     | 0 |   | zero  | 0 |    | 5 | -5
-     |   |   | null  | 0 |    | 5 | -5
      |   | 0 | zero  | 0 |    | 5 | -5
-     | 1 | 4 | one   | 0 |    | 5 | -5
-     | 2 | 3 | two   | 0 |    | 5 | -5
-     | 3 | 2 | three | 0 |    | 5 | -5
-     | 4 | 1 | four  | 0 |    | 5 | -5
-     | 5 | 0 | five  | 0 |    | 5 | -5
-     | 6 | 6 | six   | 0 |    | 5 | -5
-     | 7 | 7 | seven | 0 |    | 5 | -5
-     | 8 | 8 | eight | 0 |    | 5 | -5
-     | 0 |   | zero  | 0 |    | 5 | -5
-     |   |   | null  | 0 |    | 5 | -5
      |   | 0 | zero  | 0 |    | 5 | -5
-     | 1 | 4 | one   | 0 |    | 0 |   
-     | 2 | 3 | two   | 0 |    | 0 |   
-     | 3 | 2 | three | 0 |    | 0 |   
-     | 4 | 1 | four  | 0 |    | 0 |   
-     | 5 | 0 | five  | 0 |    | 0 |   
-     | 6 | 6 | six   | 0 |    | 0 |   
-     | 7 | 7 | seven | 0 |    | 0 |   
-     | 8 | 8 | eight | 0 |    | 0 |   
-     | 0 |   | zero  | 0 |    | 0 |   
-     |   |   | null  | 0 |    | 0 |   
      |   | 0 | zero  | 0 |    | 0 |   
-     | 1 | 4 | one   | 0 |    |   |   
-     | 2 | 3 | two   | 0 |    |   |   
-     | 3 | 2 | three | 0 |    |   |   
-     | 4 | 1 | four  | 0 |    |   |   
-     | 5 | 0 | five  | 0 |    |   |   
-     | 6 | 6 | six   | 0 |    |   |   
-     | 7 | 7 | seven | 0 |    |   |   
-     | 8 | 8 | eight | 0 |    |   |   
-     | 0 |   | zero  | 0 |    |   |   
-     |   |   | null  | 0 |    |   |   
      |   | 0 | zero  | 0 |    |   |   
-     | 1 | 4 | one   | 0 |    |   |  0
-     | 2 | 3 | two   | 0 |    |   |  0
-     | 3 | 2 | three | 0 |    |   |  0
-     | 4 | 1 | four  | 0 |    |   |  0
-     | 5 | 0 | five  | 0 |    |   |  0
-     | 6 | 6 | six   | 0 |    |   |  0
-     | 7 | 7 | seven | 0 |    |   |  0
-     | 8 | 8 | eight | 0 |    |   |  0
-     | 0 |   | zero  | 0 |    |   |  0
-     |   |   | null  | 0 |    |   |  0
      |   | 0 | zero  | 0 |    |   |  0
-     | 1 | 4 | one   |   |    | 1 | -1
-     | 2 | 3 | two   |   |    | 1 | -1
-     | 3 | 2 | three |   |    | 1 | -1
-     | 4 | 1 | four  |   |    | 1 | -1
-     | 5 | 0 | five  |   |    | 1 | -1
-     | 6 | 6 | six   |   |    | 1 | -1
-     | 7 | 7 | seven |   |    | 1 | -1
-     | 8 | 8 | eight |   |    | 1 | -1
-     | 0 |   | zero  |   |    | 1 | -1
-     |   |   | null  |   |    | 1 | -1
      |   | 0 | zero  |   |    | 1 | -1
-     | 1 | 4 | one   |   |    | 2 |  2
-     | 2 | 3 | two   |   |    | 2 |  2
-     | 3 | 2 | three |   |    | 2 |  2
-     | 4 | 1 | four  |   |    | 2 |  2
-     | 5 | 0 | five  |   |    | 2 |  2
-     | 6 | 6 | six   |   |    | 2 |  2
-     | 7 | 7 | seven |   |    | 2 |  2
-     | 8 | 8 | eight |   |    | 2 |  2
-     | 0 |   | zero  |   |    | 2 |  2
-     |   |   | null  |   |    | 2 |  2
      |   | 0 | zero  |   |    | 2 |  2
-     | 1 | 4 | one   |   |    | 3 | -3
-     | 2 | 3 | two   |   |    | 3 | -3
-     | 3 | 2 | three |   |    | 3 | -3
-     | 4 | 1 | four  |   |    | 3 | -3
-     | 5 | 0 | five  |   |    | 3 | -3
-     | 6 | 6 | six   |   |    | 3 | -3
-     | 7 | 7 | seven |   |    | 3 | -3
-     | 8 | 8 | eight |   |    | 3 | -3
-     | 0 |   | zero  |   |    | 3 | -3
-     |   |   | null  |   |    | 3 | -3
      |   | 0 | zero  |   |    | 3 | -3
-     | 1 | 4 | one   |   |    | 2 |  4
-     | 2 | 3 | two   |   |    | 2 |  4
-     | 3 | 2 | three |   |    | 2 |  4
-     | 4 | 1 | four  |   |    | 2 |  4
-     | 5 | 0 | five  |   |    | 2 |  4
-     | 6 | 6 | six   |   |    | 2 |  4
-     | 7 | 7 | seven |   |    | 2 |  4
-     | 8 | 8 | eight |   |    | 2 |  4
-     | 0 |   | zero  |   |    | 2 |  4
-     |   |   | null  |   |    | 2 |  4
      |   | 0 | zero  |   |    | 2 |  4
-     | 1 | 4 | one   |   |    | 5 | -5
-     | 2 | 3 | two   |   |    | 5 | -5
-     | 3 | 2 | three |   |    | 5 | -5
-     | 4 | 1 | four  |   |    | 5 | -5
-     | 5 | 0 | five  |   |    | 5 | -5
-     | 6 | 6 | six   |   |    | 5 | -5
-     | 7 | 7 | seven |   |    | 5 | -5
-     | 8 | 8 | eight |   |    | 5 | -5
-     | 0 |   | zero  |   |    | 5 | -5
-     |   |   | null  |   |    | 5 | -5
      |   | 0 | zero  |   |    | 5 | -5
-     | 1 | 4 | one   |   |    | 5 | -5
-     | 2 | 3 | two   |   |    | 5 | -5
-     | 3 | 2 | three |   |    | 5 | -5
-     | 4 | 1 | four  |   |    | 5 | -5
-     | 5 | 0 | five  |   |    | 5 | -5
-     | 6 | 6 | six   |   |    | 5 | -5
-     | 7 | 7 | seven |   |    | 5 | -5
-     | 8 | 8 | eight |   |    | 5 | -5
-     | 0 |   | zero  |   |    | 5 | -5
-     |   |   | null  |   |    | 5 | -5
      |   | 0 | zero  |   |    | 5 | -5
-     | 1 | 4 | one   |   |    | 0 |   
-     | 2 | 3 | two   |   |    | 0 |   
-     | 3 | 2 | three |   |    | 0 |   
-     | 4 | 1 | four  |   |    | 0 |   
-     | 5 | 0 | five  |   |    | 0 |   
-     | 6 | 6 | six   |   |    | 0 |   
-     | 7 | 7 | seven |   |    | 0 |   
-     | 8 | 8 | eight |   |    | 0 |   
-     | 0 |   | zero  |   |    | 0 |   
-     |   |   | null  |   |    | 0 |   
      |   | 0 | zero  |   |    | 0 |   
-     | 1 | 4 | one   |   |    |   |   
-     | 2 | 3 | two   |   |    |   |   
-     | 3 | 2 | three |   |    |   |   
-     | 4 | 1 | four  |   |    |   |   
-     | 5 | 0 | five  |   |    |   |   
-     | 6 | 6 | six   |   |    |   |   
-     | 7 | 7 | seven |   |    |   |   
-     | 8 | 8 | eight |   |    |   |   
-     | 0 |   | zero  |   |    |   |   
-     |   |   | null  |   |    |   |   
      |   | 0 | zero  |   |    |   |   
-     | 1 | 4 | one   |   |    |   |  0
-     | 2 | 3 | two   |   |    |   |  0
-     | 3 | 2 | three |   |    |   |  0
-     | 4 | 1 | four  |   |    |   |  0
-     | 5 | 0 | five  |   |    |   |  0
-     | 6 | 6 | six   |   |    |   |  0
-     | 7 | 7 | seven |   |    |   |  0
-     | 8 | 8 | eight |   |    |   |  0
-     | 0 |   | zero  |   |    |   |  0
-     |   |   | null  |   |    |   |  0
      |   | 0 | zero  |   |    |   |  0
-     | 1 | 4 | one   |   |  0 | 1 | -1
-     | 2 | 3 | two   |   |  0 | 1 | -1
-     | 3 | 2 | three |   |  0 | 1 | -1
-     | 4 | 1 | four  |   |  0 | 1 | -1
-     | 5 | 0 | five  |   |  0 | 1 | -1
-     | 6 | 6 | six   |   |  0 | 1 | -1
-     | 7 | 7 | seven |   |  0 | 1 | -1
-     | 8 | 8 | eight |   |  0 | 1 | -1
-     | 0 |   | zero  |   |  0 | 1 | -1
-     |   |   | null  |   |  0 | 1 | -1
      |   | 0 | zero  |   |  0 | 1 | -1
-     | 1 | 4 | one   |   |  0 | 2 |  2
-     | 2 | 3 | two   |   |  0 | 2 |  2
-     | 3 | 2 | three |   |  0 | 2 |  2
-     | 4 | 1 | four  |   |  0 | 2 |  2
-     | 5 | 0 | five  |   |  0 | 2 |  2
-     | 6 | 6 | six   |   |  0 | 2 |  2
-     | 7 | 7 | seven |   |  0 | 2 |  2
-     | 8 | 8 | eight |   |  0 | 2 |  2
-     | 0 |   | zero  |   |  0 | 2 |  2
-     |   |   | null  |   |  0 | 2 |  2
      |   | 0 | zero  |   |  0 | 2 |  2
-     | 1 | 4 | one   |   |  0 | 3 | -3
-     | 2 | 3 | two   |   |  0 | 3 | -3
-     | 3 | 2 | three |   |  0 | 3 | -3
-     | 4 | 1 | four  |   |  0 | 3 | -3
-     | 5 | 0 | five  |   |  0 | 3 | -3
-     | 6 | 6 | six   |   |  0 | 3 | -3
-     | 7 | 7 | seven |   |  0 | 3 | -3
-     | 8 | 8 | eight |   |  0 | 3 | -3
-     | 0 |   | zero  |   |  0 | 3 | -3
-     |   |   | null  |   |  0 | 3 | -3
      |   | 0 | zero  |   |  0 | 3 | -3
-     | 1 | 4 | one   |   |  0 | 2 |  4
-     | 2 | 3 | two   |   |  0 | 2 |  4
-     | 3 | 2 | three |   |  0 | 2 |  4
-     | 4 | 1 | four  |   |  0 | 2 |  4
-     | 5 | 0 | five  |   |  0 | 2 |  4
-     | 6 | 6 | six   |   |  0 | 2 |  4
-     | 7 | 7 | seven |   |  0 | 2 |  4
-     | 8 | 8 | eight |   |  0 | 2 |  4
-     | 0 |   | zero  |   |  0 | 2 |  4
-     |   |   | null  |   |  0 | 2 |  4
      |   | 0 | zero  |   |  0 | 2 |  4
-     | 1 | 4 | one   |   |  0 | 5 | -5
-     | 2 | 3 | two   |   |  0 | 5 | -5
-     | 3 | 2 | three |   |  0 | 5 | -5
-     | 4 | 1 | four  |   |  0 | 5 | -5
-     | 5 | 0 | five  |   |  0 | 5 | -5
-     | 6 | 6 | six   |   |  0 | 5 | -5
-     | 7 | 7 | seven |   |  0 | 5 | -5
-     | 8 | 8 | eight |   |  0 | 5 | -5
-     | 0 |   | zero  |   |  0 | 5 | -5
-     |   |   | null  |   |  0 | 5 | -5
      |   | 0 | zero  |   |  0 | 5 | -5
-     | 1 | 4 | one   |   |  0 | 5 | -5
-     | 2 | 3 | two   |   |  0 | 5 | -5
-     | 3 | 2 | three |   |  0 | 5 | -5
-     | 4 | 1 | four  |   |  0 | 5 | -5
-     | 5 | 0 | five  |   |  0 | 5 | -5
-     | 6 | 6 | six   |   |  0 | 5 | -5
-     | 7 | 7 | seven |   |  0 | 5 | -5
-     | 8 | 8 | eight |   |  0 | 5 | -5
-     | 0 |   | zero  |   |  0 | 5 | -5
-     |   |   | null  |   |  0 | 5 | -5
      |   | 0 | zero  |   |  0 | 5 | -5
-     | 1 | 4 | one   |   |  0 | 0 |   
-     | 2 | 3 | two   |   |  0 | 0 |   
-     | 3 | 2 | three |   |  0 | 0 |   
-     | 4 | 1 | four  |   |  0 | 0 |   
-     | 5 | 0 | five  |   |  0 | 0 |   
-     | 6 | 6 | six   |   |  0 | 0 |   
-     | 7 | 7 | seven |   |  0 | 0 |   
-     | 8 | 8 | eight |   |  0 | 0 |   
-     | 0 |   | zero  |   |  0 | 0 |   
-     |   |   | null  |   |  0 | 0 |   
      |   | 0 | zero  |   |  0 | 0 |   
-     | 1 | 4 | one   |   |  0 |   |   
-     | 2 | 3 | two   |   |  0 |   |   
-     | 3 | 2 | three |   |  0 |   |   
-     | 4 | 1 | four  |   |  0 |   |   
-     | 5 | 0 | five  |   |  0 |   |   
-     | 6 | 6 | six   |   |  0 |   |   
-     | 7 | 7 | seven |   |  0 |   |   
-     | 8 | 8 | eight |   |  0 |   |   
-     | 0 |   | zero  |   |  0 |   |   
-     |   |   | null  |   |  0 |   |   
      |   | 0 | zero  |   |  0 |   |   
-     | 1 | 4 | one   |   |  0 |   |  0
-     | 2 | 3 | two   |   |  0 |   |  0
-     | 3 | 2 | three |   |  0 |   |  0
-     | 4 | 1 | four  |   |  0 |   |  0
-     | 5 | 0 | five  |   |  0 |   |  0
-     | 6 | 6 | six   |   |  0 |   |  0
-     | 7 | 7 | seven |   |  0 |   |  0
-     | 8 | 8 | eight |   |  0 |   |  0
-     | 0 |   | zero  |   |  0 |   |  0
-     |   |   | null  |   |  0 |   |  0
      |   | 0 | zero  |   |  0 |   |  0
 (891 rows)
 
@@ -1567,13 +1567,13 @@ SELECT '' AS "xxx", *
   FROM J1_TBL INNER JOIN J2_TBL USING (i);
  xxx | i | j |   t   | k  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
      | 2 | 3 | two   |  4
+     | 2 | 3 | two   |  2
      | 3 | 2 | three | -3
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
 (7 rows)
 
 -- Same as above, slightly different syntax
@@ -1581,13 +1581,13 @@ SELECT '' AS "xxx", *
   FROM J1_TBL JOIN J2_TBL USING (i);
  xxx | i | j |   t   | k  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
      | 2 | 3 | two   |  4
+     | 2 | 3 | two   |  2
      | 3 | 2 | three | -3
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
 (7 rows)
 
 SELECT '' AS "xxx", *
@@ -1623,35 +1623,35 @@ SELECT '' AS "xxx", *
   FROM J1_TBL NATURAL JOIN J2_TBL;
  xxx | i | j |   t   | k  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
      | 2 | 3 | two   |  4
+     | 2 | 3 | two   |  2
      | 3 | 2 | three | -3
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
 (7 rows)
 
 SELECT '' AS "xxx", *
   FROM J1_TBL t1 (a, b, c) NATURAL JOIN J2_TBL t2 (a, d);
  xxx | a | b |   c   | d  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
      | 2 | 3 | two   |  4
+     | 2 | 3 | two   |  2
      | 3 | 2 | three | -3
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
 (7 rows)
 
 SELECT '' AS "xxx", *
   FROM J1_TBL t1 (a, b, c) NATURAL JOIN J2_TBL t2 (d, a);
  xxx | a | b |  c   | d 
 -----+---+---+------+---
-     | 0 |   | zero |  
      | 2 | 3 | two  | 2
      | 4 | 1 | four | 2
+     | 0 |   | zero |  
 (3 rows)
 
 -- mismatch number of columns
@@ -1660,13 +1660,13 @@ SELECT '' AS "xxx", *
   FROM J1_TBL t1 (a, b) NATURAL JOIN J2_TBL t2 (a);
  xxx | a | b |   t   | k  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
      | 2 | 3 | two   |  4
+     | 2 | 3 | two   |  2
      | 3 | 2 | three | -3
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
 (7 rows)
 
 --
@@ -1676,22 +1676,22 @@ SELECT '' AS "xxx", *
   FROM J1_TBL JOIN J2_TBL ON (J1_TBL.i = J2_TBL.i);
  xxx | i | j |   t   | i | k  
 -----+---+---+-------+---+----
-     | 0 |   | zero  | 0 |   
      | 1 | 4 | one   | 1 | -1
-     | 2 | 3 | two   | 2 |  2
      | 2 | 3 | two   | 2 |  4
+     | 2 | 3 | two   | 2 |  2
      | 3 | 2 | three | 3 | -3
      | 5 | 0 | five  | 5 | -5
      | 5 | 0 | five  | 5 | -5
+     | 0 |   | zero  | 0 |   
 (7 rows)
 
 SELECT '' AS "xxx", *
   FROM J1_TBL JOIN J2_TBL ON (J1_TBL.i = J2_TBL.k);
  xxx | i | j |  t   | i | k 
 -----+---+---+------+---+---
-     | 0 |   | zero |   | 0
      | 2 | 3 | two  | 2 | 2
      | 4 | 1 | four | 2 | 4
+     | 0 |   | zero |   | 0
 (3 rows)
 
 --
@@ -1760,13 +1760,13 @@ SELECT '' AS "xxx", *
   FROM J1_TBL RIGHT OUTER JOIN J2_TBL USING (i);
  xxx | i | j |   t   | k  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
      | 2 | 3 | two   |  2
-     | 2 | 3 | two   |  4
      | 3 | 2 | three | -3
+     | 2 | 3 | two   |  4
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
      |   |   |       |   
      |   |   |       |  0
 (9 rows)
@@ -1775,13 +1775,13 @@ SELECT '' AS "xxx", *
   FROM J1_TBL RIGHT JOIN J2_TBL USING (i);
  xxx | i | j |   t   | k  
 -----+---+---+-------+----
-     | 0 |   | zero  |   
      | 1 | 4 | one   | -1
      | 2 | 3 | two   |  2
-     | 2 | 3 | two   |  4
      | 3 | 2 | three | -3
+     | 2 | 3 | two   |  4
      | 5 | 0 | five  | -5
      | 5 | 0 | five  | -5
+     | 0 |   | zero  |   
      |   |   |       |   
      |   |   |       |  0
 (9 rows)
diff --git a/src/test/regress/expected/join_1.out b/src/test/regress/expected/join_1.out
deleted file mode 100644 (file)
index 27c7d29..0000000
+++ /dev/null
@@ -1,2149 +0,0 @@
---
--- JOIN
--- Test JOIN clauses
---
-CREATE TABLE J1_TBL (
-  i integer,
-  j integer,
-  t text
-);
-CREATE TABLE J2_TBL (
-  i integer,
-  k integer
-);
-INSERT INTO J1_TBL VALUES (1, 4, 'one');
-INSERT INTO J1_TBL VALUES (2, 3, 'two');
-INSERT INTO J1_TBL VALUES (3, 2, 'three');
-INSERT INTO J1_TBL VALUES (4, 1, 'four');
-INSERT INTO J1_TBL VALUES (5, 0, 'five');
-INSERT INTO J1_TBL VALUES (6, 6, 'six');
-INSERT INTO J1_TBL VALUES (7, 7, 'seven');
-INSERT INTO J1_TBL VALUES (8, 8, 'eight');
-INSERT INTO J1_TBL VALUES (0, NULL, 'zero');
-INSERT INTO J1_TBL VALUES (NULL, NULL, 'null');
-INSERT INTO J1_TBL VALUES (NULL, 0, 'zero');
-INSERT INTO J2_TBL VALUES (1, -1);
-INSERT INTO J2_TBL VALUES (2, 2);
-INSERT INTO J2_TBL VALUES (3, -3);
-INSERT INTO J2_TBL VALUES (2, 4);
-INSERT INTO J2_TBL VALUES (5, -5);
-INSERT INTO J2_TBL VALUES (5, -5);
-INSERT INTO J2_TBL VALUES (0, NULL);
-INSERT INTO J2_TBL VALUES (NULL, NULL);
-INSERT INTO J2_TBL VALUES (NULL, 0);
---
--- CORRELATION NAMES
--- Make sure that table/column aliases are supported
--- before diving into more complex join syntax.
---
-SELECT '' AS "xxx", *
-  FROM J1_TBL AS tx;
- xxx | i | j |   t   
------+---+---+-------
-     | 1 | 4 | one
-     | 2 | 3 | two
-     | 3 | 2 | three
-     | 4 | 1 | four
-     | 5 | 0 | five
-     | 6 | 6 | six
-     | 7 | 7 | seven
-     | 8 | 8 | eight
-     | 0 |   | zero
-     |   |   | null
-     |   | 0 | zero
-(11 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL tx;
- xxx | i | j |   t   
------+---+---+-------
-     | 1 | 4 | one
-     | 2 | 3 | two
-     | 3 | 2 | three
-     | 4 | 1 | four
-     | 5 | 0 | five
-     | 6 | 6 | six
-     | 7 | 7 | seven
-     | 8 | 8 | eight
-     | 0 |   | zero
-     |   |   | null
-     |   | 0 | zero
-(11 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL AS t1 (a, b, c);
- xxx | a | b |   c   
------+---+---+-------
-     | 1 | 4 | one
-     | 2 | 3 | two
-     | 3 | 2 | three
-     | 4 | 1 | four
-     | 5 | 0 | five
-     | 6 | 6 | six
-     | 7 | 7 | seven
-     | 8 | 8 | eight
-     | 0 |   | zero
-     |   |   | null
-     |   | 0 | zero
-(11 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b, c);
- xxx | a | b |   c   
------+---+---+-------
-     | 1 | 4 | one
-     | 2 | 3 | two
-     | 3 | 2 | three
-     | 4 | 1 | four
-     | 5 | 0 | five
-     | 6 | 6 | six
-     | 7 | 7 | seven
-     | 8 | 8 | eight
-     | 0 |   | zero
-     |   |   | null
-     |   | 0 | zero
-(11 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b, c), J2_TBL t2 (d, e);
- xxx | a | b |   c   | d | e  
------+---+---+-------+---+----
-     | 1 | 4 | one   | 1 | -1
-     | 1 | 4 | one   | 2 |  2
-     | 1 | 4 | one   | 3 | -3
-     | 1 | 4 | one   | 2 |  4
-     | 1 | 4 | one   | 5 | -5
-     | 1 | 4 | one   | 5 | -5
-     | 1 | 4 | one   | 0 |   
-     | 1 | 4 | one   |   |   
-     | 1 | 4 | one   |   |  0
-     | 2 | 3 | two   | 1 | -1
-     | 2 | 3 | two   | 2 |  2
-     | 2 | 3 | two   | 3 | -3
-     | 2 | 3 | two   | 2 |  4
-     | 2 | 3 | two   | 5 | -5
-     | 2 | 3 | two   | 5 | -5
-     | 2 | 3 | two   | 0 |   
-     | 2 | 3 | two   |   |   
-     | 2 | 3 | two   |   |  0
-     | 3 | 2 | three | 1 | -1
-     | 3 | 2 | three | 2 |  2
-     | 3 | 2 | three | 3 | -3
-     | 3 | 2 | three | 2 |  4
-     | 3 | 2 | three | 5 | -5
-     | 3 | 2 | three | 5 | -5
-     | 3 | 2 | three | 0 |   
-     | 3 | 2 | three |   |   
-     | 3 | 2 | three |   |  0
-     | 4 | 1 | four  | 1 | -1
-     | 4 | 1 | four  | 2 |  2
-     | 4 | 1 | four  | 3 | -3
-     | 4 | 1 | four  | 2 |  4
-     | 4 | 1 | four  | 5 | -5
-     | 4 | 1 | four  | 5 | -5
-     | 4 | 1 | four  | 0 |   
-     | 4 | 1 | four  |   |   
-     | 4 | 1 | four  |   |  0
-     | 5 | 0 | five  | 1 | -1
-     | 5 | 0 | five  | 2 |  2
-     | 5 | 0 | five  | 3 | -3
-     | 5 | 0 | five  | 2 |  4
-     | 5 | 0 | five  | 5 | -5
-     | 5 | 0 | five  | 5 | -5
-     | 5 | 0 | five  | 0 |   
-     | 5 | 0 | five  |   |   
-     | 5 | 0 | five  |   |  0
-     | 6 | 6 | six   | 1 | -1
-     | 6 | 6 | six   | 2 |  2
-     | 6 | 6 | six   | 3 | -3
-     | 6 | 6 | six   | 2 |  4
-     | 6 | 6 | six   | 5 | -5
-     | 6 | 6 | six   | 5 | -5
-     | 6 | 6 | six   | 0 |   
-     | 6 | 6 | six   |   |   
-     | 6 | 6 | six   |   |  0
-     | 7 | 7 | seven | 1 | -1
-     | 7 | 7 | seven | 2 |  2
-     | 7 | 7 | seven | 3 | -3
-     | 7 | 7 | seven | 2 |  4
-     | 7 | 7 | seven | 5 | -5
-     | 7 | 7 | seven | 5 | -5
-     | 7 | 7 | seven | 0 |   
-     | 7 | 7 | seven |   |   
-     | 7 | 7 | seven |   |  0
-     | 8 | 8 | eight | 1 | -1
-     | 8 | 8 | eight | 2 |  2
-     | 8 | 8 | eight | 3 | -3
-     | 8 | 8 | eight | 2 |  4
-     | 8 | 8 | eight | 5 | -5
-     | 8 | 8 | eight | 5 | -5
-     | 8 | 8 | eight | 0 |   
-     | 8 | 8 | eight |   |   
-     | 8 | 8 | eight |   |  0
-     | 0 |   | zero  | 1 | -1
-     | 0 |   | zero  | 2 |  2
-     | 0 |   | zero  | 3 | -3
-     | 0 |   | zero  | 2 |  4
-     | 0 |   | zero  | 5 | -5
-     | 0 |   | zero  | 5 | -5
-     | 0 |   | zero  | 0 |   
-     | 0 |   | zero  |   |   
-     | 0 |   | zero  |   |  0
-     |   |   | null  | 1 | -1
-     |   |   | null  | 2 |  2
-     |   |   | null  | 3 | -3
-     |   |   | null  | 2 |  4
-     |   |   | null  | 5 | -5
-     |   |   | null  | 5 | -5
-     |   |   | null  | 0 |   
-     |   |   | null  |   |   
-     |   |   | null  |   |  0
-     |   | 0 | zero  | 1 | -1
-     |   | 0 | zero  | 2 |  2
-     |   | 0 | zero  | 3 | -3
-     |   | 0 | zero  | 2 |  4
-     |   | 0 | zero  | 5 | -5
-     |   | 0 | zero  | 5 | -5
-     |   | 0 | zero  | 0 |   
-     |   | 0 | zero  |   |   
-     |   | 0 | zero  |   |  0
-(99 rows)
-
-SELECT '' AS "xxx", t1.a, t2.e
-  FROM J1_TBL t1 (a, b, c), J2_TBL t2 (d, e)
-  WHERE t1.a = t2.d;
- xxx | a | e  
------+---+----
-     | 0 |   
-     | 1 | -1
-     | 2 |  4
-     | 2 |  2
-     | 3 | -3
-     | 5 | -5
-     | 5 | -5
-(7 rows)
-
---
--- CROSS JOIN
--- Qualifications are not allowed on cross joins,
--- which degenerate into a standard unqualified inner join.
---
-SELECT '' AS "xxx", *
-  FROM J1_TBL CROSS JOIN J2_TBL;
- xxx | i | j |   t   | i | k  
------+---+---+-------+---+----
-     | 1 | 4 | one   | 1 | -1
-     | 1 | 4 | one   | 2 |  2
-     | 1 | 4 | one   | 3 | -3
-     | 1 | 4 | one   | 2 |  4
-     | 1 | 4 | one   | 5 | -5
-     | 1 | 4 | one   | 5 | -5
-     | 1 | 4 | one   | 0 |   
-     | 1 | 4 | one   |   |   
-     | 1 | 4 | one   |   |  0
-     | 2 | 3 | two   | 1 | -1
-     | 2 | 3 | two   | 2 |  2
-     | 2 | 3 | two   | 3 | -3
-     | 2 | 3 | two   | 2 |  4
-     | 2 | 3 | two   | 5 | -5
-     | 2 | 3 | two   | 5 | -5
-     | 2 | 3 | two   | 0 |   
-     | 2 | 3 | two   |   |   
-     | 2 | 3 | two   |   |  0
-     | 3 | 2 | three | 1 | -1
-     | 3 | 2 | three | 2 |  2
-     | 3 | 2 | three | 3 | -3
-     | 3 | 2 | three | 2 |  4
-     | 3 | 2 | three | 5 | -5
-     | 3 | 2 | three | 5 | -5
-     | 3 | 2 | three | 0 |   
-     | 3 | 2 | three |   |   
-     | 3 | 2 | three |   |  0
-     | 4 | 1 | four  | 1 | -1
-     | 4 | 1 | four  | 2 |  2
-     | 4 | 1 | four  | 3 | -3
-     | 4 | 1 | four  | 2 |  4
-     | 4 | 1 | four  | 5 | -5
-     | 4 | 1 | four  | 5 | -5
-     | 4 | 1 | four  | 0 |   
-     | 4 | 1 | four  |   |   
-     | 4 | 1 | four  |   |  0
-     | 5 | 0 | five  | 1 | -1
-     | 5 | 0 | five  | 2 |  2
-     | 5 | 0 | five  | 3 | -3
-     | 5 | 0 | five  | 2 |  4
-     | 5 | 0 | five  | 5 | -5
-     | 5 | 0 | five  | 5 | -5
-     | 5 | 0 | five  | 0 |   
-     | 5 | 0 | five  |   |   
-     | 5 | 0 | five  |   |  0
-     | 6 | 6 | six   | 1 | -1
-     | 6 | 6 | six   | 2 |  2
-     | 6 | 6 | six   | 3 | -3
-     | 6 | 6 | six   | 2 |  4
-     | 6 | 6 | six   | 5 | -5
-     | 6 | 6 | six   | 5 | -5
-     | 6 | 6 | six   | 0 |   
-     | 6 | 6 | six   |   |   
-     | 6 | 6 | six   |   |  0
-     | 7 | 7 | seven | 1 | -1
-     | 7 | 7 | seven | 2 |  2
-     | 7 | 7 | seven | 3 | -3
-     | 7 | 7 | seven | 2 |  4
-     | 7 | 7 | seven | 5 | -5
-     | 7 | 7 | seven | 5 | -5
-     | 7 | 7 | seven | 0 |   
-     | 7 | 7 | seven |   |   
-     | 7 | 7 | seven |   |  0
-     | 8 | 8 | eight | 1 | -1
-     | 8 | 8 | eight | 2 |  2
-     | 8 | 8 | eight | 3 | -3
-     | 8 | 8 | eight | 2 |  4
-     | 8 | 8 | eight | 5 | -5
-     | 8 | 8 | eight | 5 | -5
-     | 8 | 8 | eight | 0 |   
-     | 8 | 8 | eight |   |   
-     | 8 | 8 | eight |   |  0
-     | 0 |   | zero  | 1 | -1
-     | 0 |   | zero  | 2 |  2
-     | 0 |   | zero  | 3 | -3
-     | 0 |   | zero  | 2 |  4
-     | 0 |   | zero  | 5 | -5
-     | 0 |   | zero  | 5 | -5
-     | 0 |   | zero  | 0 |   
-     | 0 |   | zero  |   |   
-     | 0 |   | zero  |   |  0
-     |   |   | null  | 1 | -1
-     |   |   | null  | 2 |  2
-     |   |   | null  | 3 | -3
-     |   |   | null  | 2 |  4
-     |   |   | null  | 5 | -5
-     |   |   | null  | 5 | -5
-     |   |   | null  | 0 |   
-     |   |   | null  |   |   
-     |   |   | null  |   |  0
-     |   | 0 | zero  | 1 | -1
-     |   | 0 | zero  | 2 |  2
-     |   | 0 | zero  | 3 | -3
-     |   | 0 | zero  | 2 |  4
-     |   | 0 | zero  | 5 | -5
-     |   | 0 | zero  | 5 | -5
-     |   | 0 | zero  | 0 |   
-     |   | 0 | zero  |   |   
-     |   | 0 | zero  |   |  0
-(99 rows)
-
--- ambiguous column
-SELECT '' AS "xxx", i, k, t
-  FROM J1_TBL CROSS JOIN J2_TBL;
-ERROR:  column reference "i" is ambiguous
--- resolve previous ambiguity by specifying the table name
-SELECT '' AS "xxx", t1.i, k, t
-  FROM J1_TBL t1 CROSS JOIN J2_TBL t2;
- xxx | i | k  |   t   
------+---+----+-------
-     | 1 | -1 | one
-     | 1 |  2 | one
-     | 1 | -3 | one
-     | 1 |  4 | one
-     | 1 | -5 | one
-     | 1 | -5 | one
-     | 1 |    | one
-     | 1 |    | one
-     | 1 |  0 | one
-     | 2 | -1 | two
-     | 2 |  2 | two
-     | 2 | -3 | two
-     | 2 |  4 | two
-     | 2 | -5 | two
-     | 2 | -5 | two
-     | 2 |    | two
-     | 2 |    | two
-     | 2 |  0 | two
-     | 3 | -1 | three
-     | 3 |  2 | three
-     | 3 | -3 | three
-     | 3 |  4 | three
-     | 3 | -5 | three
-     | 3 | -5 | three
-     | 3 |    | three
-     | 3 |    | three
-     | 3 |  0 | three
-     | 4 | -1 | four
-     | 4 |  2 | four
-     | 4 | -3 | four
-     | 4 |  4 | four
-     | 4 | -5 | four
-     | 4 | -5 | four
-     | 4 |    | four
-     | 4 |    | four
-     | 4 |  0 | four
-     | 5 | -1 | five
-     | 5 |  2 | five
-     | 5 | -3 | five
-     | 5 |  4 | five
-     | 5 | -5 | five
-     | 5 | -5 | five
-     | 5 |    | five
-     | 5 |    | five
-     | 5 |  0 | five
-     | 6 | -1 | six
-     | 6 |  2 | six
-     | 6 | -3 | six
-     | 6 |  4 | six
-     | 6 | -5 | six
-     | 6 | -5 | six
-     | 6 |    | six
-     | 6 |    | six
-     | 6 |  0 | six
-     | 7 | -1 | seven
-     | 7 |  2 | seven
-     | 7 | -3 | seven
-     | 7 |  4 | seven
-     | 7 | -5 | seven
-     | 7 | -5 | seven
-     | 7 |    | seven
-     | 7 |    | seven
-     | 7 |  0 | seven
-     | 8 | -1 | eight
-     | 8 |  2 | eight
-     | 8 | -3 | eight
-     | 8 |  4 | eight
-     | 8 | -5 | eight
-     | 8 | -5 | eight
-     | 8 |    | eight
-     | 8 |    | eight
-     | 8 |  0 | eight
-     | 0 | -1 | zero
-     | 0 |  2 | zero
-     | 0 | -3 | zero
-     | 0 |  4 | zero
-     | 0 | -5 | zero
-     | 0 | -5 | zero
-     | 0 |    | zero
-     | 0 |    | zero
-     | 0 |  0 | zero
-     |   | -1 | null
-     |   |  2 | null
-     |   | -3 | null
-     |   |  4 | null
-     |   | -5 | null
-     |   | -5 | null
-     |   |    | null
-     |   |    | null
-     |   |  0 | null
-     |   | -1 | zero
-     |   |  2 | zero
-     |   | -3 | zero
-     |   |  4 | zero
-     |   | -5 | zero
-     |   | -5 | zero
-     |   |    | zero
-     |   |    | zero
-     |   |  0 | zero
-(99 rows)
-
-SELECT '' AS "xxx", ii, tt, kk
-  FROM (J1_TBL CROSS JOIN J2_TBL)
-    AS tx (ii, jj, tt, ii2, kk);
- xxx | ii |  tt   | kk 
------+----+-------+----
-     |  1 | one   | -1
-     |  1 | one   |  2
-     |  1 | one   | -3
-     |  1 | one   |  4
-     |  1 | one   | -5
-     |  1 | one   | -5
-     |  1 | one   |   
-     |  1 | one   |   
-     |  1 | one   |  0
-     |  2 | two   | -1
-     |  2 | two   |  2
-     |  2 | two   | -3
-     |  2 | two   |  4
-     |  2 | two   | -5
-     |  2 | two   | -5
-     |  2 | two   |   
-     |  2 | two   |   
-     |  2 | two   |  0
-     |  3 | three | -1
-     |  3 | three |  2
-     |  3 | three | -3
-     |  3 | three |  4
-     |  3 | three | -5
-     |  3 | three | -5
-     |  3 | three |   
-     |  3 | three |   
-     |  3 | three |  0
-     |  4 | four  | -1
-     |  4 | four  |  2
-     |  4 | four  | -3
-     |  4 | four  |  4
-     |  4 | four  | -5
-     |  4 | four  | -5
-     |  4 | four  |   
-     |  4 | four  |   
-     |  4 | four  |  0
-     |  5 | five  | -1
-     |  5 | five  |  2
-     |  5 | five  | -3
-     |  5 | five  |  4
-     |  5 | five  | -5
-     |  5 | five  | -5
-     |  5 | five  |   
-     |  5 | five  |   
-     |  5 | five  |  0
-     |  6 | six   | -1
-     |  6 | six   |  2
-     |  6 | six   | -3
-     |  6 | six   |  4
-     |  6 | six   | -5
-     |  6 | six   | -5
-     |  6 | six   |   
-     |  6 | six   |   
-     |  6 | six   |  0
-     |  7 | seven | -1
-     |  7 | seven |  2
-     |  7 | seven | -3
-     |  7 | seven |  4
-     |  7 | seven | -5
-     |  7 | seven | -5
-     |  7 | seven |   
-     |  7 | seven |   
-     |  7 | seven |  0
-     |  8 | eight | -1
-     |  8 | eight |  2
-     |  8 | eight | -3
-     |  8 | eight |  4
-     |  8 | eight | -5
-     |  8 | eight | -5
-     |  8 | eight |   
-     |  8 | eight |   
-     |  8 | eight |  0
-     |  0 | zero  | -1
-     |  0 | zero  |  2
-     |  0 | zero  | -3
-     |  0 | zero  |  4
-     |  0 | zero  | -5
-     |  0 | zero  | -5
-     |  0 | zero  |   
-     |  0 | zero  |   
-     |  0 | zero  |  0
-     |    | null  | -1
-     |    | null  |  2
-     |    | null  | -3
-     |    | null  |  4
-     |    | null  | -5
-     |    | null  | -5
-     |    | null  |   
-     |    | null  |   
-     |    | null  |  0
-     |    | zero  | -1
-     |    | zero  |  2
-     |    | zero  | -3
-     |    | zero  |  4
-     |    | zero  | -5
-     |    | zero  | -5
-     |    | zero  |   
-     |    | zero  |   
-     |    | zero  |  0
-(99 rows)
-
-SELECT '' AS "xxx", tx.ii, tx.jj, tx.kk
-  FROM (J1_TBL t1 (a, b, c) CROSS JOIN J2_TBL t2 (d, e))
-    AS tx (ii, jj, tt, ii2, kk);
- xxx | ii | jj | kk 
------+----+----+----
-     |  1 |  4 | -1
-     |  1 |  4 |  2
-     |  1 |  4 | -3
-     |  1 |  4 |  4
-     |  1 |  4 | -5
-     |  1 |  4 | -5
-     |  1 |  4 |   
-     |  1 |  4 |   
-     |  1 |  4 |  0
-     |  2 |  3 | -1
-     |  2 |  3 |  2
-     |  2 |  3 | -3
-     |  2 |  3 |  4
-     |  2 |  3 | -5
-     |  2 |  3 | -5
-     |  2 |  3 |   
-     |  2 |  3 |   
-     |  2 |  3 |  0
-     |  3 |  2 | -1
-     |  3 |  2 |  2
-     |  3 |  2 | -3
-     |  3 |  2 |  4
-     |  3 |  2 | -5
-     |  3 |  2 | -5
-     |  3 |  2 |   
-     |  3 |  2 |   
-     |  3 |  2 |  0
-     |  4 |  1 | -1
-     |  4 |  1 |  2
-     |  4 |  1 | -3
-     |  4 |  1 |  4
-     |  4 |  1 | -5
-     |  4 |  1 | -5
-     |  4 |  1 |   
-     |  4 |  1 |   
-     |  4 |  1 |  0
-     |  5 |  0 | -1
-     |  5 |  0 |  2
-     |  5 |  0 | -3
-     |  5 |  0 |  4
-     |  5 |  0 | -5
-     |  5 |  0 | -5
-     |  5 |  0 |   
-     |  5 |  0 |   
-     |  5 |  0 |  0
-     |  6 |  6 | -1
-     |  6 |  6 |  2
-     |  6 |  6 | -3
-     |  6 |  6 |  4
-     |  6 |  6 | -5
-     |  6 |  6 | -5
-     |  6 |  6 |   
-     |  6 |  6 |   
-     |  6 |  6 |  0
-     |  7 |  7 | -1
-     |  7 |  7 |  2
-     |  7 |  7 | -3
-     |  7 |  7 |  4
-     |  7 |  7 | -5
-     |  7 |  7 | -5
-     |  7 |  7 |   
-     |  7 |  7 |   
-     |  7 |  7 |  0
-     |  8 |  8 | -1
-     |  8 |  8 |  2
-     |  8 |  8 | -3
-     |  8 |  8 |  4
-     |  8 |  8 | -5
-     |  8 |  8 | -5
-     |  8 |  8 |   
-     |  8 |  8 |   
-     |  8 |  8 |  0
-     |  0 |    | -1
-     |  0 |    |  2
-     |  0 |    | -3
-     |  0 |    |  4
-     |  0 |    | -5
-     |  0 |    | -5
-     |  0 |    |   
-     |  0 |    |   
-     |  0 |    |  0
-     |    |    | -1
-     |    |    |  2
-     |    |    | -3
-     |    |    |  4
-     |    |    | -5
-     |    |    | -5
-     |    |    |   
-     |    |    |   
-     |    |    |  0
-     |    |  0 | -1
-     |    |  0 |  2
-     |    |  0 | -3
-     |    |  0 |  4
-     |    |  0 | -5
-     |    |  0 | -5
-     |    |  0 |   
-     |    |  0 |   
-     |    |  0 |  0
-(99 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL CROSS JOIN J2_TBL a CROSS JOIN J2_TBL b;
- xxx | i | j |   t   | i | k  | i | k  
------+---+---+-------+---+----+---+----
-     | 1 | 4 | one   | 1 | -1 | 1 | -1
-     | 2 | 3 | two   | 1 | -1 | 1 | -1
-     | 3 | 2 | three | 1 | -1 | 1 | -1
-     | 4 | 1 | four  | 1 | -1 | 1 | -1
-     | 5 | 0 | five  | 1 | -1 | 1 | -1
-     | 6 | 6 | six   | 1 | -1 | 1 | -1
-     | 7 | 7 | seven | 1 | -1 | 1 | -1
-     | 8 | 8 | eight | 1 | -1 | 1 | -1
-     | 0 |   | zero  | 1 | -1 | 1 | -1
-     |   |   | null  | 1 | -1 | 1 | -1
-     |   | 0 | zero  | 1 | -1 | 1 | -1
-     | 1 | 4 | one   | 1 | -1 | 2 |  2
-     | 2 | 3 | two   | 1 | -1 | 2 |  2
-     | 3 | 2 | three | 1 | -1 | 2 |  2
-     | 4 | 1 | four  | 1 | -1 | 2 |  2
-     | 5 | 0 | five  | 1 | -1 | 2 |  2
-     | 6 | 6 | six   | 1 | -1 | 2 |  2
-     | 7 | 7 | seven | 1 | -1 | 2 |  2
-     | 8 | 8 | eight | 1 | -1 | 2 |  2
-     | 0 |   | zero  | 1 | -1 | 2 |  2
-     |   |   | null  | 1 | -1 | 2 |  2
-     |   | 0 | zero  | 1 | -1 | 2 |  2
-     | 1 | 4 | one   | 1 | -1 | 3 | -3
-     | 2 | 3 | two   | 1 | -1 | 3 | -3
-     | 3 | 2 | three | 1 | -1 | 3 | -3
-     | 4 | 1 | four  | 1 | -1 | 3 | -3
-     | 5 | 0 | five  | 1 | -1 | 3 | -3
-     | 6 | 6 | six   | 1 | -1 | 3 | -3
-     | 7 | 7 | seven | 1 | -1 | 3 | -3
-     | 8 | 8 | eight | 1 | -1 | 3 | -3
-     | 0 |   | zero  | 1 | -1 | 3 | -3
-     |   |   | null  | 1 | -1 | 3 | -3
-     |   | 0 | zero  | 1 | -1 | 3 | -3
-     | 1 | 4 | one   | 1 | -1 | 2 |  4
-     | 2 | 3 | two   | 1 | -1 | 2 |  4
-     | 3 | 2 | three | 1 | -1 | 2 |  4
-     | 4 | 1 | four  | 1 | -1 | 2 |  4
-     | 5 | 0 | five  | 1 | -1 | 2 |  4
-     | 6 | 6 | six   | 1 | -1 | 2 |  4
-     | 7 | 7 | seven | 1 | -1 | 2 |  4
-     | 8 | 8 | eight | 1 | -1 | 2 |  4
-     | 0 |   | zero  | 1 | -1 | 2 |  4
-     |   |   | null  | 1 | -1 | 2 |  4
-     |   | 0 | zero  | 1 | -1 | 2 |  4
-     | 1 | 4 | one   | 1 | -1 | 5 | -5
-     | 2 | 3 | two   | 1 | -1 | 5 | -5
-     | 3 | 2 | three | 1 | -1 | 5 | -5
-     | 4 | 1 | four  | 1 | -1 | 5 | -5
-     | 5 | 0 | five  | 1 | -1 | 5 | -5
-     | 6 | 6 | six   | 1 | -1 | 5 | -5
-     | 7 | 7 | seven | 1 | -1 | 5 | -5
-     | 8 | 8 | eight | 1 | -1 | 5 | -5
-     | 0 |   | zero  | 1 | -1 | 5 | -5
-     |   |   | null  | 1 | -1 | 5 | -5
-     |   | 0 | zero  | 1 | -1 | 5 | -5
-     | 1 | 4 | one   | 1 | -1 | 5 | -5
-     | 2 | 3 | two   | 1 | -1 | 5 | -5
-     | 3 | 2 | three | 1 | -1 | 5 | -5
-     | 4 | 1 | four  | 1 | -1 | 5 | -5
-     | 5 | 0 | five  | 1 | -1 | 5 | -5
-     | 6 | 6 | six   | 1 | -1 | 5 | -5
-     | 7 | 7 | seven | 1 | -1 | 5 | -5
-     | 8 | 8 | eight | 1 | -1 | 5 | -5
-     | 0 |   | zero  | 1 | -1 | 5 | -5
-     |   |   | null  | 1 | -1 | 5 | -5
-     |   | 0 | zero  | 1 | -1 | 5 | -5
-     | 1 | 4 | one   | 1 | -1 | 0 |   
-     | 2 | 3 | two   | 1 | -1 | 0 |   
-     | 3 | 2 | three | 1 | -1 | 0 |   
-     | 4 | 1 | four  | 1 | -1 | 0 |   
-     | 5 | 0 | five  | 1 | -1 | 0 |   
-     | 6 | 6 | six   | 1 | -1 | 0 |   
-     | 7 | 7 | seven | 1 | -1 | 0 |   
-     | 8 | 8 | eight | 1 | -1 | 0 |   
-     | 0 |   | zero  | 1 | -1 | 0 |   
-     |   |   | null  | 1 | -1 | 0 |   
-     |   | 0 | zero  | 1 | -1 | 0 |   
-     | 1 | 4 | one   | 1 | -1 |   |   
-     | 2 | 3 | two   | 1 | -1 |   |   
-     | 3 | 2 | three | 1 | -1 |   |   
-     | 4 | 1 | four  | 1 | -1 |   |   
-     | 5 | 0 | five  | 1 | -1 |   |   
-     | 6 | 6 | six   | 1 | -1 |   |   
-     | 7 | 7 | seven | 1 | -1 |   |   
-     | 8 | 8 | eight | 1 | -1 |   |   
-     | 0 |   | zero  | 1 | -1 |   |   
-     |   |   | null  | 1 | -1 |   |   
-     |   | 0 | zero  | 1 | -1 |   |   
-     | 1 | 4 | one   | 1 | -1 |   |  0
-     | 2 | 3 | two   | 1 | -1 |   |  0
-     | 3 | 2 | three | 1 | -1 |   |  0
-     | 4 | 1 | four  | 1 | -1 |   |  0
-     | 5 | 0 | five  | 1 | -1 |   |  0
-     | 6 | 6 | six   | 1 | -1 |   |  0
-     | 7 | 7 | seven | 1 | -1 |   |  0
-     | 8 | 8 | eight | 1 | -1 |   |  0
-     | 0 |   | zero  | 1 | -1 |   |  0
-     |   |   | null  | 1 | -1 |   |  0
-     |   | 0 | zero  | 1 | -1 |   |  0
-     | 1 | 4 | one   | 2 |  2 | 1 | -1
-     | 2 | 3 | two   | 2 |  2 | 1 | -1
-     | 3 | 2 | three | 2 |  2 | 1 | -1
-     | 4 | 1 | four  | 2 |  2 | 1 | -1
-     | 5 | 0 | five  | 2 |  2 | 1 | -1
-     | 6 | 6 | six   | 2 |  2 | 1 | -1
-     | 7 | 7 | seven | 2 |  2 | 1 | -1
-     | 8 | 8 | eight | 2 |  2 | 1 | -1
-     | 0 |   | zero  | 2 |  2 | 1 | -1
-     |   |   | null  | 2 |  2 | 1 | -1
-     |   | 0 | zero  | 2 |  2 | 1 | -1
-     | 1 | 4 | one   | 2 |  2 | 2 |  2
-     | 2 | 3 | two   | 2 |  2 | 2 |  2
-     | 3 | 2 | three | 2 |  2 | 2 |  2
-     | 4 | 1 | four  | 2 |  2 | 2 |  2
-     | 5 | 0 | five  | 2 |  2 | 2 |  2
-     | 6 | 6 | six   | 2 |  2 | 2 |  2
-     | 7 | 7 | seven | 2 |  2 | 2 |  2
-     | 8 | 8 | eight | 2 |  2 | 2 |  2
-     | 0 |   | zero  | 2 |  2 | 2 |  2
-     |   |   | null  | 2 |  2 | 2 |  2
-     |   | 0 | zero  | 2 |  2 | 2 |  2
-     | 1 | 4 | one   | 2 |  2 | 3 | -3
-     | 2 | 3 | two   | 2 |  2 | 3 | -3
-     | 3 | 2 | three | 2 |  2 | 3 | -3
-     | 4 | 1 | four  | 2 |  2 | 3 | -3
-     | 5 | 0 | five  | 2 |  2 | 3 | -3
-     | 6 | 6 | six   | 2 |  2 | 3 | -3
-     | 7 | 7 | seven | 2 |  2 | 3 | -3
-     | 8 | 8 | eight | 2 |  2 | 3 | -3
-     | 0 |   | zero  | 2 |  2 | 3 | -3
-     |   |   | null  | 2 |  2 | 3 | -3
-     |   | 0 | zero  | 2 |  2 | 3 | -3
-     | 1 | 4 | one   | 2 |  2 | 2 |  4
-     | 2 | 3 | two   | 2 |  2 | 2 |  4
-     | 3 | 2 | three | 2 |  2 | 2 |  4
-     | 4 | 1 | four  | 2 |  2 | 2 |  4
-     | 5 | 0 | five  | 2 |  2 | 2 |  4
-     | 6 | 6 | six   | 2 |  2 | 2 |  4
-     | 7 | 7 | seven | 2 |  2 | 2 |  4
-     | 8 | 8 | eight | 2 |  2 | 2 |  4
-     | 0 |   | zero  | 2 |  2 | 2 |  4
-     |   |   | null  | 2 |  2 | 2 |  4
-     |   | 0 | zero  | 2 |  2 | 2 |  4
-     | 1 | 4 | one   | 2 |  2 | 5 | -5
-     | 2 | 3 | two   | 2 |  2 | 5 | -5
-     | 3 | 2 | three | 2 |  2 | 5 | -5
-     | 4 | 1 | four  | 2 |  2 | 5 | -5
-     | 5 | 0 | five  | 2 |  2 | 5 | -5
-     | 6 | 6 | six   | 2 |  2 | 5 | -5
-     | 7 | 7 | seven | 2 |  2 | 5 | -5
-     | 8 | 8 | eight | 2 |  2 | 5 | -5
-     | 0 |   | zero  | 2 |  2 | 5 | -5
-     |   |   | null  | 2 |  2 | 5 | -5
-     |   | 0 | zero  | 2 |  2 | 5 | -5
-     | 1 | 4 | one   | 2 |  2 | 5 | -5
-     | 2 | 3 | two   | 2 |  2 | 5 | -5
-     | 3 | 2 | three | 2 |  2 | 5 | -5
-     | 4 | 1 | four  | 2 |  2 | 5 | -5
-     | 5 | 0 | five  | 2 |  2 | 5 | -5
-     | 6 | 6 | six   | 2 |  2 | 5 | -5
-     | 7 | 7 | seven | 2 |  2 | 5 | -5
-     | 8 | 8 | eight | 2 |  2 | 5 | -5
-     | 0 |   | zero  | 2 |  2 | 5 | -5
-     |   |   | null  | 2 |  2 | 5 | -5
-     |   | 0 | zero  | 2 |  2 | 5 | -5
-     | 1 | 4 | one   | 2 |  2 | 0 |   
-     | 2 | 3 | two   | 2 |  2 | 0 |   
-     | 3 | 2 | three | 2 |  2 | 0 |   
-     | 4 | 1 | four  | 2 |  2 | 0 |   
-     | 5 | 0 | five  | 2 |  2 | 0 |   
-     | 6 | 6 | six   | 2 |  2 | 0 |   
-     | 7 | 7 | seven | 2 |  2 | 0 |   
-     | 8 | 8 | eight | 2 |  2 | 0 |   
-     | 0 |   | zero  | 2 |  2 | 0 |   
-     |   |   | null  | 2 |  2 | 0 |   
-     |   | 0 | zero  | 2 |  2 | 0 |   
-     | 1 | 4 | one   | 2 |  2 |   |   
-     | 2 | 3 | two   | 2 |  2 |   |   
-     | 3 | 2 | three | 2 |  2 |   |   
-     | 4 | 1 | four  | 2 |  2 |   |   
-     | 5 | 0 | five  | 2 |  2 |   |   
-     | 6 | 6 | six   | 2 |  2 |   |   
-     | 7 | 7 | seven | 2 |  2 |   |   
-     | 8 | 8 | eight | 2 |  2 |   |   
-     | 0 |   | zero  | 2 |  2 |   |   
-     |   |   | null  | 2 |  2 |   |   
-     |   | 0 | zero  | 2 |  2 |   |   
-     | 1 | 4 | one   | 2 |  2 |   |  0
-     | 2 | 3 | two   | 2 |  2 |   |  0
-     | 3 | 2 | three | 2 |  2 |   |  0
-     | 4 | 1 | four  | 2 |  2 |   |  0
-     | 5 | 0 | five  | 2 |  2 |   |  0
-     | 6 | 6 | six   | 2 |  2 |   |  0
-     | 7 | 7 | seven | 2 |  2 |   |  0
-     | 8 | 8 | eight | 2 |  2 |   |  0
-     | 0 |   | zero  | 2 |  2 |   |  0
-     |   |   | null  | 2 |  2 |   |  0
-     |   | 0 | zero  | 2 |  2 |   |  0
-     | 1 | 4 | one   | 3 | -3 | 1 | -1
-     | 2 | 3 | two   | 3 | -3 | 1 | -1
-     | 3 | 2 | three | 3 | -3 | 1 | -1
-     | 4 | 1 | four  | 3 | -3 | 1 | -1
-     | 5 | 0 | five  | 3 | -3 | 1 | -1
-     | 6 | 6 | six   | 3 | -3 | 1 | -1
-     | 7 | 7 | seven | 3 | -3 | 1 | -1
-     | 8 | 8 | eight | 3 | -3 | 1 | -1
-     | 0 |   | zero  | 3 | -3 | 1 | -1
-     |   |   | null  | 3 | -3 | 1 | -1
-     |   | 0 | zero  | 3 | -3 | 1 | -1
-     | 1 | 4 | one   | 3 | -3 | 2 |  2
-     | 2 | 3 | two   | 3 | -3 | 2 |  2
-     | 3 | 2 | three | 3 | -3 | 2 |  2
-     | 4 | 1 | four  | 3 | -3 | 2 |  2
-     | 5 | 0 | five  | 3 | -3 | 2 |  2
-     | 6 | 6 | six   | 3 | -3 | 2 |  2
-     | 7 | 7 | seven | 3 | -3 | 2 |  2
-     | 8 | 8 | eight | 3 | -3 | 2 |  2
-     | 0 |   | zero  | 3 | -3 | 2 |  2
-     |   |   | null  | 3 | -3 | 2 |  2
-     |   | 0 | zero  | 3 | -3 | 2 |  2
-     | 1 | 4 | one   | 3 | -3 | 3 | -3
-     | 2 | 3 | two   | 3 | -3 | 3 | -3
-     | 3 | 2 | three | 3 | -3 | 3 | -3
-     | 4 | 1 | four  | 3 | -3 | 3 | -3
-     | 5 | 0 | five  | 3 | -3 | 3 | -3
-     | 6 | 6 | six   | 3 | -3 | 3 | -3
-     | 7 | 7 | seven | 3 | -3 | 3 | -3
-     | 8 | 8 | eight | 3 | -3 | 3 | -3
-     | 0 |   | zero  | 3 | -3 | 3 | -3
-     |   |   | null  | 3 | -3 | 3 | -3
-     |   | 0 | zero  | 3 | -3 | 3 | -3
-     | 1 | 4 | one   | 3 | -3 | 2 |  4
-     | 2 | 3 | two   | 3 | -3 | 2 |  4
-     | 3 | 2 | three | 3 | -3 | 2 |  4
-     | 4 | 1 | four  | 3 | -3 | 2 |  4
-     | 5 | 0 | five  | 3 | -3 | 2 |  4
-     | 6 | 6 | six   | 3 | -3 | 2 |  4
-     | 7 | 7 | seven | 3 | -3 | 2 |  4
-     | 8 | 8 | eight | 3 | -3 | 2 |  4
-     | 0 |   | zero  | 3 | -3 | 2 |  4
-     |   |   | null  | 3 | -3 | 2 |  4
-     |   | 0 | zero  | 3 | -3 | 2 |  4
-     | 1 | 4 | one   | 3 | -3 | 5 | -5
-     | 2 | 3 | two   | 3 | -3 | 5 | -5
-     | 3 | 2 | three | 3 | -3 | 5 | -5
-     | 4 | 1 | four  | 3 | -3 | 5 | -5
-     | 5 | 0 | five  | 3 | -3 | 5 | -5
-     | 6 | 6 | six   | 3 | -3 | 5 | -5
-     | 7 | 7 | seven | 3 | -3 | 5 | -5
-     | 8 | 8 | eight | 3 | -3 | 5 | -5
-     | 0 |   | zero  | 3 | -3 | 5 | -5
-     |   |   | null  | 3 | -3 | 5 | -5
-     |   | 0 | zero  | 3 | -3 | 5 | -5
-     | 1 | 4 | one   | 3 | -3 | 5 | -5
-     | 2 | 3 | two   | 3 | -3 | 5 | -5
-     | 3 | 2 | three | 3 | -3 | 5 | -5
-     | 4 | 1 | four  | 3 | -3 | 5 | -5
-     | 5 | 0 | five  | 3 | -3 | 5 | -5
-     | 6 | 6 | six   | 3 | -3 | 5 | -5
-     | 7 | 7 | seven | 3 | -3 | 5 | -5
-     | 8 | 8 | eight | 3 | -3 | 5 | -5
-     | 0 |   | zero  | 3 | -3 | 5 | -5
-     |   |   | null  | 3 | -3 | 5 | -5
-     |   | 0 | zero  | 3 | -3 | 5 | -5
-     | 1 | 4 | one   | 3 | -3 | 0 |   
-     | 2 | 3 | two   | 3 | -3 | 0 |   
-     | 3 | 2 | three | 3 | -3 | 0 |   
-     | 4 | 1 | four  | 3 | -3 | 0 |   
-     | 5 | 0 | five  | 3 | -3 | 0 |   
-     | 6 | 6 | six   | 3 | -3 | 0 |   
-     | 7 | 7 | seven | 3 | -3 | 0 |   
-     | 8 | 8 | eight | 3 | -3 | 0 |   
-     | 0 |   | zero  | 3 | -3 | 0 |   
-     |   |   | null  | 3 | -3 | 0 |   
-     |   | 0 | zero  | 3 | -3 | 0 |   
-     | 1 | 4 | one   | 3 | -3 |   |   
-     | 2 | 3 | two   | 3 | -3 |   |   
-     | 3 | 2 | three | 3 | -3 |   |   
-     | 4 | 1 | four  | 3 | -3 |   |   
-     | 5 | 0 | five  | 3 | -3 |   |   
-     | 6 | 6 | six   | 3 | -3 |   |   
-     | 7 | 7 | seven | 3 | -3 |   |   
-     | 8 | 8 | eight | 3 | -3 |   |   
-     | 0 |   | zero  | 3 | -3 |   |   
-     |   |   | null  | 3 | -3 |   |   
-     |   | 0 | zero  | 3 | -3 |   |   
-     | 1 | 4 | one   | 3 | -3 |   |  0
-     | 2 | 3 | two   | 3 | -3 |   |  0
-     | 3 | 2 | three | 3 | -3 |   |  0
-     | 4 | 1 | four  | 3 | -3 |   |  0
-     | 5 | 0 | five  | 3 | -3 |   |  0
-     | 6 | 6 | six   | 3 | -3 |   |  0
-     | 7 | 7 | seven | 3 | -3 |   |  0
-     | 8 | 8 | eight | 3 | -3 |   |  0
-     | 0 |   | zero  | 3 | -3 |   |  0
-     |   |   | null  | 3 | -3 |   |  0
-     |   | 0 | zero  | 3 | -3 |   |  0
-     | 1 | 4 | one   | 2 |  4 | 1 | -1
-     | 2 | 3 | two   | 2 |  4 | 1 | -1
-     | 3 | 2 | three | 2 |  4 | 1 | -1
-     | 4 | 1 | four  | 2 |  4 | 1 | -1
-     | 5 | 0 | five  | 2 |  4 | 1 | -1
-     | 6 | 6 | six   | 2 |  4 | 1 | -1
-     | 7 | 7 | seven | 2 |  4 | 1 | -1
-     | 8 | 8 | eight | 2 |  4 | 1 | -1
-     | 0 |   | zero  | 2 |  4 | 1 | -1
-     |   |   | null  | 2 |  4 | 1 | -1
-     |   | 0 | zero  | 2 |  4 | 1 | -1
-     | 1 | 4 | one   | 2 |  4 | 2 |  2
-     | 2 | 3 | two   | 2 |  4 | 2 |  2
-     | 3 | 2 | three | 2 |  4 | 2 |  2
-     | 4 | 1 | four  | 2 |  4 | 2 |  2
-     | 5 | 0 | five  | 2 |  4 | 2 |  2
-     | 6 | 6 | six   | 2 |  4 | 2 |  2
-     | 7 | 7 | seven | 2 |  4 | 2 |  2
-     | 8 | 8 | eight | 2 |  4 | 2 |  2
-     | 0 |   | zero  | 2 |  4 | 2 |  2
-     |   |   | null  | 2 |  4 | 2 |  2
-     |   | 0 | zero  | 2 |  4 | 2 |  2
-     | 1 | 4 | one   | 2 |  4 | 3 | -3
-     | 2 | 3 | two   | 2 |  4 | 3 | -3
-     | 3 | 2 | three | 2 |  4 | 3 | -3
-     | 4 | 1 | four  | 2 |  4 | 3 | -3
-     | 5 | 0 | five  | 2 |  4 | 3 | -3
-     | 6 | 6 | six   | 2 |  4 | 3 | -3
-     | 7 | 7 | seven | 2 |  4 | 3 | -3
-     | 8 | 8 | eight | 2 |  4 | 3 | -3
-     | 0 |   | zero  | 2 |  4 | 3 | -3
-     |   |   | null  | 2 |  4 | 3 | -3
-     |   | 0 | zero  | 2 |  4 | 3 | -3
-     | 1 | 4 | one   | 2 |  4 | 2 |  4
-     | 2 | 3 | two   | 2 |  4 | 2 |  4
-     | 3 | 2 | three | 2 |  4 | 2 |  4
-     | 4 | 1 | four  | 2 |  4 | 2 |  4
-     | 5 | 0 | five  | 2 |  4 | 2 |  4
-     | 6 | 6 | six   | 2 |  4 | 2 |  4
-     | 7 | 7 | seven | 2 |  4 | 2 |  4
-     | 8 | 8 | eight | 2 |  4 | 2 |  4
-     | 0 |   | zero  | 2 |  4 | 2 |  4
-     |   |   | null  | 2 |  4 | 2 |  4
-     |   | 0 | zero  | 2 |  4 | 2 |  4
-     | 1 | 4 | one   | 2 |  4 | 5 | -5
-     | 2 | 3 | two   | 2 |  4 | 5 | -5
-     | 3 | 2 | three | 2 |  4 | 5 | -5
-     | 4 | 1 | four  | 2 |  4 | 5 | -5
-     | 5 | 0 | five  | 2 |  4 | 5 | -5
-     | 6 | 6 | six   | 2 |  4 | 5 | -5
-     | 7 | 7 | seven | 2 |  4 | 5 | -5
-     | 8 | 8 | eight | 2 |  4 | 5 | -5
-     | 0 |   | zero  | 2 |  4 | 5 | -5
-     |   |   | null  | 2 |  4 | 5 | -5
-     |   | 0 | zero  | 2 |  4 | 5 | -5
-     | 1 | 4 | one   | 2 |  4 | 5 | -5
-     | 2 | 3 | two   | 2 |  4 | 5 | -5
-     | 3 | 2 | three | 2 |  4 | 5 | -5
-     | 4 | 1 | four  | 2 |  4 | 5 | -5
-     | 5 | 0 | five  | 2 |  4 | 5 | -5
-     | 6 | 6 | six   | 2 |  4 | 5 | -5
-     | 7 | 7 | seven | 2 |  4 | 5 | -5
-     | 8 | 8 | eight | 2 |  4 | 5 | -5
-     | 0 |   | zero  | 2 |  4 | 5 | -5
-     |   |   | null  | 2 |  4 | 5 | -5
-     |   | 0 | zero  | 2 |  4 | 5 | -5
-     | 1 | 4 | one   | 2 |  4 | 0 |   
-     | 2 | 3 | two   | 2 |  4 | 0 |   
-     | 3 | 2 | three | 2 |  4 | 0 |   
-     | 4 | 1 | four  | 2 |  4 | 0 |   
-     | 5 | 0 | five  | 2 |  4 | 0 |   
-     | 6 | 6 | six   | 2 |  4 | 0 |   
-     | 7 | 7 | seven | 2 |  4 | 0 |   
-     | 8 | 8 | eight | 2 |  4 | 0 |   
-     | 0 |   | zero  | 2 |  4 | 0 |   
-     |   |   | null  | 2 |  4 | 0 |   
-     |   | 0 | zero  | 2 |  4 | 0 |   
-     | 1 | 4 | one   | 2 |  4 |   |   
-     | 2 | 3 | two   | 2 |  4 |   |   
-     | 3 | 2 | three | 2 |  4 |   |   
-     | 4 | 1 | four  | 2 |  4 |   |   
-     | 5 | 0 | five  | 2 |  4 |   |   
-     | 6 | 6 | six   | 2 |  4 |   |   
-     | 7 | 7 | seven | 2 |  4 |   |   
-     | 8 | 8 | eight | 2 |  4 |   |   
-     | 0 |   | zero  | 2 |  4 |   |   
-     |   |   | null  | 2 |  4 |   |   
-     |   | 0 | zero  | 2 |  4 |   |   
-     | 1 | 4 | one   | 2 |  4 |   |  0
-     | 2 | 3 | two   | 2 |  4 |   |  0
-     | 3 | 2 | three | 2 |  4 |   |  0
-     | 4 | 1 | four  | 2 |  4 |   |  0
-     | 5 | 0 | five  | 2 |  4 |   |  0
-     | 6 | 6 | six   | 2 |  4 |   |  0
-     | 7 | 7 | seven | 2 |  4 |   |  0
-     | 8 | 8 | eight | 2 |  4 |   |  0
-     | 0 |   | zero  | 2 |  4 |   |  0
-     |   |   | null  | 2 |  4 |   |  0
-     |   | 0 | zero  | 2 |  4 |   |  0
-     | 1 | 4 | one   | 5 | -5 | 1 | -1
-     | 2 | 3 | two   | 5 | -5 | 1 | -1
-     | 3 | 2 | three | 5 | -5 | 1 | -1
-     | 4 | 1 | four  | 5 | -5 | 1 | -1
-     | 5 | 0 | five  | 5 | -5 | 1 | -1
-     | 6 | 6 | six   | 5 | -5 | 1 | -1
-     | 7 | 7 | seven | 5 | -5 | 1 | -1
-     | 8 | 8 | eight | 5 | -5 | 1 | -1
-     | 0 |   | zero  | 5 | -5 | 1 | -1
-     |   |   | null  | 5 | -5 | 1 | -1
-     |   | 0 | zero  | 5 | -5 | 1 | -1
-     | 1 | 4 | one   | 5 | -5 | 2 |  2
-     | 2 | 3 | two   | 5 | -5 | 2 |  2
-     | 3 | 2 | three | 5 | -5 | 2 |  2
-     | 4 | 1 | four  | 5 | -5 | 2 |  2
-     | 5 | 0 | five  | 5 | -5 | 2 |  2
-     | 6 | 6 | six   | 5 | -5 | 2 |  2
-     | 7 | 7 | seven | 5 | -5 | 2 |  2
-     | 8 | 8 | eight | 5 | -5 | 2 |  2
-     | 0 |   | zero  | 5 | -5 | 2 |  2
-     |   |   | null  | 5 | -5 | 2 |  2
-     |   | 0 | zero  | 5 | -5 | 2 |  2
-     | 1 | 4 | one   | 5 | -5 | 3 | -3
-     | 2 | 3 | two   | 5 | -5 | 3 | -3
-     | 3 | 2 | three | 5 | -5 | 3 | -3
-     | 4 | 1 | four  | 5 | -5 | 3 | -3
-     | 5 | 0 | five  | 5 | -5 | 3 | -3
-     | 6 | 6 | six   | 5 | -5 | 3 | -3
-     | 7 | 7 | seven | 5 | -5 | 3 | -3
-     | 8 | 8 | eight | 5 | -5 | 3 | -3
-     | 0 |   | zero  | 5 | -5 | 3 | -3
-     |   |   | null  | 5 | -5 | 3 | -3
-     |   | 0 | zero  | 5 | -5 | 3 | -3
-     | 1 | 4 | one   | 5 | -5 | 2 |  4
-     | 2 | 3 | two   | 5 | -5 | 2 |  4
-     | 3 | 2 | three | 5 | -5 | 2 |  4
-     | 4 | 1 | four  | 5 | -5 | 2 |  4
-     | 5 | 0 | five  | 5 | -5 | 2 |  4
-     | 6 | 6 | six   | 5 | -5 | 2 |  4
-     | 7 | 7 | seven | 5 | -5 | 2 |  4
-     | 8 | 8 | eight | 5 | -5 | 2 |  4
-     | 0 |   | zero  | 5 | -5 | 2 |  4
-     |   |   | null  | 5 | -5 | 2 |  4
-     |   | 0 | zero  | 5 | -5 | 2 |  4
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
-     |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
-     |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 0 |   
-     | 2 | 3 | two   | 5 | -5 | 0 |   
-     | 3 | 2 | three | 5 | -5 | 0 |   
-     | 4 | 1 | four  | 5 | -5 | 0 |   
-     | 5 | 0 | five  | 5 | -5 | 0 |   
-     | 6 | 6 | six   | 5 | -5 | 0 |   
-     | 7 | 7 | seven | 5 | -5 | 0 |   
-     | 8 | 8 | eight | 5 | -5 | 0 |   
-     | 0 |   | zero  | 5 | -5 | 0 |   
-     |   |   | null  | 5 | -5 | 0 |   
-     |   | 0 | zero  | 5 | -5 | 0 |   
-     | 1 | 4 | one   | 5 | -5 |   |   
-     | 2 | 3 | two   | 5 | -5 |   |   
-     | 3 | 2 | three | 5 | -5 |   |   
-     | 4 | 1 | four  | 5 | -5 |   |   
-     | 5 | 0 | five  | 5 | -5 |   |   
-     | 6 | 6 | six   | 5 | -5 |   |   
-     | 7 | 7 | seven | 5 | -5 |   |   
-     | 8 | 8 | eight | 5 | -5 |   |   
-     | 0 |   | zero  | 5 | -5 |   |   
-     |   |   | null  | 5 | -5 |   |   
-     |   | 0 | zero  | 5 | -5 |   |   
-     | 1 | 4 | one   | 5 | -5 |   |  0
-     | 2 | 3 | two   | 5 | -5 |   |  0
-     | 3 | 2 | three | 5 | -5 |   |  0
-     | 4 | 1 | four  | 5 | -5 |   |  0
-     | 5 | 0 | five  | 5 | -5 |   |  0
-     | 6 | 6 | six   | 5 | -5 |   |  0
-     | 7 | 7 | seven | 5 | -5 |   |  0
-     | 8 | 8 | eight | 5 | -5 |   |  0
-     | 0 |   | zero  | 5 | -5 |   |  0
-     |   |   | null  | 5 | -5 |   |  0
-     |   | 0 | zero  | 5 | -5 |   |  0
-     | 1 | 4 | one   | 5 | -5 | 1 | -1
-     | 2 | 3 | two   | 5 | -5 | 1 | -1
-     | 3 | 2 | three | 5 | -5 | 1 | -1
-     | 4 | 1 | four  | 5 | -5 | 1 | -1
-     | 5 | 0 | five  | 5 | -5 | 1 | -1
-     | 6 | 6 | six   | 5 | -5 | 1 | -1
-     | 7 | 7 | seven | 5 | -5 | 1 | -1
-     | 8 | 8 | eight | 5 | -5 | 1 | -1
-     | 0 |   | zero  | 5 | -5 | 1 | -1
-     |   |   | null  | 5 | -5 | 1 | -1
-     |   | 0 | zero  | 5 | -5 | 1 | -1
-     | 1 | 4 | one   | 5 | -5 | 2 |  2
-     | 2 | 3 | two   | 5 | -5 | 2 |  2
-     | 3 | 2 | three | 5 | -5 | 2 |  2
-     | 4 | 1 | four  | 5 | -5 | 2 |  2
-     | 5 | 0 | five  | 5 | -5 | 2 |  2
-     | 6 | 6 | six   | 5 | -5 | 2 |  2
-     | 7 | 7 | seven | 5 | -5 | 2 |  2
-     | 8 | 8 | eight | 5 | -5 | 2 |  2
-     | 0 |   | zero  | 5 | -5 | 2 |  2
-     |   |   | null  | 5 | -5 | 2 |  2
-     |   | 0 | zero  | 5 | -5 | 2 |  2
-     | 1 | 4 | one   | 5 | -5 | 3 | -3
-     | 2 | 3 | two   | 5 | -5 | 3 | -3
-     | 3 | 2 | three | 5 | -5 | 3 | -3
-     | 4 | 1 | four  | 5 | -5 | 3 | -3
-     | 5 | 0 | five  | 5 | -5 | 3 | -3
-     | 6 | 6 | six   | 5 | -5 | 3 | -3
-     | 7 | 7 | seven | 5 | -5 | 3 | -3
-     | 8 | 8 | eight | 5 | -5 | 3 | -3
-     | 0 |   | zero  | 5 | -5 | 3 | -3
-     |   |   | null  | 5 | -5 | 3 | -3
-     |   | 0 | zero  | 5 | -5 | 3 | -3
-     | 1 | 4 | one   | 5 | -5 | 2 |  4
-     | 2 | 3 | two   | 5 | -5 | 2 |  4
-     | 3 | 2 | three | 5 | -5 | 2 |  4
-     | 4 | 1 | four  | 5 | -5 | 2 |  4
-     | 5 | 0 | five  | 5 | -5 | 2 |  4
-     | 6 | 6 | six   | 5 | -5 | 2 |  4
-     | 7 | 7 | seven | 5 | -5 | 2 |  4
-     | 8 | 8 | eight | 5 | -5 | 2 |  4
-     | 0 |   | zero  | 5 | -5 | 2 |  4
-     |   |   | null  | 5 | -5 | 2 |  4
-     |   | 0 | zero  | 5 | -5 | 2 |  4
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
-     |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 5 | -5
-     | 2 | 3 | two   | 5 | -5 | 5 | -5
-     | 3 | 2 | three | 5 | -5 | 5 | -5
-     | 4 | 1 | four  | 5 | -5 | 5 | -5
-     | 5 | 0 | five  | 5 | -5 | 5 | -5
-     | 6 | 6 | six   | 5 | -5 | 5 | -5
-     | 7 | 7 | seven | 5 | -5 | 5 | -5
-     | 8 | 8 | eight | 5 | -5 | 5 | -5
-     | 0 |   | zero  | 5 | -5 | 5 | -5
-     |   |   | null  | 5 | -5 | 5 | -5
-     |   | 0 | zero  | 5 | -5 | 5 | -5
-     | 1 | 4 | one   | 5 | -5 | 0 |   
-     | 2 | 3 | two   | 5 | -5 | 0 |   
-     | 3 | 2 | three | 5 | -5 | 0 |   
-     | 4 | 1 | four  | 5 | -5 | 0 |   
-     | 5 | 0 | five  | 5 | -5 | 0 |   
-     | 6 | 6 | six   | 5 | -5 | 0 |   
-     | 7 | 7 | seven | 5 | -5 | 0 |   
-     | 8 | 8 | eight | 5 | -5 | 0 |   
-     | 0 |   | zero  | 5 | -5 | 0 |   
-     |   |   | null  | 5 | -5 | 0 |   
-     |   | 0 | zero  | 5 | -5 | 0 |   
-     | 1 | 4 | one   | 5 | -5 |   |   
-     | 2 | 3 | two   | 5 | -5 |   |   
-     | 3 | 2 | three | 5 | -5 |   |   
-     | 4 | 1 | four  | 5 | -5 |   |   
-     | 5 | 0 | five  | 5 | -5 |   |   
-     | 6 | 6 | six   | 5 | -5 |   |   
-     | 7 | 7 | seven | 5 | -5 |   |   
-     | 8 | 8 | eight | 5 | -5 |   |   
-     | 0 |   | zero  | 5 | -5 |   |   
-     |   |   | null  | 5 | -5 |   |   
-     |   | 0 | zero  | 5 | -5 |   |   
-     | 1 | 4 | one   | 5 | -5 |   |  0
-     | 2 | 3 | two   | 5 | -5 |   |  0
-     | 3 | 2 | three | 5 | -5 |   |  0
-     | 4 | 1 | four  | 5 | -5 |   |  0
-     | 5 | 0 | five  | 5 | -5 |   |  0
-     | 6 | 6 | six   | 5 | -5 |   |  0
-     | 7 | 7 | seven | 5 | -5 |   |  0
-     | 8 | 8 | eight | 5 | -5 |   |  0
-     | 0 |   | zero  | 5 | -5 |   |  0
-     |   |   | null  | 5 | -5 |   |  0
-     |   | 0 | zero  | 5 | -5 |   |  0
-     | 1 | 4 | one   | 0 |    | 1 | -1
-     | 2 | 3 | two   | 0 |    | 1 | -1
-     | 3 | 2 | three | 0 |    | 1 | -1
-     | 4 | 1 | four  | 0 |    | 1 | -1
-     | 5 | 0 | five  | 0 |    | 1 | -1
-     | 6 | 6 | six   | 0 |    | 1 | -1
-     | 7 | 7 | seven | 0 |    | 1 | -1
-     | 8 | 8 | eight | 0 |    | 1 | -1
-     | 0 |   | zero  | 0 |    | 1 | -1
-     |   |   | null  | 0 |    | 1 | -1
-     |   | 0 | zero  | 0 |    | 1 | -1
-     | 1 | 4 | one   | 0 |    | 2 |  2
-     | 2 | 3 | two   | 0 |    | 2 |  2
-     | 3 | 2 | three | 0 |    | 2 |  2
-     | 4 | 1 | four  | 0 |    | 2 |  2
-     | 5 | 0 | five  | 0 |    | 2 |  2
-     | 6 | 6 | six   | 0 |    | 2 |  2
-     | 7 | 7 | seven | 0 |    | 2 |  2
-     | 8 | 8 | eight | 0 |    | 2 |  2
-     | 0 |   | zero  | 0 |    | 2 |  2
-     |   |   | null  | 0 |    | 2 |  2
-     |   | 0 | zero  | 0 |    | 2 |  2
-     | 1 | 4 | one   | 0 |    | 3 | -3
-     | 2 | 3 | two   | 0 |    | 3 | -3
-     | 3 | 2 | three | 0 |    | 3 | -3
-     | 4 | 1 | four  | 0 |    | 3 | -3
-     | 5 | 0 | five  | 0 |    | 3 | -3
-     | 6 | 6 | six   | 0 |    | 3 | -3
-     | 7 | 7 | seven | 0 |    | 3 | -3
-     | 8 | 8 | eight | 0 |    | 3 | -3
-     | 0 |   | zero  | 0 |    | 3 | -3
-     |   |   | null  | 0 |    | 3 | -3
-     |   | 0 | zero  | 0 |    | 3 | -3
-     | 1 | 4 | one   | 0 |    | 2 |  4
-     | 2 | 3 | two   | 0 |    | 2 |  4
-     | 3 | 2 | three | 0 |    | 2 |  4
-     | 4 | 1 | four  | 0 |    | 2 |  4
-     | 5 | 0 | five  | 0 |    | 2 |  4
-     | 6 | 6 | six   | 0 |    | 2 |  4
-     | 7 | 7 | seven | 0 |    | 2 |  4
-     | 8 | 8 | eight | 0 |    | 2 |  4
-     | 0 |   | zero  | 0 |    | 2 |  4
-     |   |   | null  | 0 |    | 2 |  4
-     |   | 0 | zero  | 0 |    | 2 |  4
-     | 1 | 4 | one   | 0 |    | 5 | -5
-     | 2 | 3 | two   | 0 |    | 5 | -5
-     | 3 | 2 | three | 0 |    | 5 | -5
-     | 4 | 1 | four  | 0 |    | 5 | -5
-     | 5 | 0 | five  | 0 |    | 5 | -5
-     | 6 | 6 | six   | 0 |    | 5 | -5
-     | 7 | 7 | seven | 0 |    | 5 | -5
-     | 8 | 8 | eight | 0 |    | 5 | -5
-     | 0 |   | zero  | 0 |    | 5 | -5
-     |   |   | null  | 0 |    | 5 | -5
-     |   | 0 | zero  | 0 |    | 5 | -5
-     | 1 | 4 | one   | 0 |    | 5 | -5
-     | 2 | 3 | two   | 0 |    | 5 | -5
-     | 3 | 2 | three | 0 |    | 5 | -5
-     | 4 | 1 | four  | 0 |    | 5 | -5
-     | 5 | 0 | five  | 0 |    | 5 | -5
-     | 6 | 6 | six   | 0 |    | 5 | -5
-     | 7 | 7 | seven | 0 |    | 5 | -5
-     | 8 | 8 | eight | 0 |    | 5 | -5
-     | 0 |   | zero  | 0 |    | 5 | -5
-     |   |   | null  | 0 |    | 5 | -5
-     |   | 0 | zero  | 0 |    | 5 | -5
-     | 1 | 4 | one   | 0 |    | 0 |   
-     | 2 | 3 | two   | 0 |    | 0 |   
-     | 3 | 2 | three | 0 |    | 0 |   
-     | 4 | 1 | four  | 0 |    | 0 |   
-     | 5 | 0 | five  | 0 |    | 0 |   
-     | 6 | 6 | six   | 0 |    | 0 |   
-     | 7 | 7 | seven | 0 |    | 0 |   
-     | 8 | 8 | eight | 0 |    | 0 |   
-     | 0 |   | zero  | 0 |    | 0 |   
-     |   |   | null  | 0 |    | 0 |   
-     |   | 0 | zero  | 0 |    | 0 |   
-     | 1 | 4 | one   | 0 |    |   |   
-     | 2 | 3 | two   | 0 |    |   |   
-     | 3 | 2 | three | 0 |    |   |   
-     | 4 | 1 | four  | 0 |    |   |   
-     | 5 | 0 | five  | 0 |    |   |   
-     | 6 | 6 | six   | 0 |    |   |   
-     | 7 | 7 | seven | 0 |    |   |   
-     | 8 | 8 | eight | 0 |    |   |   
-     | 0 |   | zero  | 0 |    |   |   
-     |   |   | null  | 0 |    |   |   
-     |   | 0 | zero  | 0 |    |   |   
-     | 1 | 4 | one   | 0 |    |   |  0
-     | 2 | 3 | two   | 0 |    |   |  0
-     | 3 | 2 | three | 0 |    |   |  0
-     | 4 | 1 | four  | 0 |    |   |  0
-     | 5 | 0 | five  | 0 |    |   |  0
-     | 6 | 6 | six   | 0 |    |   |  0
-     | 7 | 7 | seven | 0 |    |   |  0
-     | 8 | 8 | eight | 0 |    |   |  0
-     | 0 |   | zero  | 0 |    |   |  0
-     |   |   | null  | 0 |    |   |  0
-     |   | 0 | zero  | 0 |    |   |  0
-     | 1 | 4 | one   |   |    | 1 | -1
-     | 2 | 3 | two   |   |    | 1 | -1
-     | 3 | 2 | three |   |    | 1 | -1
-     | 4 | 1 | four  |   |    | 1 | -1
-     | 5 | 0 | five  |   |    | 1 | -1
-     | 6 | 6 | six   |   |    | 1 | -1
-     | 7 | 7 | seven |   |    | 1 | -1
-     | 8 | 8 | eight |   |    | 1 | -1
-     | 0 |   | zero  |   |    | 1 | -1
-     |   |   | null  |   |    | 1 | -1
-     |   | 0 | zero  |   |    | 1 | -1
-     | 1 | 4 | one   |   |    | 2 |  2
-     | 2 | 3 | two   |   |    | 2 |  2
-     | 3 | 2 | three |   |    | 2 |  2
-     | 4 | 1 | four  |   |    | 2 |  2
-     | 5 | 0 | five  |   |    | 2 |  2
-     | 6 | 6 | six   |   |    | 2 |  2
-     | 7 | 7 | seven |   |    | 2 |  2
-     | 8 | 8 | eight |   |    | 2 |  2
-     | 0 |   | zero  |   |    | 2 |  2
-     |   |   | null  |   |    | 2 |  2
-     |   | 0 | zero  |   |    | 2 |  2
-     | 1 | 4 | one   |   |    | 3 | -3
-     | 2 | 3 | two   |   |    | 3 | -3
-     | 3 | 2 | three |   |    | 3 | -3
-     | 4 | 1 | four  |   |    | 3 | -3
-     | 5 | 0 | five  |   |    | 3 | -3
-     | 6 | 6 | six   |   |    | 3 | -3
-     | 7 | 7 | seven |   |    | 3 | -3
-     | 8 | 8 | eight |   |    | 3 | -3
-     | 0 |   | zero  |   |    | 3 | -3
-     |   |   | null  |   |    | 3 | -3
-     |   | 0 | zero  |   |    | 3 | -3
-     | 1 | 4 | one   |   |    | 2 |  4
-     | 2 | 3 | two   |   |    | 2 |  4
-     | 3 | 2 | three |   |    | 2 |  4
-     | 4 | 1 | four  |   |    | 2 |  4
-     | 5 | 0 | five  |   |    | 2 |  4
-     | 6 | 6 | six   |   |    | 2 |  4
-     | 7 | 7 | seven |   |    | 2 |  4
-     | 8 | 8 | eight |   |    | 2 |  4
-     | 0 |   | zero  |   |    | 2 |  4
-     |   |   | null  |   |    | 2 |  4
-     |   | 0 | zero  |   |    | 2 |  4
-     | 1 | 4 | one   |   |    | 5 | -5
-     | 2 | 3 | two   |   |    | 5 | -5
-     | 3 | 2 | three |   |    | 5 | -5
-     | 4 | 1 | four  |   |    | 5 | -5
-     | 5 | 0 | five  |   |    | 5 | -5
-     | 6 | 6 | six   |   |    | 5 | -5
-     | 7 | 7 | seven |   |    | 5 | -5
-     | 8 | 8 | eight |   |    | 5 | -5
-     | 0 |   | zero  |   |    | 5 | -5
-     |   |   | null  |   |    | 5 | -5
-     |   | 0 | zero  |   |    | 5 | -5
-     | 1 | 4 | one   |   |    | 5 | -5
-     | 2 | 3 | two   |   |    | 5 | -5
-     | 3 | 2 | three |   |    | 5 | -5
-     | 4 | 1 | four  |   |    | 5 | -5
-     | 5 | 0 | five  |   |    | 5 | -5
-     | 6 | 6 | six   |   |    | 5 | -5
-     | 7 | 7 | seven |   |    | 5 | -5
-     | 8 | 8 | eight |   |    | 5 | -5
-     | 0 |   | zero  |   |    | 5 | -5
-     |   |   | null  |   |    | 5 | -5
-     |   | 0 | zero  |   |    | 5 | -5
-     | 1 | 4 | one   |   |    | 0 |   
-     | 2 | 3 | two   |   |    | 0 |   
-     | 3 | 2 | three |   |    | 0 |   
-     | 4 | 1 | four  |   |    | 0 |   
-     | 5 | 0 | five  |   |    | 0 |   
-     | 6 | 6 | six   |   |    | 0 |   
-     | 7 | 7 | seven |   |    | 0 |   
-     | 8 | 8 | eight |   |    | 0 |   
-     | 0 |   | zero  |   |    | 0 |   
-     |   |   | null  |   |    | 0 |   
-     |   | 0 | zero  |   |    | 0 |   
-     | 1 | 4 | one   |   |    |   |   
-     | 2 | 3 | two   |   |    |   |   
-     | 3 | 2 | three |   |    |   |   
-     | 4 | 1 | four  |   |    |   |   
-     | 5 | 0 | five  |   |    |   |   
-     | 6 | 6 | six   |   |    |   |   
-     | 7 | 7 | seven |   |    |   |   
-     | 8 | 8 | eight |   |    |   |   
-     | 0 |   | zero  |   |    |   |   
-     |   |   | null  |   |    |   |   
-     |   | 0 | zero  |   |    |   |   
-     | 1 | 4 | one   |   |    |   |  0
-     | 2 | 3 | two   |   |    |   |  0
-     | 3 | 2 | three |   |    |   |  0
-     | 4 | 1 | four  |   |    |   |  0
-     | 5 | 0 | five  |   |    |   |  0
-     | 6 | 6 | six   |   |    |   |  0
-     | 7 | 7 | seven |   |    |   |  0
-     | 8 | 8 | eight |   |    |   |  0
-     | 0 |   | zero  |   |    |   |  0
-     |   |   | null  |   |    |   |  0
-     |   | 0 | zero  |   |    |   |  0
-     | 1 | 4 | one   |   |  0 | 1 | -1
-     | 2 | 3 | two   |   |  0 | 1 | -1
-     | 3 | 2 | three |   |  0 | 1 | -1
-     | 4 | 1 | four  |   |  0 | 1 | -1
-     | 5 | 0 | five  |   |  0 | 1 | -1
-     | 6 | 6 | six   |   |  0 | 1 | -1
-     | 7 | 7 | seven |   |  0 | 1 | -1
-     | 8 | 8 | eight |   |  0 | 1 | -1
-     | 0 |   | zero  |   |  0 | 1 | -1
-     |   |   | null  |   |  0 | 1 | -1
-     |   | 0 | zero  |   |  0 | 1 | -1
-     | 1 | 4 | one   |   |  0 | 2 |  2
-     | 2 | 3 | two   |   |  0 | 2 |  2
-     | 3 | 2 | three |   |  0 | 2 |  2
-     | 4 | 1 | four  |   |  0 | 2 |  2
-     | 5 | 0 | five  |   |  0 | 2 |  2
-     | 6 | 6 | six   |   |  0 | 2 |  2
-     | 7 | 7 | seven |   |  0 | 2 |  2
-     | 8 | 8 | eight |   |  0 | 2 |  2
-     | 0 |   | zero  |   |  0 | 2 |  2
-     |   |   | null  |   |  0 | 2 |  2
-     |   | 0 | zero  |   |  0 | 2 |  2
-     | 1 | 4 | one   |   |  0 | 3 | -3
-     | 2 | 3 | two   |   |  0 | 3 | -3
-     | 3 | 2 | three |   |  0 | 3 | -3
-     | 4 | 1 | four  |   |  0 | 3 | -3
-     | 5 | 0 | five  |   |  0 | 3 | -3
-     | 6 | 6 | six   |   |  0 | 3 | -3
-     | 7 | 7 | seven |   |  0 | 3 | -3
-     | 8 | 8 | eight |   |  0 | 3 | -3
-     | 0 |   | zero  |   |  0 | 3 | -3
-     |   |   | null  |   |  0 | 3 | -3
-     |   | 0 | zero  |   |  0 | 3 | -3
-     | 1 | 4 | one   |   |  0 | 2 |  4
-     | 2 | 3 | two   |   |  0 | 2 |  4
-     | 3 | 2 | three |   |  0 | 2 |  4
-     | 4 | 1 | four  |   |  0 | 2 |  4
-     | 5 | 0 | five  |   |  0 | 2 |  4
-     | 6 | 6 | six   |   |  0 | 2 |  4
-     | 7 | 7 | seven |   |  0 | 2 |  4
-     | 8 | 8 | eight |   |  0 | 2 |  4
-     | 0 |   | zero  |   |  0 | 2 |  4
-     |   |   | null  |   |  0 | 2 |  4
-     |   | 0 | zero  |   |  0 | 2 |  4
-     | 1 | 4 | one   |   |  0 | 5 | -5
-     | 2 | 3 | two   |   |  0 | 5 | -5
-     | 3 | 2 | three |   |  0 | 5 | -5
-     | 4 | 1 | four  |   |  0 | 5 | -5
-     | 5 | 0 | five  |   |  0 | 5 | -5
-     | 6 | 6 | six   |   |  0 | 5 | -5
-     | 7 | 7 | seven |   |  0 | 5 | -5
-     | 8 | 8 | eight |   |  0 | 5 | -5
-     | 0 |   | zero  |   |  0 | 5 | -5
-     |   |   | null  |   |  0 | 5 | -5
-     |   | 0 | zero  |   |  0 | 5 | -5
-     | 1 | 4 | one   |   |  0 | 5 | -5
-     | 2 | 3 | two   |   |  0 | 5 | -5
-     | 3 | 2 | three |   |  0 | 5 | -5
-     | 4 | 1 | four  |   |  0 | 5 | -5
-     | 5 | 0 | five  |   |  0 | 5 | -5
-     | 6 | 6 | six   |   |  0 | 5 | -5
-     | 7 | 7 | seven |   |  0 | 5 | -5
-     | 8 | 8 | eight |   |  0 | 5 | -5
-     | 0 |   | zero  |   |  0 | 5 | -5
-     |   |   | null  |   |  0 | 5 | -5
-     |   | 0 | zero  |   |  0 | 5 | -5
-     | 1 | 4 | one   |   |  0 | 0 |   
-     | 2 | 3 | two   |   |  0 | 0 |   
-     | 3 | 2 | three |   |  0 | 0 |   
-     | 4 | 1 | four  |   |  0 | 0 |   
-     | 5 | 0 | five  |   |  0 | 0 |   
-     | 6 | 6 | six   |   |  0 | 0 |   
-     | 7 | 7 | seven |   |  0 | 0 |   
-     | 8 | 8 | eight |   |  0 | 0 |   
-     | 0 |   | zero  |   |  0 | 0 |   
-     |   |   | null  |   |  0 | 0 |   
-     |   | 0 | zero  |   |  0 | 0 |   
-     | 1 | 4 | one   |   |  0 |   |   
-     | 2 | 3 | two   |   |  0 |   |   
-     | 3 | 2 | three |   |  0 |   |   
-     | 4 | 1 | four  |   |  0 |   |   
-     | 5 | 0 | five  |   |  0 |   |   
-     | 6 | 6 | six   |   |  0 |   |   
-     | 7 | 7 | seven |   |  0 |   |   
-     | 8 | 8 | eight |   |  0 |   |   
-     | 0 |   | zero  |   |  0 |   |   
-     |   |   | null  |   |  0 |   |   
-     |   | 0 | zero  |   |  0 |   |   
-     | 1 | 4 | one   |   |  0 |   |  0
-     | 2 | 3 | two   |   |  0 |   |  0
-     | 3 | 2 | three |   |  0 |   |  0
-     | 4 | 1 | four  |   |  0 |   |  0
-     | 5 | 0 | five  |   |  0 |   |  0
-     | 6 | 6 | six   |   |  0 |   |  0
-     | 7 | 7 | seven |   |  0 |   |  0
-     | 8 | 8 | eight |   |  0 |   |  0
-     | 0 |   | zero  |   |  0 |   |  0
-     |   |   | null  |   |  0 |   |  0
-     |   | 0 | zero  |   |  0 |   |  0
-(891 rows)
-
---
---
--- Inner joins (equi-joins)
---
---
---
--- Inner joins (equi-joins) with USING clause
--- The USING syntax changes the shape of the resulting table
--- by including a column in the USING clause only once in the result.
---
--- Inner equi-join on specified column
-SELECT '' AS "xxx", *
-  FROM J1_TBL INNER JOIN J2_TBL USING (i);
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-(7 rows)
-
--- Same as above, slightly different syntax
-SELECT '' AS "xxx", *
-  FROM J1_TBL JOIN J2_TBL USING (i);
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-(7 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b, c) JOIN J2_TBL t2 (a, d) USING (a)
-  ORDER BY a, d;
- xxx | a | b |   c   | d  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
-     | 2 | 3 | two   |  4
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-(7 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b, c) JOIN J2_TBL t2 (a, b) USING (b)
-  ORDER BY b, t1.a;
- xxx | b | a |   c   | a 
------+---+---+-------+---
-     | 0 | 5 | five  |  
-     | 0 |   | zero  |  
-     | 2 | 3 | three | 2
-     | 4 | 1 | one   | 2
-(4 rows)
-
---
--- NATURAL JOIN
--- Inner equi-join on all columns with the same name
---
-SELECT '' AS "xxx", *
-  FROM J1_TBL NATURAL JOIN J2_TBL;
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-(7 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b, c) NATURAL JOIN J2_TBL t2 (a, d);
- xxx | a | b |   c   | d  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-(7 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b, c) NATURAL JOIN J2_TBL t2 (d, a);
- xxx | a | b |  c   | d 
------+---+---+------+---
-     | 0 |   | zero |  
-     | 2 | 3 | two  | 2
-     | 4 | 1 | four | 2
-(3 rows)
-
--- mismatch number of columns
--- currently, Postgres will fill in with underlying names
-SELECT '' AS "xxx", *
-  FROM J1_TBL t1 (a, b) NATURAL JOIN J2_TBL t2 (a);
- xxx | a | b |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-(7 rows)
-
---
--- Inner joins (equi-joins)
---
-SELECT '' AS "xxx", *
-  FROM J1_TBL JOIN J2_TBL ON (J1_TBL.i = J2_TBL.i);
- xxx | i | j |   t   | i | k  
------+---+---+-------+---+----
-     | 0 |   | zero  | 0 |   
-     | 1 | 4 | one   | 1 | -1
-     | 2 | 3 | two   | 2 |  4
-     | 2 | 3 | two   | 2 |  2
-     | 3 | 2 | three | 3 | -3
-     | 5 | 0 | five  | 5 | -5
-     | 5 | 0 | five  | 5 | -5
-(7 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL JOIN J2_TBL ON (J1_TBL.i = J2_TBL.k);
- xxx | i | j |  t   | i | k 
------+---+---+------+---+---
-     | 0 |   | zero |   | 0
-     | 2 | 3 | two  | 2 | 2
-     | 4 | 1 | four | 2 | 4
-(3 rows)
-
---
--- Non-equi-joins
---
-SELECT '' AS "xxx", *
-  FROM J1_TBL JOIN J2_TBL ON (J1_TBL.i <= J2_TBL.k);
- xxx | i | j |   t   | i | k 
------+---+---+-------+---+---
-     | 1 | 4 | one   | 2 | 2
-     | 1 | 4 | one   | 2 | 4
-     | 2 | 3 | two   | 2 | 2
-     | 2 | 3 | two   | 2 | 4
-     | 3 | 2 | three | 2 | 4
-     | 4 | 1 | four  | 2 | 4
-     | 0 |   | zero  | 2 | 2
-     | 0 |   | zero  | 2 | 4
-     | 0 |   | zero  |   | 0
-(9 rows)
-
---
--- Outer joins
--- Note that OUTER is a noise word
---
-SELECT '' AS "xxx", *
-  FROM J1_TBL LEFT OUTER JOIN J2_TBL USING (i)
-  ORDER BY i;
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 4 | 1 | four  |   
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-     | 6 | 6 | six   |   
-     | 7 | 7 | seven |   
-     | 8 | 8 | eight |   
-     |   | 0 | zero  |   
-     |   |   | null  |   
-(13 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL LEFT JOIN J2_TBL USING (i)
-  ORDER BY i;
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 4 | 1 | four  |   
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-     | 6 | 6 | six   |   
-     | 7 | 7 | seven |   
-     | 8 | 8 | eight |   
-     |   | 0 | zero  |   
-     |   |   | null  |   
-(13 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL RIGHT OUTER JOIN J2_TBL USING (i);
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-     |   |   |       |  0
-     |   |   |       |   
-(9 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL RIGHT JOIN J2_TBL USING (i);
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  4
-     | 2 | 3 | two   |  2
-     | 3 | 2 | three | -3
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-     |   |   |       |  0
-     |   |   |       |   
-(9 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL FULL OUTER JOIN J2_TBL USING (i)
-  ORDER BY i, t;
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
-     | 2 | 3 | two   |  4
-     | 3 | 2 | three | -3
-     | 4 | 1 | four  |   
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-     | 6 | 6 | six   |   
-     | 7 | 7 | seven |   
-     | 8 | 8 | eight |   
-     |   |   | null  |   
-     |   | 0 | zero  |   
-     |   |   |       |   
-     |   |   |       |  0
-(15 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL FULL JOIN J2_TBL USING (i)
-  ORDER BY i, t;
- xxx | i | j |   t   | k  
------+---+---+-------+----
-     | 0 |   | zero  |   
-     | 1 | 4 | one   | -1
-     | 2 | 3 | two   |  2
-     | 2 | 3 | two   |  4
-     | 3 | 2 | three | -3
-     | 4 | 1 | four  |   
-     | 5 | 0 | five  | -5
-     | 5 | 0 | five  | -5
-     | 6 | 6 | six   |   
-     | 7 | 7 | seven |   
-     | 8 | 8 | eight |   
-     |   |   | null  |   
-     |   | 0 | zero  |   
-     |   |   |       |   
-     |   |   |       |  0
-(15 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL LEFT JOIN J2_TBL USING (i) WHERE (k = 1);
- xxx | i | j | t | k 
------+---+---+---+---
-(0 rows)
-
-SELECT '' AS "xxx", *
-  FROM J1_TBL LEFT JOIN J2_TBL USING (i) WHERE (i = 1);
- xxx | i | j |  t  | k  
------+---+---+-----+----
-     | 1 | 4 | one | -1
-(1 row)
-
---
--- More complicated constructs
---
--- UNION JOIN isn't implemented yet
-SELECT '' AS "xxx", *
-  FROM J1_TBL UNION JOIN J2_TBL;
-ERROR:  UNION JOIN is not implemented
---
--- Multiway full join
---
-CREATE TABLE t1 (name TEXT, n INTEGER);
-CREATE TABLE t2 (name TEXT, n INTEGER);
-CREATE TABLE t3 (name TEXT, n INTEGER);
-INSERT INTO t1 VALUES ( 'aa', 11 );
-INSERT INTO t2 VALUES ( 'aa', 12 );
-INSERT INTO t2 VALUES ( 'bb', 22 );
-INSERT INTO t2 VALUES ( 'dd', 42 );
-INSERT INTO t3 VALUES ( 'aa', 13 );
-INSERT INTO t3 VALUES ( 'bb', 23 );
-INSERT INTO t3 VALUES ( 'cc', 33 );
-SELECT * FROM t1 FULL JOIN t2 USING (name) FULL JOIN t3 USING (name);
- name | n  | n  | n  
-------+----+----+----
- aa   | 11 | 12 | 13
- bb   |    | 22 | 23
- cc   |    |    | 33
- dd   |    | 42 |   
-(4 rows)
-
---
--- Test interactions of join syntax and subqueries
---
--- Basic cases (we expect planner to pull up the subquery here)
-SELECT * FROM
-(SELECT * FROM t2) as s2
-INNER JOIN
-(SELECT * FROM t3) s3
-USING (name);
- name | n  | n  
-------+----+----
- aa   | 12 | 13
- bb   | 22 | 23
-(2 rows)
-
-SELECT * FROM
-(SELECT * FROM t2) as s2
-LEFT JOIN
-(SELECT * FROM t3) s3
-USING (name);
- name | n  | n  
-------+----+----
- aa   | 12 | 13
- bb   | 22 | 23
- dd   | 42 |   
-(3 rows)
-
-SELECT * FROM
-(SELECT * FROM t2) as s2
-FULL JOIN
-(SELECT * FROM t3) s3
-USING (name);
- name | n  | n  
-------+----+----
- aa   | 12 | 13
- bb   | 22 | 23
- cc   |    | 33
- dd   | 42 |   
-(4 rows)
-
--- Cases with non-nullable expressions in subquery results;
--- make sure these go to null as expected
-SELECT * FROM
-(SELECT name, n as s2_n, 2 as s2_2 FROM t2) as s2
-NATURAL INNER JOIN
-(SELECT name, n as s3_n, 3 as s3_2 FROM t3) s3;
- name | s2_n | s2_2 | s3_n | s3_2 
-------+------+------+------+------
- aa   |   12 |    2 |   13 |    3
- bb   |   22 |    2 |   23 |    3
-(2 rows)
-
-SELECT * FROM
-(SELECT name, n as s2_n, 2 as s2_2 FROM t2) as s2
-NATURAL LEFT JOIN
-(SELECT name, n as s3_n, 3 as s3_2 FROM t3) s3;
- name | s2_n | s2_2 | s3_n | s3_2 
-------+------+------+------+------
- aa   |   12 |    2 |   13 |    3
- bb   |   22 |    2 |   23 |    3
- dd   |   42 |    2 |      |     
-(3 rows)
-
-SELECT * FROM
-(SELECT name, n as s2_n, 2 as s2_2 FROM t2) as s2
-NATURAL FULL JOIN
-(SELECT name, n as s3_n, 3 as s3_2 FROM t3) s3;
- name | s2_n | s2_2 | s3_n | s3_2 
-------+------+------+------+------
- aa   |   12 |    2 |   13 |    3
- bb   |   22 |    2 |   23 |    3
- cc   |      |      |   33 |    3
- dd   |   42 |    2 |      |     
-(4 rows)
-
-SELECT * FROM
-(SELECT name, n as s1_n, 1 as s1_1 FROM t1) as s1
-NATURAL INNER JOIN
-(SELECT name, n as s2_n, 2 as s2_2 FROM t2) as s2
-NATURAL INNER JOIN
-(SELECT name, n as s3_n, 3 as s3_2 FROM t3) s3;
- name | s1_n | s1_1 | s2_n | s2_2 | s3_n | s3_2 
-------+------+------+------+------+------+------
- aa   |   11 |    1 |   12 |    2 |   13 |    3
-(1 row)
-
-SELECT * FROM
-(SELECT name, n as s1_n, 1 as s1_1 FROM t1) as s1
-NATURAL FULL JOIN
-(SELECT name, n as s2_n, 2 as s2_2 FROM t2) as s2
-NATURAL FULL JOIN
-(SELECT name, n as s3_n, 3 as s3_2 FROM t3) s3;
- name | s1_n | s1_1 | s2_n | s2_2 | s3_n | s3_2 
-------+------+------+------+------+------+------
- aa   |   11 |    1 |   12 |    2 |   13 |    3
- bb   |      |      |   22 |    2 |   23 |    3
- cc   |      |      |      |      |   33 |    3
- dd   |      |      |   42 |    2 |      |     
-(4 rows)
-
-SELECT * FROM
-(SELECT name, n as s1_n FROM t1) as s1
-NATURAL FULL JOIN
-  (SELECT * FROM
-    (SELECT name, n as s2_n FROM t2) as s2
-    NATURAL FULL JOIN
-    (SELECT name, n as s3_n FROM t3) as s3
-  ) ss2;
- name | s1_n | s2_n | s3_n 
-------+------+------+------
- aa   |   11 |   12 |   13
- bb   |      |   22 |   23
- cc   |      |      |   33
- dd   |      |   42 |     
-(4 rows)
-
-SELECT * FROM
-(SELECT name, n as s1_n FROM t1) as s1
-NATURAL FULL JOIN
-  (SELECT * FROM
-    (SELECT name, n as s2_n, 2 as s2_2 FROM t2) as s2
-    NATURAL FULL JOIN
-    (SELECT name, n as s3_n FROM t3) as s3
-  ) ss2;
- name | s1_n | s2_n | s2_2 | s3_n 
-------+------+------+------+------
- aa   |   11 |   12 |    2 |   13
- bb   |      |   22 |    2 |   23
- cc   |      |      |      |   33
- dd   |      |   42 |    2 |     
-(4 rows)
-
--- Test for propagation of nullability constraints into sub-joins
-create temp table x (x1 int, x2 int);
-insert into x values (1,11);
-insert into x values (2,22);
-insert into x values (3,null);
-insert into x values (4,44);
-insert into x values (5,null);
-create temp table y (y1 int, y2 int);
-insert into y values (1,111);
-insert into y values (2,222);
-insert into y values (3,333);
-insert into y values (4,null);
-select * from x;
- x1 | x2 
-----+----
-  1 | 11
-  2 | 22
-  3 |   
-  4 | 44
-  5 |   
-(5 rows)
-
-select * from y;
- y1 | y2  
-----+-----
-  1 | 111
-  2 | 222
-  3 | 333
-  4 |    
-(4 rows)
-
-select * from x left join y on (x1 = y1 and x2 is not null);
- x1 | x2 | y1 | y2  
-----+----+----+-----
-  1 | 11 |  1 | 111
-  2 | 22 |  2 | 222
-  3 |    |    |    
-  4 | 44 |  4 |    
-  5 |    |    |    
-(5 rows)
-
-select * from x left join y on (x1 = y1 and y2 is not null);
- x1 | x2 | y1 | y2  
-----+----+----+-----
-  1 | 11 |  1 | 111
-  2 | 22 |  2 | 222
-  3 |    |  3 | 333
-  4 | 44 |    |    
-  5 |    |    |    
-(5 rows)
-
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  3 |    |  3 | 333 |   3 |    
-  4 | 44 |  4 |     |   4 |  44
-  5 |    |    |     |   5 |    
-(5 rows)
-
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1 and x2 is not null);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  3 |    |  3 | 333 |     |    
-  4 | 44 |  4 |     |   4 |  44
-  5 |    |    |     |     |    
-(5 rows)
-
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1 and y2 is not null);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  3 |    |  3 | 333 |   3 |    
-  4 | 44 |  4 |     |     |    
-  5 |    |    |     |     |    
-(5 rows)
-
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1 and xx2 is not null);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  3 |    |  3 | 333 |     |    
-  4 | 44 |  4 |     |   4 |  44
-  5 |    |    |     |     |    
-(5 rows)
-
--- these should NOT give the same answers as above
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1) where (x2 is not null);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  4 | 44 |  4 |     |   4 |  44
-(3 rows)
-
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1) where (y2 is not null);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  3 |    |  3 | 333 |   3 |    
-(3 rows)
-
-select * from (x left join y on (x1 = y1)) left join x xx(xx1,xx2)
-on (x1 = xx1) where (xx2 is not null);
- x1 | x2 | y1 | y2  | xx1 | xx2 
-----+----+----+-----+-----+-----
-  1 | 11 |  1 | 111 |   1 |  11
-  2 | 22 |  2 | 222 |   2 |  22
-  4 | 44 |  4 |     |   4 |  44
-(3 rows)
-
---
--- regression test: check for bug with propagation of implied equality
--- to outside an IN
---
-select count(*) from tenk1 a where unique1 in
-  (select unique1 from tenk1 b join tenk1 c using (unique1)
-   where b.unique2 = 42);
- count 
--------
-     1
-(1 row)
-
---
--- Clean up
---
-DROP TABLE t1;
-DROP TABLE t2;
-DROP TABLE t3;
-DROP TABLE J1_TBL;
-DROP TABLE J2_TBL;
index 55687467a0d25751442b1251cfb3263ebbabdb8c..23ee8b839e7157fed2c83c21e562a64e3fc5ded5 100644 (file)
@@ -349,184 +349,184 @@ insert into t values(3,array[3],'b');
 select f3, myaggp01a(*) from t group by f3;
  f3 | myaggp01a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp03a(*) from t group by f3;
  f3 | myaggp03a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp03b(*) from t group by f3;
  f3 | myaggp03b 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp05a(f1) from t group by f3;
  f3 | myaggp05a 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggp06a(f1) from t group by f3;
  f3 | myaggp06a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp08a(f1) from t group by f3;
  f3 | myaggp08a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp09a(f1) from t group by f3;
  f3 | myaggp09a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp09b(f1) from t group by f3;
  f3 | myaggp09b 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggp10a(f1) from t group by f3;
  f3 | myaggp10a 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggp10b(f1) from t group by f3;
  f3 | myaggp10b 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggp20a(f1) from t group by f3;
  f3 | myaggp20a 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggp20b(f1) from t group by f3;
  f3 | myaggp20b 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggn01a(*) from t group by f3;
  f3 | myaggn01a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn01b(*) from t group by f3;
  f3 | myaggn01b 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn03a(*) from t group by f3;
  f3 | myaggn03a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn05a(f1) from t group by f3;
  f3 | myaggn05a 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggn05b(f1) from t group by f3;
  f3 | myaggn05b 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)
 
 select f3, myaggn06a(f1) from t group by f3;
  f3 | myaggn06a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn06b(f1) from t group by f3;
  f3 | myaggn06b 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn08a(f1) from t group by f3;
  f3 | myaggn08a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn08b(f1) from t group by f3;
  f3 | myaggn08b 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn09a(f1) from t group by f3;
  f3 | myaggn09a 
 ----+-----------
- b  | {}
  c  | {}
  a  | {}
+ b  | {}
 (3 rows)
 
 select f3, myaggn10a(f1) from t group by f3;
  f3 | myaggn10a 
 ----+-----------
- b  | {1,2,3}
  c  | {1,2}
  a  | {1,2,3}
+ b  | {1,2,3}
 (3 rows)