Thanks, Lukas, I did manage to get a working solution.

You're of course welcome to stop here, but I'll include my work for your
consideration.  First off, context is so much more of an issue in more
complex examples: I cannot concisely explain the point of this code
beyond saying that the CTE part is looking for "straggler markers".
That I'm using the postgres ANY may disqualify this example (but the
related FIELD work needed should definitely be publicized).

All the best,
rjs

TL/DR

We have a SEGMENT in hand.
   version4019=# \d v20.segment (hundreds of millions)
                        Table "v20.segment"
         Column      |  Type   | Collation | Nullable | Default
   ------------------+---------+-----------+----------+---------
    id               | uuid    |           | not null |
    chrom            | integer |           | not null |
    markerset_id     | uuid    |           | not null |
    probandset_id    | uuid    |           | not null |
    startbase        | integer |           | not null |
    endbase          | integer |           | not null |
    firstmarker      | integer |           | not null |
    lastmarker       | integer |           | not null |
    events_less      | bigint  |           | not null | 0
    events_equal     | bigint  |           | not null | 0
    events_greater   | bigint  |           | not null | 0
    threshold_events | integer |           |          |

We need the list of markers BETWEEN firstmarker and lastmarker.
   version4019=# \d base.markerset_member; (0.5 million)
                     Table "base.markerset_member"
       Column    |       Type       | Collation | Nullable | Default
--------------+------------------+-----------+----------+---------
    markerset_id | uuid             |           | not null |
    member_id    | uuid             |           | not null |
    ordinal      | integer          |           | not null |
    theta        | double precision |           |          |

And markers may be reused in various sets.
   version4019=# \d base.markerset_member; (0.5 million)
                     Table "base.markerset_member"
       Column    |       Type       | Collation | Nullable | Default
--------------+------------------+-----------+----------+---------
    markerset_id | uuid             |           | not null |
    member_id    | uuid             |           | not null |
    ordinal      | integer          |           | not null |
    theta        | double precision |           |          |

