<html><head>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
  </head>
  <body>
    <p>Hi.</p>
    <p>An interesting facet of eventual sending with promises is the
      bonus of sending multiple result handlers to a single eventual
      send result promise. So multiple result handlers, or whatever best
      describes, for whatever that is worth.</p>
    <p>Here are 3 return handlers, <br/>
    </p>
    <blockquote>
      <p>promise := ((pair := self promiseResolverPair) key xgcd: 9).</p>
    </blockquote>
    <p>the first for each argument <br/>
    </p>
    <blockquote>
      <p>promise <<* [:each | selectCount := selectCount + 1.
        Transcript cr; show: 'each = ', each];</p>
    </blockquote>
    <p>and the last 2 for all three arguments.</p>
    <blockquote>
      <p>promise <<* [:g :s :t | firstUnionFlag := true.
        Transcript cr; show: 'gcd = 'g'].</p>
      <p>promise <<* [:g :s :t | secondUnionFlag := true.
        Transcript cr; show: 'g = ', g, '; s = ', s, '; t = ', t.].</p>
    </blockquote>
    <pre class="moz-signature" cols="72">--
❤️‍🔥🐰



</pre>
    <p></p>
    <div class="moz-cite-prefix">On 6/23/23 16:15, Luciano
      Notarfrancesco wrote:<br/>
    </div>
    <blockquote type="cite" cite="mid:CAL5GDyoz_kWja=LN_ods3VxmbsnAAqt9OgP0_AL8bXgpgbYC6A@mail.gmail.com">
      <meta http-equiv="content-type" content="text/html; charset=UTF-8"/>
      <div dir="auto">Right, good point! Fortunately, messages with
        multiple return values are not very common in my system, I just
        have a few examples, and I’ll rewrite them with Juan’s
        suggestion, and I’ll keep your point in mind.</div>
      <div><br/>
        <div class="gmail_quote">
          <div dir="ltr" class="gmail_attr">On Fri, 23 Jun 2023 at 21:33
            Nicolas Cellier <<a href="mailto:nicolas.cellier.aka.nice@gmail.com" moz-do-not-send="true" class="moz-txt-link-freetext">nicolas.cellier.aka.nice@gmail.com</a>>
            wrote:<br/>
          </div>
          <blockquote class="gmail_quote" style="margin:0px 0px 0px
0.8ex;border-left-width:1px;border-left-style:solid;padding-left:1ex;border-left-color:rgb(204,204,204)">
            <div dir="ltr">
              <div>Hi all,</div>
              <div>please note that the keyword message did eliminate
                the positional semantics found in almost every other
                language.</div>
              <div>With multiple return arguments, as well as multiple
                arguments block workaround, we are back to a kind of
                positional semantic.</div>
              <div>Of course, there is still some name used as block
                args [:g :s :t | ...] but nothing would tell that [:t :g
                :s | ...] is a mistake.</div>
              <div>A hint on order can be given by the keyword used to
                pass block argument, like qr: [:quo :rem | ] or
                whatever, but when there is more than 2, naming is
                getting difficult.</div>
            </div>
            <div dir="ltr">
              <div>Nicolas<br/>
              </div>
              <div><br/>
              </div>
            </div>
            <br/>
            <div class="gmail_quote">
              <div dir="ltr" class="gmail_attr">Le ven. 23 juin 2023
                à 21:00, rabbit via Cuis-dev <<a href="mailto:cuis-dev@lists.cuis.st" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">cuis-dev@lists.cuis.st</a>>
                a écrit :<br/>
              </div>
              <blockquote class="gmail_quote" style="margin:0px 0px 0px
0.8ex;border-left-width:1px;border-left-style:solid;padding-left:1ex;border-left-color:rgb(204,204,204)">
                <div>
                  <p>I just realized I have been working in squeak. I
                    updated PromisesLocal-rabbt.66.mcz and am attaching
                    it. I am getting the error below when I 'browse
                    code' or 'install Mionticello package'. I do not
                    know. How can I load Monticello packages? Any way to
                    get the Installer available in cuis? Install
                    Monticello config maps?<br/>
                  </p>
                  <p>I appreciate you,<br/>
                    rabbit</p>
                  <p><img src="cid:part1.eLPsDRXO.PhCyQCyk@callistohouse.org" alt="" style="width:1180px;max-width:100%" class=""/></p>
                  <p><br/>
                  </p>
                  <div>On 6/22/23 16:21, rabbit via Cuis-dev wrote:<br/>
                  </div>
                  <blockquote type="cite">
                    <p>Hey! I got inspired by your proposal, Luciano,
                      and here's my solution in eventual promises. Code
                      can be loaded as:</p>
                    <blockquote>
                      <p>Installer ss project: 'Cryptography'; install:
                        'ProCrypto.release.3'.<br/>
                      </p>
                    </blockquote>
                    <p>I added a test method <br/>
                    </p>
                    <blockquote>
                      <p>RefsTest>>#testMultiReturns<br/>
                        <br/>
                            | selectCount unionFlag pair |<br/>
                            unionFlag := false.<br/>
                            selectCount := 0.<br/>
                            ((pair := self promiseResolverPair) key
                        xgcd: 9) <br/>
                                <<* [:each | selectCount :=
                        selectCount + 1. Transcript cr; show: 'each = ',
                        each];<br/>
                                <<* [:g :s :t | unionFlag := true.
                        Transcript cr; show: 'g = ', g, '; s = ', s, ';
                        t = ', t. g + s + t].<br/>
                            pair value resolve: 21.<br/>
                            (Delay forMilliseconds: 333) wait.<br/>
                            self assert: (selectCount == 3).<br/>
                            self assert: (unionFlag).</p>
                    </blockquote>
                    <p>This calls new multireturn #xgcd: method</p>
                    <blockquote>
                      <p>xgcd: anInteger<br/>
                            " 21 xgcd: 9"<br/>
                            | g s t |<br/>
                            g := self gcd: anInteger.<br/>
                            s := self / g.<br/>
                            t := anInteger / g.<br/>
                            ^ { g. s. t}<br/>
                      </p>
                    </blockquote>
                    <p>And in the test method there are eventual sends
                      (#<<*) to the promise of the #xgcd: send
                      once the reciever promise is resolved to 21. This
                      implementation detects cardinality of the
                      continuation block and sends #whenResolved:
                      appropriately, for future evaluation.</p>
                    <blockquote>
                      <p>Object>>#<<* continuation<br/>
                        <br/>
                            (continuation numArgs == 1)<br/>
                                ifTrue: [^ self whenResolved: [:result |
                        result do: [:each | continuation value: each]]].<br/>
                            ^ self whenResolved: [:result | continuation
                        valueWithArguments: result].</p>
                    </blockquote>
                    <p>One can see a 1 cardinality schedules the
                      continuation to evaluate with each result, while a
                      continuation with cardinality 2 or more will be
                      scheduled to receive all results.
                      #valueWithArguments:</p>
                    <p>Here are 2 return handlers, <br/>
                    </p>
                    <blockquote>
                      <p>promise := ((pair := self promiseResolverPair)
                        key xgcd: 9).</p>
                    </blockquote>
                    <p>the first for each argument <br/>
                    </p>
                    <blockquote>
                      <p>promise <<* [:each | selectCount :=
                        selectCount + 1. Transcript cr; show: 'each = ',
                        each];</p>
                    </blockquote>
                    <p>and the second for all three arguments.</p>
                    <blockquote>
                      <p>promise <<* [:g :s :t | unionFlag :=
                        true. Transcript cr; show: 'g = ', g, '; s = ',
                        s, '; t = ', t. g + s + t].</p>
                    </blockquote>
                    <pre cols="72" style="font-family:monospace">--
❤️‍🔥🐰



</pre>
                    <div>On 6/21/23 09:44, Luciano Notarfrancesco via
                      Cuis-dev wrote:<br/>
                    </div>
                    <blockquote type="cite">
                      <div dir="auto">Interesting, thanks for sharing!</div>
                      <div dir="auto">Actually I think it’s the same
                        thing I did, my implementation calls
                        BlockClosure>>#valueWithPossibleArgs: and
                        takes only as many arguments as needed by the
                        block but the array can be bigger than that (it
                        should be named #valueWithPossibleArguments:
                        tho, abbreviations are ugly).</div>
                      <div dir="auto"><br/>
                      </div>
                      <div><br/>
                        <div class="gmail_quote">
                          <div dir="ltr" class="gmail_attr">On Wed, 21
                            Jun 2023 at 15:37 Christian Haider via
                            Cuis-dev <<a href="mailto:cuis-dev@lists.cuis.st" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">cuis-dev@lists.cuis.st</a>>
                            wrote:<br/>
                          </div>
                          <blockquote class="gmail_quote" style="margin:0px 0px 0px
0.8ex;border-left-width:1px;border-left-style:solid;padding-left:1ex;border-left-color:rgb(204,204,204)">
                            <div lang="DE">
                              <div>
                                <p class="MsoNormal"><span lang="EN-CA">I
                                    added something similar to my Values
                                    package (VW and ports).</span></p>
                                <p class="MsoNormal"><span lang="EN-CA">The
                                    source is</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">SequenceableCollection>>asArgumentsIn:
                                    aBlock</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">    
                                    "Evaluate aBlock with the receiver's
                                    elements as parameters.</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     aBlock
                                    takes its arguments from the
                                    receiver.</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     'ok'</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     #(1 2
                                    3) asArgumentsIn: [:a :b :c | a + b
                                    + c]</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     #(1 2
                                    3) asArgumentsIn: [:a :b | a + b]</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     #(1 2
                                    3) asArgumentsIn: [:a | a]</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     #(1 2
                                    3) asArgumentsIn: [42]</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     'not
                                    ok'</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     #(1 2
                                    3) asArgumentsIn: [:a :b :c :d | a +
                                    b + c + d]</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     "</span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA"> </span></p>
                                <p class="MsoNormal" style="margin-left:35.4pt"><span style="font-family:"Courier
                                    New"" lang="EN-CA">     ^aBlock
                                    cullWithArguments: self asArray</span><span lang="EN-CA"></span></p>
                                <p class="MsoNormal"><span lang="EN-CA"> </span></p>
                                <p class="MsoNormal"><span lang="EN-CA">The
                                    difference is that it takes a list
                                    of any size and picks out the first
                                    items and binds them to the
                                    variables.</span></p>
                                <p class="MsoNormal"><span lang="EN-CA">I
                                    use it often for CSV processing like</span></p>
                                <p class="MsoNormal"><span lang="EN-CA">               
                                  </span><span lang="EN-CA">(line
                                    tokensBasedOn: $;) asArgumentsIn:
                                    [:first :second :y | … ].</span></p>
                                <p class="MsoNormal"><span lang="EN-CA"> </span></p>
                                <p class="MsoNormal"><span lang="EN-CA">I
                                    am just a bit unhappy with the name
                                    – it is too long. It reads ok
                                    though.</span></p>
                                <p class="MsoNormal"><span lang="EN-CA">The
                                    pipe character is an interesting
                                    idea. I have to think about it.</span></p>
                                <p class="MsoNormal"><span lang="EN-CA"> </span></p>
                                <p class="MsoNormal"><span lang="EN-CA">I
                                    am use it for a while now and I am
                                    very happy with it.</span></p>
                                <p class="MsoNormal"><span lang="EN-CA"> </span></p>
                                <p class="MsoNormal"><span lang="EN-CA">Happy
                                    hacking,</span></p>
                                <p class="MsoNormal"><span>Christian</span></p>
                              </div>
                            </div>
                            <div lang="DE">
                              <div>
                                <p class="MsoNormal"><span> </span></p>
                                <p class="MsoNormal"><span> </span></p>
                                <div style="border-width:1pt medium
                                  medium;border-style:solid none
                                  none;padding:3pt 0cm
                                  0cm;border-color:rgb(225,225,225)
                                  currentcolor currentcolor">
                                  <p class="MsoNormal"><b>Von:</b>
                                    Cuis-dev <<a href="mailto:cuis-dev-bounces@lists.cuis.st" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">cuis-dev-bounces@lists.cuis.st</a>>
                                    <b>Im Auftrag von </b>Luciano
                                    Notarfrancesco via Cuis-dev<br/>
                                    <b>Gesendet:</b> Mittwoch, 21. Juni
                                    2023 15:13<br/>
                                    <b>An:</b> Discussion of Cuis
                                    Smalltalk <<a href="mailto:cuis-dev@lists.cuis.st" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">cuis-dev@lists.cuis.st</a>><br/>
                                    <b>Cc:</b> Luciano Notarfrancesco
                                    <<a href="mailto:luchiano@gmail.com" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">luchiano@gmail.com</a>><br/>
                                    <b>Betreff:</b> [Cuis-dev] Methods
                                    that return multiple values</p>
                                </div>
                                <p class="MsoNormal"> </p>
                                <p class="MsoNormal">Smalltalk doesn’t
                                  have a convention for methods
                                  returning multiple values, and I’m not
                                  aware of any implementation.</p>
                                <div>
                                  <p class="MsoNormal">An example of
                                    such thing is the extended gcd: ‘a
                                    xgcd: b’ returns g, s, t where g is
                                    the gcd, and as + bt = g. Writing
                                    methods that return multiple values
                                    is easy with the curly brackets
                                    syntax, Integer>>#xgcd: ends
                                    with something like</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">    ^ {g. s. t}</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">But using sending
                                    messages that return multiple values
                                    is kind of annoying, I end up doing
                                    something like:</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">    xgcd := a
                                    xgcd: b.</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">    g := xgcd at:
                                    1.</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">    s := xgcd at:
                                    2.</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">    t := xgcd at:
                                    3</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">Some years ago I
                                    thought about using blocks for this,
                                    but I never tried it. Today I just
                                    did a little experiment implementing
                                    anArray | aBlock as ‘^ aBlock
                                    valueWithPossibleArgs: self’ and I
                                    can do:</p>
                                </div>
                                <div>
                                  <p class="MsoNormal">    (a xgcd: b) |
                                    [:g :s :t| … ]</p>
                                </div>
                                <div>
                                  <p class="MsoNormal"> </p>
                                </div>
                                <div>
                                  <p class="MsoNormal">This is seems
                                    quite nice already, I guess I’ll
                                    start using it and see how it feels.
                                    But the point of this mail is not to
                                    show a solution, but to ask if
                                    anyone have thought about this or if
                                    they know any nicer solutions. Any
                                    ideas?</p>
                                </div>
                              </div>
                            </div>
                            -- <br/>
                            Cuis-dev mailing list<br/>
                            <a href="mailto:Cuis-dev@lists.cuis.st" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">Cuis-dev@lists.cuis.st</a><br/>
                            <a href="https://lists.cuis.st/mailman/listinfo/cuis-dev" rel="noreferrer" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">https://lists.cuis.st/mailman/listinfo/cuis-dev</a><br/>
                          </blockquote>
                        </div>
                      </div>
                    </blockquote>
                  </blockquote>
                  <pre cols="72" style="font-family:monospace">--
❤️‍🔥🐰</pre>
                </div>
                -- <br/>
                Cuis-dev mailing list<br/>
                <a href="mailto:Cuis-dev@lists.cuis.st" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">Cuis-dev@lists.cuis.st</a><br/>
                <a href="https://lists.cuis.st/mailman/listinfo/cuis-dev" rel="noreferrer" target="_blank" moz-do-not-send="true" class="moz-txt-link-freetext">https://lists.cuis.st/mailman/listinfo/cuis-dev</a><br/>
              </blockquote>
            </div>
          </blockquote>
        </div>
      </div>
    </blockquote>
    <pre class="moz-signature" cols="72">-- 
❤️‍🔥🐰</pre>
  
</body></html>