<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
</head>
<body text="#000000" bgcolor="#FFFFFF">
<div class="moz-cite-prefix">Thanks for all the explanations. <br>
<br>
and yes, I have to get a feel when I need a new class and when
not. <br>
and when it's "allowed" to use a if then and when not. <br>
<br>
and if I understand the explanations I did not ask a class
something so a if then is <br>
allowed. <br>
<br>
Roelof<br>
<br>
<br>
<br>
Op 28-11-2018 om 09:01 schreef Richard O'Keefe:<br>
</div>
<blockquote type="cite"
cite="mid:CABcYAd+5dYkzfNiEYMJ_QqXMsWYVk9DNjD9pxd3R-***@mail.gmail.com">
<meta http-equiv="content-type" content="text/html; charset=UTF-8">
<div dir="ltr">
<div class="gmail_default"
style="font-family:monospace,monospace">DRAT! What (genius
negated) designed gmail's interface?</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">If I am wrong that the
canHandleInput: class method of</div>
<div class="gmail_default"
style="font-family:monospace,monospace">IllegalMoveSanta
should return false, not true (because</div>
<div class="gmail_default"
style="font-family:monospace,monospace">the order of the
elements of #subclasses is not defined,</div>
<div class="gmail_default"
style="font-family:monospace,monospace">so that
IllegalMoveSanta might *always* be selected),</div>
<div class="gmail_default"
style="font-family:monospace,monospace">then that is further
evidence that avoiding "if" made</div>
<div class="gmail_default"
style="font-family:monospace,monospace">the code LESS
readable.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">You are a beginner at
this, doing all the right things</div>
<div class="gmail_default"
style="font-family:monospace,monospace">for a beginner to do.
One of the things you have to do</div>
<div class="gmail_default"
style="font-family:monospace,monospace">is to develop a sense
of "smell" for code. Each class</div>
<div class="gmail_default"
style="font-family:monospace,monospace">ought to "pull its
weight". Four classes -- which it</div>
<div class="gmail_default"
style="font-family:monospace,monospace">really does not make
sense to instantiate, just put the</div>
<div class="gmail_default"
style="font-family:monospace,monospace">instance methods on
the class side and drop the #new --</div>
<div class="gmail_default"
style="font-family:monospace,monospace">just to avoid a couple
of very clear "ifs"? I don't</div>
<div class="gmail_default"
style="font-family:monospace,monospace">think so. IF THESE
CLASSES NEEDED TO EXIST FOR SOME</div>
<div class="gmail_default"
style="font-family:monospace,monospace">OTHER REASON, if they
had real work to do, sure. But</div>
<div class="gmail_default"
style="font-family:monospace,monospace">they don't. They only
bloat and obscure the code.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
</div>
<br>
<div class="gmail_quote">
<div dir="ltr">On Wed, 28 Nov 2018 at 20:54, Richard O'Keefe
<<a href="mailto:***@gmail.com" moz-do-not-send="true">***@gmail.com</a>>
wrote:<br>
</div>
<blockquote class="gmail_quote" style="margin:0 0 0
.8ex;border-left:1px #ccc solid;padding-left:1ex">
<div dir="ltr">
<div dir="ltr">
<div dir="ltr">
<div dir="ltr">
<div dir="ltr">
<div class="gmail_default"
style="font-family:monospace,monospace">In
Advent-of-Code 2015, the first problem is</div>
<div class="gmail_default"
style="font-family:monospace,monospace">really
quite simple. There are at least two</div>
<div class="gmail_default"
style="font-family:monospace,monospace">ways to
think about it.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">"CS101":</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> set a
counter to 0</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> for
each character of the string</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> if it
is '(' increment the counter</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> if it
is ')' decrement the counter</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> report
the counter</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">"Higher
level":</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> report
the difference between</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> (the
number of '(' characters in the string) and</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> (the
number of ')' characters in the string).</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Expressed
in Smalltalk this looks something like</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
Transcript print:</div>
<div class="gmail_default">
<div class="gmail_default"
style="font-family:monospace,monospace"> (s
occurrencesOf: $() - (s occurrencesOf: $)); cr.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Make no
mistake: you *cannot* tell the difference</div>
<div class="gmail_default"
style="font-family:monospace,monospace">between
$( and $) using class-based dispatch because</div>
<div class="gmail_default"
style="font-family:monospace,monospace">they
belong to the same class. There has to be an</div>
<div class="gmail_default"
style="font-family:monospace,monospace">"if"
somewhere, the question is not whether but
where.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">In this
case, counting the number of occurrences of an</div>
<div class="gmail_default"
style="font-family:monospace,monospace">object
in a collection is has been a standard
Collection</div>
<div class="gmail_default"
style="font-family:monospace,monospace">method
for nearly 40 years; it's one of the basic</div>
<div class="gmail_default"
style="font-family:monospace,monospace">operations
you need to learn.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">The
"higher level" approach can be less efficient
that</div>
<div class="gmail_default"
style="font-family:monospace,monospace">the
"CS101" approach, but in a case like this we
really</div>
<div class="gmail_default"
style="font-family:monospace,monospace">do not
care. We want the code to be *clear*.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">What
about the second part of the problem?</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Not
having submitted any answers, I can't actually</div>
<div class="gmail_default"
style="font-family:monospace,monospace">see the
second part on the AOC site, but luckily you</div>
<div class="gmail_default"
style="font-family:monospace,monospace">have
included it in your program.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">We want
to</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> [find
the first place] where</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
[the cumulative sum] of (c=$()</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
[minus]</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
[the cumulative sum] of (c=$))</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
equals -1.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">The
"CS101" approach is</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> n :=
i := 0.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> while
n >= 0 and i < size(s) do</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
i +:= 1</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> if
s[i] = $( then n := n + 1</div>
<div class="gmail_default"
style="font-family:monospace,monospace"> if
s[i] = $) then n := n - 1</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
report n</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">The
"higher level" approach looks something like</div>
<div class="gmail_default">
<div class="gmail_default"
style="font-family:monospace,monospace"> n :=
(s cumCount: [:each | each = $(]) -</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
(s cumCount: [:each | each = $)])</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
indexOf: -1.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">--
although it gives 0 instead of s size + 1 when</div>
<div class="gmail_default"
style="font-family:monospace,monospace">-1 is
never reached.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Here
#indexOf: is standard, #- is defined on
sequences</div>
<div class="gmail_default"
style="font-family:monospace,monospace">in
Squeak and Pharo, but #cumCount: does not</div>
<div class="gmail_default"
style="font-family:monospace,monospace">exist.
So we need something like</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default">
<div class="gmail_default"><font
face="monospace, monospace"> cumCount:
aBlock </font></div>
<div class="gmail_default"><font
face="monospace, monospace"> |c a|
</font></div>
<div class="gmail_default"><font
face="monospace, monospace"> a :=
Array new: self size.</font></div>
<div class="gmail_default"><font
face="monospace, monospace"> c := 0.</font></div>
<div class="gmail_default"><font
face="monospace, monospace"> self
withIndexDo: [:each :i |</font></div>
<div class="gmail_default"><font
face="monospace, monospace">
(aBlock value: each) ifTrue: [c := c + 1].</font></div>
<div class="gmail_default"><font
face="monospace, monospace"> a at:
i put: c].</font></div>
<div class="gmail_default"><font
face="monospace, monospace"> ^a</font></div>
<div class="gmail_default"
style="font-family:monospace,monospace">This
is *not* coupled to the particular use we
have</div>
<div class="gmail_default"
style="font-family:monospace,monospace">in
mind for it; it is in no way tied to
characters</div>
<div class="gmail_default"
style="font-family:monospace,monospace">or
strings. It's quite general.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Note:
we do not need any new classes, except maybe</div>
<div class="gmail_default"
style="font-family:monospace,monospace">a
place to put one problem-specific method.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">While
this answer, with no loop and no if in the</div>
<div class="gmail_default"
style="font-family:monospace,monospace">problem-specific
code, is quite pretty, it has a</div>
<div class="gmail_default"
style="font-family:monospace,monospace">problem.
Suppose the string to have M characters</div>
<div class="gmail_default"
style="font-family:monospace,monospace">and
the desired step to be number K. The CS101</div>
<div class="gmail_default"
style="font-family:monospace,monospace">approach
takes O(K) time and no allocations, but</div>
<div class="gmail_default"
style="font-family:monospace,monospace">the
higher level approach takes O(M) time and</div>
<div class="gmail_default"
style="font-family:monospace,monospace">allocates
three M-element Arrays. (In a non-strict</div>
<div class="gmail_default"
style="font-family:monospace,monospace">functional
language like Haskell, the higher level</div>
<div class="gmail_default"
style="font-family:monospace,monospace">version
*also* takes O(K) time, and with a good</div>
<div class="gmail_default"
style="font-family:monospace,monospace">enough
"deforesting" compiler should allocate no</div>
<div class="gmail_default"
style="font-family:monospace,monospace">data
structures.)</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">For
a problem like this, I really don't care
about</div>
<div class="gmail_default"
style="font-family:monospace,monospace">the
efficiency aspect. If I *do* care about
that,</div>
<div class="gmail_default"
style="font-family:monospace,monospace">then
starting from a higher level version gives
me</div>
<div class="gmail_default"
style="font-family:monospace,monospace">something
to test a lower level version against.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">To
get an efficient answer to the second part,</div>
<div class="gmail_default"
style="font-family:monospace,monospace">we
still don't need a new semantic class, just</div>
<div class="gmail_default"
style="font-family:monospace,monospace">some
place to put the code.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Day1</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
class methods:</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
indexOfFirstBasementTime: steps</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
|floor|</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
floor := 0.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
steps keysAndValuesDo: [:i :each |</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
each = $( ifTrue: [floor := floor + 1].</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
each = $) ifTrue: [floor := floor - 1].</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
floor = -1 ifTrue: [^i]].</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
^0 "same convention as #indexOf:"</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Does
this contain "if"? Why yes, it does.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Is
there any problem with that? Why no, there
isn't.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">You
need to treat members of the same class
(left</div>
<div class="gmail_default"
style="font-family:monospace,monospace">parenthesis,
right parenthesis, others) differently.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">You
need to treat members of the same class
(minus</div>
<div class="gmail_default"
style="font-family:monospace,monospace">one,
all other integers) differently.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Would
there be any gain in clarity or
maintainability</div>
<div class="gmail_default"
style="font-family:monospace,monospace">if
these ifs were somehow eliminated?
Certainly NOT.</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">Quite
the reverse, in fact.</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
<div class="gmail_default">input2
withIndexDo: [ :element :index | |action| </div>
<div class="gmail_default"><span style="white-space:pre-wrap"> </span>action:=
SantaAction getActionFor: element. floor
:= action doMovementFor: floor .</div>
<div class="gmail_default"><span style="white-space:pre-wrap"> </span>self
hasReachedBasement </div>
<div class="gmail_default"><span style="white-space:pre-wrap"> </span>ifTrue:
[^ index]].</div>
<div class="gmail_default"> ^ '-2'.</div>
<div class="gmail_default"><br>
</div>
<div class="gmail_default">There is only one
word for this: obfuscated.</div>
<div class="gmail_default">I was initially
puzzled by your returning -2</div>
<div class="gmail_default">instead of the
conventional 0 if the basement</div>
<div class="gmail_default">is not reached,
and then *deeply confused* by</div>
<div class="gmail_default">the fact that you
are returning a *string* in</div>
<div class="gmail_default">this case.</div>
<div class="gmail_default"><br>
</div>
<div class="gmail_default">Looking at your
code, I was further confused</div>
<div class="gmail_default">by variables
called 'aSymbol' whose value is</div>
<div class="gmail_default">always and only a
Character, never a Symbol.</div>
<div class="gmail_default">And if I am wrong
that</div>
<div class="gmail_default">
<table
class="m_7790805574745581477gmail-highlight
m_7790805574745581477gmail-tab-size
m_7790805574745581477gmail-js-file-line-container"
style="box-sizing:border-box;border-collapse:collapse;border-spacing:0px;color:rgb(36,41,46);font-family:-apple-system,BlinkMacSystemFont,"Segoe
UI",Helvetica,Arial,sans-serif,"Apple Color
Emoji","Segoe UI
Emoji","Segoe UI
Symbol";font-size:14px"> <tbody style="box-sizing:border-box"> <tr style="box-sizing:border-box"> <td id="m_7790805574745581477gmail-LC7" class="m_7790805574745581477gmail-blob-code m_7790805574745581477gmail-blob-code-inner m_7790805574745581477gmail-js-file-line" style="box-sizing:border-box;padding:0px 10px;line-height:20px;vertical-align:top;font-family:SFMono-Regular,Consolas,"Liberation Mono",Menlo,Courier,monospace;font-size:12px;overflow:visible;white-space:pre-wrap;word-wrap:normal">IllegalMoveSanta class>> canHandleInput:
</td>
</tr>
</tbody>
</table>
</div>
<div class="gmail_default">in Smalltalk is
to return 0 when something is</div>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">approach</div>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div style="font-family:monospace,monospace"><br>
</div>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace"><br>
</div>
<div class="gmail_default"
style="font-family:monospace,monospace">We want
to find the first place where something</div>
<div class="gmail_default"
style="font-family:monospace,monospace">becomes
true. There are again at least to approaches. </div>
</div>
</div>
<br>
<div class="gmail_quote">
<div dir="ltr">On Wed, 28 Nov 2018 at 05:41, Roelof
Wobben <<a href="mailto:***@home.nl"
target="_blank" moz-do-not-send="true">***@home.nl</a>>
wrote:<br>
</div>
<blockquote class="gmail_quote" style="margin:0px
0px 0px 0.8ex;border-left:1px solid
rgb(204,204,204);padding-left:1ex">Hello,<br>
<br>
Yesterday I had a talk with luc frabresse about
using if then.<br>
He said if I understand it right, Its the best to
not using a if then or <br>
a ifTrue/ifFalse.<br>
<br>
Can anyone help me figure out how to rewrite this
project so I will not <br>
use the ifTrue in the basement function.<br>
<br>
my code so far can be found here : <a
href="https://github.com/RoelofWobben/AOC2015"
rel="noreferrer" target="_blank"
moz-do-not-send="true"><span
class="gmail_default"
style="font-family:monospace,monospace"></span>https://github.com/RoelofWobben/AOC2015</a><br>
<br>
Roelof<br>
<br>
<br>
</blockquote>
</div>
</div>
</div>
</div>
</div>
</blockquote>
</div>
</blockquote>
<br>
</body>
</html>