Markers are also clumped in small clusters or "cliques", with the array
"LOCI_ORDINALS" comprised of a list of markerset_member ordinals. (The
cliques themselves have their own ordinal.
   version4019=# \d base.ld_clique;(0.5 million)
                          Table "base.ld_clique"
       Column     |        Type        | Collation | Nullable | Default
---------------+--------------------+-----------+----------+---------
    markerset_id  | uuid               |           | not null |
    ordinal       | integer            |           | not null |
    loci_ordinals | integer[]          |           |          |
    potential     | double precision[] |           |          |

Working SQL.
   with cliqueset as(
   -- get all members and any cliques referencing markers between
   -- first/last marker
   select l.*, m.*
   from base.ld_clique l join base.markerset_member m
        on (m.ordinal =any(l.loci_ordinals) and l.markerset_id = m.markerset_id)
   where l.markerset_id = '75832ca7-2303-4792-a023-d4d8f9a07471'
         and m.ordinal between 12849 and 12994
   ), extras as
   -- but some cliques will contain markers not include in the
   -- first/last range
   (
   select distinct unnest(c.loci_ordinals) as ord
   from cliqueset c
   where 12994 < any(c.loci_ordinals) or 12849 > any(c.loci_ordinals)
   )
   select s.*, s.ordinal, m.*
   from extras x join base.markerset_member s on x.ord = s.ordinal
        join base.marker m on s.member_id = m.id
   where s.markerset_id = '75832ca7-2303-4792-a023-d4d8f9a07471'
          and not x.ord between (12849) and (12994)
   order by s.ordinal
   \p\g

Working jOOQ.  (Sorta.  I may need to shift all ordinals to be zero
based, but that's another story)
    // I have a SegmentRecord in hand but I need to pad each end a
    // little. (Don't ask)
    int expander = 3 * getExpansionStep() + 1;  //Three steps of 5, plus the boundning marker     int pterIndex = expander > sRec.getFirstmarker() ? 0 : sRec.getFirstmarker() - expander;     int qterIndex = sRec.getLastmarker() + expander; // We could lookup max ordinal but the /between/ will safely stop


    // QUESTION: Apparently it's necessary to spell out the selected columns, asterisk() didn't work? CommonTableExpression<Record8<UUID,Integer,Integer[],Double[],UUID,UUID,Integer,Double>> cliqueset =       name("qm").fields("qid", "qord", "qloci", "qpot", "msid", "mid", "mord", "mtheta")
      .as(select(LD_CLIQUE.MARKERSET_ID.as("qid"),
         LD_CLIQUE.ORDINAL.as("qord"),
         LD_CLIQUE.LOCI_ORDINALS.as("qloci"),
         LD_CLIQUE.POTENTIAL.as("qpot"),
         MARKERSET_MEMBER.MARKERSET_ID.as("msid"),
         MARKERSET_MEMBER.MEMBER_ID.as("mid"),
         MARKERSET_MEMBER.ORDINAL.as("mord"),
         MARKERSET_MEMBER.THETA.as("mtheta"))
.from(LD_CLIQUE.join(MARKERSET_MEMBER).on(MARKERSET_MEMBER.ORDINAL.equal(DSL.any(LD_CLIQUE.LOCI_ORDINALS))))
.where((LD_CLIQUE.MARKERSET_ID.eq(sRec.getMarkersetId()))
 .and(MARKERSET_MEMBER.ORDINAL.between(pterIndex).and(qterIndex))));

    //NOTE: This "Field<>" trick should be near the ANY examples
    Field<Integer> lowOrd = DSL.val(pterIndex);
    Field<Integer> highOrd = DSL.val(qterIndex);
    //This CTE is looking for the "ordinal" of markers mentioned in cliques
    //but which are out side the original the pter/qterIndex range
    CommonTableExpression<Record1<Integer>> extras =
      name("xm").fields("xord")
.as(selectDistinct(cliqueset.field("mord").cast(Integer.class).as("xord"))
.from(cliqueset.join(LD_CLIQUE).on(cliqueset.field("qid").cast(UUID.class).eq(LD_CLIQUE.MARKERSET_ID)
.and(cliqueset.field("qord").cast(Integer.class).eq(LD_CLIQUE.ORDINAL))))
          .where(lowOrd.gt(DSL.any(LD_CLIQUE.LOCI_ORDINALS)))
          .or(highOrd.lt(DSL.any(LD_CLIQUE.LOCI_ORDINALS))));

    Result<?>markerdata = context
      .with(cliqueset)
      .with(extras)
      .select(MARKERSET_MEMBER.asterisk(), MARKER.asterisk())
.from(extras).join(MARKERSET_MEMBER).on(extras.field("xord") == (MARKERSET_MEMBER.ORDINAL))
      .join(MARKER).on(MARKERSET_MEMBER.MEMBER_ID.eq(MARKER.ID))
.where(MARKERSET_MEMBER.MARKERSET_ID.eq(sRec.getMarkersetId())
.and(extras.field("xord").cast(Integer.class).between(pterIndex).and(qterIndex)))
      // NOTE: I do a union because when I had the below as a separate select I
      // had trouble putting the two Result<?> sets together.
      .union(select(MARKERSET_MEMBER.asterisk(), MARKER.asterisk())
        .from(MARKERSET_MEMBER
.join(MARKER).on(MARKERSET_MEMBER.MEMBER_ID.equal(MARKER.ID)))
.where(MARKERSET_MEMBER.MARKERSET_ID.equal(sRec.getMarkersetId())
.and(MARKERSET_MEMBER.ORDINAL.between(pterIndex).and(qterIndex)))
        .orderBy(MARKERSET_MEMBER.ORDINAL))
      .fetch();

On 3/5/21 1:04 AM, Lukas Eder wrote:
We don't have any, though we probably should (especially for CTE, there's a pending issue for that). What are you looking for, specifically?

On Thu, Mar 4, 2021 at 10:40 PM Rob Sargent <[email protected] <mailto:[email protected]>> wrote:

    Is there a repository of more complex examples of jOOQ code?  I'm
    having
    a lot of fun with CTEs and DSL.any and I think I'm conforming to the
    website examples.

-- You received this message because you are subscribed to the Google
    Groups "jOOQ User Group" group.
    To unsubscribe from this group and stop receiving emails from it,
    send an email to [email protected]
    <mailto:jooq-user%[email protected]>.
    To view this discussion on the web visit
    
https://groups.google.com/d/msgid/jooq-user/0c174979-b542-eca3-44cb-adc47ade1310%40gmail.com
    
<https://groups.google.com/d/msgid/jooq-user/0c174979-b542-eca3-44cb-adc47ade1310%40gmail.com>.

--
You received this message because you are subscribed to the Google Groups "jOOQ User Group" group. To unsubscribe from this group and stop receiving emails from it, send an email to [email protected] <mailto:[email protected]>. To view this discussion on the web visit https://groups.google.com/d/msgid/jooq-user/CAB4ELO7FRKpTKcKXEGfaB533G0XmmARuSuFNkoVNgbANCP5aqg%40mail.gmail.com <https://groups.google.com/d/msgid/jooq-user/CAB4ELO7FRKpTKcKXEGfaB533G0XmmARuSuFNkoVNgbANCP5aqg%40mail.gmail.com?utm_medium=email&utm_source=footer>.

--
You received this message because you are subscribed to the Google Groups "jOOQ User 
Group" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
To view this discussion on the web visit 
https://groups.google.com/d/msgid/jooq-user/2c6cb54c-956f-3a40-d3f3-c04a2486b469%40gmail.com.

Reply via email to