    <rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:sy="http://purl.org/rss/1.0/modules/syndication/" xmlns:admin="http://webns.net/mvcb/" xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#" xmlns:content="http://purl.org/rss/1.0/modules/content/">
     <channel>
        <title>ACCU  :: Student Code Critique Competition 28</title>
        <link>https://members.accu.org/index.php/journals/677</link>
        <description>Professionalism in Programming</description>
        <dc:language>en-us</dc:language> 
        <dc:creator>Administrator</dc:creator> 
        <admin:generatorAgent rdf:resource="http://www.xaraya.org" /> 
        <admin:errorReportsTo rdf:resource="mailto:webeditor@accu.org" />
       <sy:updatePeriod>hourly</sy:updatePeriod>
       <sy:updateFrequency>1</sy:updateFrequency>
       <docs>http://backend.userland.com/rss</docs>


        <h2>Journal Articles</h2>


<div class="xar-mod-head"><span class="xar-mod-title">CVu Journal Vol 16, #3 - Jun 2004 + Student Code Critiques from CVu journal.</span></div>

<table border="0" cellpadding="1" cellspacing="0">
    <tbody>
    <tr>
        <td valign="top">
            Browse in :
       </td>
       <td valign="top">

                                            <a href="https://members.accu.org/index.php/journals/">All</a>

                     &gt;                         <a href="https://members.accu.org/index.php/journals/c76/">Journals</a>

                     &gt;                         <a href="https://members.accu.org/index.php/journals/c77/">CVu</a>

                     &gt;                         <a href="https://members.accu.org/index.php/journals/c102/">163</a>
                    (11)
<br />

                                            <a href="https://members.accu.org/index.php/journals/">All</a>

                     &gt;                         <a href="https://members.accu.org/index.php/journals/c184/">Journal Columns</a>

                     &gt;                         <a href="https://members.accu.org/index.php/journals/c183/">Code Critique</a>
                    (70)
<br />

                                            <a href="https://members.accu.org/index.php/journals/c102-183/">Any of these categories</a>

                    -                        <a href="https://members.accu.org/index.php/journals/c102+183/">All of these categories</a>
<br />
</td>
   </tr>
   </tbody>
</table>




<div class="xar-error">
   <p>
 <strong>Note:</strong> when you create a new publication type,
the articles module will automatically use the templates
<em>user-display-[publicationtype].xt</em>
and <em>user-summary-[publicationtype].xt</em>.
If those templates do not exist when you try to preview or display a new article,
you'll get this warning :-)  Please place your own templates in themes/<em>yourtheme</em>/modules/articles . The templates will get the extension .xt there. </p>
</div>
<div class="xar-norm xar-standard-box-padding">
   <h1><strong>Title:</strong>&nbsp;Student Code Critique Competition 28</h1>
<p><strong>Author:</strong>&nbsp;</p>
<p>
<strong>Date:</strong> 03 June 2004 13:16:06 +01:00 or Thu, 03 June 2004 13:16:06 +01:00</p>
<p><strong>Summary:</strong>&nbsp;</p>
<p><strong>Body:</strong>&nbsp;<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e22" id="d0e22"></a></h2>
</div>
<p><span class="bold"><b>Prizes provided by Blackwells Bookshops
&amp; Addison-Wesley</b></span></p>
<p><span class="emphasis"><em>Please note that participation in
this competition is open to all members. The title reflects the
fact that the code used is normally provided by a student as part
of their course work.</em></span></p>
<p><span class="emphasis"><em>This item is part of the Dialogue
section of C Vu, which is intended to designate it as an item where
reader interaction is particularly important. Readers' comments and
criticisms of published entries are always welcome.</em></span></p>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e33" id="d0e33"></a>Before We
Start</h2>
</div>
<p>Given the amount of entries received so far (I hope this
attitude doesn't decay as time goes by), I'll be as concise as
possible. Please remember that you can get the current problem on
the ACCU website (<a href="http://www.accu.org/journals/" target=
"_top">http://www.accu.org/journals/</a>). This should be enough
motivation for people who don't participate due to the short time
span between the date they receive C Vu and the contest deadline.
As Francis stated in the last column, other languages such as Java,
C# and Python are also very welcomed, so if you have some snippet
you consider suitable for publishing, drop me a line at <tt class=
"email">&lt;<a href=
"mailto:caabeiro@vodafone.es">caabeiro@vodafone.es</a>&gt;</tt></p>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e43" id="d0e43"></a>Late Submission
For SCC 26</h2>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e46" id="d0e46"></a>From Ian (surname
not provided)</h3>
</div>
<p>The simple answer to the student's problem is arrays in C++
being indexed from 0 he does not need the + 1 in his loop which
would then read:</p>
<pre class="programlisting">
for (int i = 0; i &lt;= len; i++)
cout &lt;&lt; str[i];
</pre>
<p>However this leaves a few problems. Addressing the most obvious
first main should return an int rather than a void (most obvious
because my version of GCC will not compile the code until this is
fixed). [<span class="emphasis"><em>gcc 3.3.3 will allow void
main() to be compiled. A warning is given rather than an error -
Ed</em></span>]</p>
<p>A lot of the remaining problems stem from the use of C-style
strings and changing these for STL strings will address a number of
issues. In terms of the current issues related to the C strings the
<tt class="constant">arraySize</tt> constant is unnecessary and
dangerous, if <tt class="literal">&quot;Need help with C++.&quot;</tt>
becomes <tt class="literal">&quot;Need no help with C++.&quot;</tt> in a
moment of hubris and the <tt class="constant">arraySize</tt> value
is not increased then there are potential problems, <tt class=
"literal">char str[] = &quot;Need ...&quot;</tt> will suffice instead. The
loop given is printing the final null character which whilst not
harmful is not necessary.</p>
<p>Initially changing to use C++ strings tidies these up a bit.</p>
<pre class="programlisting">
#include &lt;iostream&gt;
#include &lt;string&gt;
using namespace std;
int main() {
  string str = &quot;Need help with C++.&quot;;
  int len = str.size();
  cout &lt;&lt; &quot;The sentence \&quot;Need help with
       C++.\&quot; has &quot; &lt;&lt; len &lt;&lt; &quot; characters.&quot;
       &lt;&lt; endl &lt;&lt; endl;
  for (int i = 0; i &lt; len; i++)
    cout &lt;&lt; str[i];
}
</pre>
<p>Even this is correct but could still be improved in a few ways.
The <tt class="literal">&quot;Need help with C++.&quot;</tt> string is hard
coded in two places and the <tt class="varname">len</tt> variable
is could be replaced with the <tt class=
"methodname">str.size()</tt> call where it is used. In a program of
this size it also not necessary (though not harmful) to flush the
output buffers with <tt class="literal">endl</tt> repeatedly,
<tt class="literal">&quot;\n&quot;</tt> will suffice. (Incidentally the
original loop version dropped the carriage return after each
character, which behaviour is required is unclear.)</p>
<pre class="programlisting">
#include &lt;iostream&gt;
#include &lt;string&gt;
using namespace std;
int main() {
  string str = &quot;Need help with C++.&quot;;
  cout &lt;&lt; &quot;The sentence \&quot;&quot; &lt;&lt; str &lt;&lt; &quot;\&quot; has &quot;
       &lt;&lt; str.size() &lt;&lt; &quot; characters.\n\n&quot;;
  for (int i = 0; i &lt; str.size(); i++)
    cout &lt;&lt; str[i];
}
</pre>
<p>Finally the loop could be made more idiomatic by using string
iterators rather than indexing (which would also handle the case if
the string size happened to overflow the <span class=
"type">int</span>).</p>
<pre class="programlisting">
for (string::const_iterator i = str.begin();
     i != str.end(); ++i)
  cout &lt;&lt; *i;
</pre>
<p>But even more so by using an STL algorithm rather than an
explicit loop to perform the job, the final version becoming</p>
<pre class="programlisting">
#include &lt;iostream&gt;
#include &lt;string&gt;
#include &lt;algorithm&gt;
#include &lt;iterator&gt;
using namespace std;
int main() {
  string str = &quot;Need help with C++.&quot;;
  cout &lt;&lt; &quot;The sentence \&quot;&quot; &lt;&lt; str &lt;&lt; &quot;\&quot; has &quot;
       &lt;&lt; str.size() &lt;&lt; &quot; characters.\n\n&quot;;
  std::copy(str.begin(), str.end(),
            ostream_iterator&lt;char&gt;(cout, &quot;&quot;));
}
</pre></div>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e109" id="d0e109"></a>Student Code
Critique 27 Entries</h2>
</div>
<p><span class="emphasis"><em>There are at least two issues with
this issue's problem code. The first is finding the immediate logic
error in the code that results in false positives. The second, to
my mind more important issue, is the student's approach to solving
the problem. It is relatively easy to learn to write syntactically
correct code but that is not programming any more than writing
grammatically correct English is writing poetry or a
novel.</em></span></p>
<p><span class="emphasis"><em>Please submit a critique of the code
as it is and then append a critique of the student's approach to
the problem s/he was set.</em></span></p>
<p>In this exercise an ugly number is defined as a compound number
whose only prime factors are 2, 3 or 5. Note that a factor can
repeat so 20 (2*2*5) is an ugly number. The following program
outputs ugly numbers correctly, but also outputs prime numbers. I
can't understand why this is happening because the pointer returned
by <tt class="function">pf()</tt> points to a zeroed 1st element of
the array <tt class="varname">flist</tt> when the input to
<tt class="function">pf()</tt> is prime. It should fail the
<tt class="literal">while()</tt> test and the next number should be
factored. I can kludge this with a separate test for primes, but I
would like to understand why it's not working as is.</p>
<pre class="programlisting">
/* find &quot;ugly numbers&quot;: their prime factors
are all 2, 3, or 5 */
#include &lt;stdio.h&gt;
#include &lt;stdlib.h&gt;
#define SIZE 20
/* SIZE is the max number of prime factors */
#define TWO 2
#define THREE 3
#define FIVE 5
int *pf(int number);

int main(int argc, char *argv[]) {
  int *flist,idx, n, ugly = 0;
  int start, stop;
  if(argc != 3)exit(EXIT_FAILURE);
  start = atoi(argv[1]); /*enter a range */
  stop = atoi(argv[2]);
  for(n = start; n &lt; stop +1; ++n) {
    idx = 0;
    flist = pf(n);
    while(flist[idx]) {
      if(flist[idx]==TWO ||flist[idx]==THREE
         ||flist[idx]==FIVE) {
        ugly = 1;
        ++idx;
      }
      else {
        ugly = 0;
        ++idx;
      }
    }
    if(ugly == 1)
    printf(&quot;%d\n&quot;, n);
    free(flist);
  }
  return 0;
}

/* find the prime factors of number */
int *pf(int number) {
  int *flist, quotient=0, divisor=2, idx=0;
  flist = calloc(SIZE, sizeof(int));
  while(divisor &lt; number + 1) {
    if(divisor == number){
      flist[idx] = quotient;
      /* add last factor to list */
      break;
    }
    if(number % divisor == 0) {
      flist[idx++] = divisor;
      quotient = number/divisor;
      number = quotient;
    }
    else ++divisor;
  }
  return flist;
}
</pre>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e134" id="d0e134"></a>From Roger Orr
<tt class="email">&lt;<a href=
"mailto:rogero@howzatt.demon.co.uk">rogero@howzatt.demon.co.uk</a>&gt;</tt></h3>
</div>
<p>The initial problem which the student reports is the false
positives for some primes. For example:</p>
<pre class="screen">
C:&gt;ugly 30 32
30
31
32
</pre>
<p>where '31' should be missing - but:</p>
<pre class="screen">
C:&gt;ugly 70 72
72
</pre>
<p>correctly doesn't display '71'. How can we find the bug?</p>
<p>I can think of four main ways to resolve down the problem.</p>
<div class="orderedlist">
<ol type="a">
<li>
<p>explore the problem further</p>
</li>
<li>
<p>review the code</p>
</li>
<li>
<p>use a debugger</p>
</li>
<li>
<p>change the algorithm</p>
</li>
</ol>
</div>
<p>These options are not exclusive - and for more complicated
problems several of these might be used together.</p>
<p>Let's look at how the problem might be resolved in each
case:</p>
<div class="orderedlist">
<ol type="a">
<li>
<p><span class="bold"><b>Try more numbers and see if a pattern
appears.</b></span></p>
<pre class="screen">
C:&gt;ugly 10 40
10
11 **
12
13 **
15
16
17 **
18
19 **
20
24
25
27
30
31 **
32
36
37 **
40
</pre>
<p>The ones with asterisks ought not to be displayed. However 23
and 29 are correctly not shown.</p>
<p>We may eventually realise that a prime is printed if and only if
the previous number printed was 'ugly'. It is then a small step to
realise that the <tt class="varname">ugly</tt> variable - which
maintains the state of being ugly - is not being reset between
iterations of the main loop.</p>
</li>
<li>
<p><span class="bold"><b>Review the code</b></span></p>
<p>It is possible to perform a walk through of the code and
discover the fault. Even for only a few lines of code however it
might take a long time to find the error in failing to reset
<tt class="varname">ugly</tt>.</p>
</li>
<li>
<p><span class="bold"><b>Use a debugger</b></span></p>
<p>If the program is compiled for debugging and the first example
is single stepped through the debugger it should be fairly easy to
spot that the variable <tt class="varname">ugly</tt> starts the
loop with the value 1 for the second number (31).</p>
<p>Then the <tt class="literal">while(flist[idx])</tt> evaluates to
false since the first element is zero, and so the test <tt class=
"literal">if(ugly == 1)</tt> is successful.</p>
</li>
<li>
<p><span class="bold"><b>Change the algorithm</b></span></p>
<p>We could simply cover over the problem by changing the
algorithm. Many bugs are caused by boundary conditions and special
cases.</p>
<p>In this example, <tt class="function">pf</tt> returns an array
with the first number zero for prime numbers which is a special
case. This is because, when the number is prime, no number divides
it and so the initial value if quotient is returned.</p>
<p>The first approach is to add extra code for this special case -
we could change the test</p>
<pre class="programlisting">
if (ugly == 1)
</pre>
<p>to</p>
<pre class="programlisting">
if (ugly == 1 &amp;&amp; flist[0])
</pre>
<p>and if we try this out we'll find that the bug appears to have
gone.</p>
<p>The danger with this approach - as pointed out by the student -
is that this may not have fixed the bug but simply changed the
symptoms. The other danger is that the new algorithm may not be
correct!</p>
<p>A second approach, for example, is to change the initialisation
of <tt class="varname">quotient</tt> from</p>
<pre class="programlisting">
quotient = 0
</pre>
<p>to</p>
<pre class="programlisting">
quotient = number
</pre>
<p>then <tt class="function">pf</tt> will return the input number
as the first item for primes and we remove the special case for
primes.</p>
<p>If we try this we will find that both the examples above now
work correctly. However we've introduced a different bug - 2, 3 and
5 are now displayed although they are not compound numbers.</p>
<p>What have we done? We've tried to remove a special case - prime
numbers - but they are a special case in the problem statement and
not just an implementation detail. Albert Einstein is credited with
the statement: &quot;<span class="quote">Make things as simple as
possible, but no simpler</span>&quot;, and we've hit the second part of
this!</p>
<p>How can we fix the bug? We need to ensure that ugly is reset at
the beginning of the loop. The simple, naive approach just adds a
line <tt class="literal">ugly=0</tt>, after the <tt class=
"literal">for</tt> statement.</p>
<p>While this is adequate a better approach moves the declaration
of the variable <tt class="varname">ugly</tt> inside the <tt class=
"literal">for</tt> loop.</p>
<p>Remove:</p>
<pre class="programlisting">
, ugly = 0
</pre>
<p>from the line after <tt class="function">main</tt>, and put the
line:</p>
<pre class="programlisting">
int ugly = 0;
</pre>
<p>directly after the <tt class="literal">for</tt> statement.</p>
<p>It is in general good to declare variables with the smallest
scope possible, and close to their use. The variable <tt class=
"varname">ugly</tt> is required only within the loop and it should
not persist its value between iterations. We can make the change
and now the program runs as expected.</p>
<p>What else is wrong with the code? The corrected code works for
all numbers up to 1048576 when it misbehaves. The problem is the
hard-wired limit of <tt class="literal">SIZE</tt>. This limits the
program to 19 factors (the last entry can't be used since the
<tt class="varname">flist</tt> array is always terminated with a
zero.) One easy solution is to check <tt class="literal">stop</tt>
is less than 1048576 and report an error if not. More complicated
solutions are obviously possible to remove the fixed size limit -
but only if necessary.</p>
<p>Using <tt class="literal">#define</tt> to define names for
numbers seems strange, to put it mildly. What is going on? The
numbers 2, 3 and 5 are special for this program, and I think the
programmer wanted to make that explicit.</p>
<p>However the names are not helpful - they literally add nothing
to the program (try reading it aloud to see what I mean!)</p>
<p>The principle is a good one though - beware magic numbers. I
would like to keep the principle but not the implementation.</p>
<p>For example:</p>
<pre class="programlisting">
const int factors[] = { 2, 3, 5 };
</pre>
<p>This defines an array containing all the factors making 'ugly'
numbers, and the rest of the code does not need to refer to them
again directly, so the test</p>
<pre class="programlisting">
if (flist[idx] == TWO ||
    flist[idx] == THREE ||
    flist[idx] == FIVE) {
</pre>
<p>can be re-written as</p>
<pre class="programlisting">
if (flist[idx] == factors[0] ||
    flist[idx] == factors[1] ||
    flist[idx] == factors[2]) {
</pre>
<p>Of course, once the magic numbers are in an array it might be
worth generalising the check so the code could be modified very
easily if you decided that, for example, '7' was also an ugly
factor.</p>
<p>The complete check could be re-written using a nested loop
as</p>
<pre class="programlisting">
ugly = 0;
int j;
for(j = 0; j &lt; sizeof(ugly_factors) /
  sizeof(ugly_factors[0]); ++j)
  if(flist[idx] == ugly_factors[j])
    ugly = 1;
++idx;
</pre>
<p>While on the subject of names, I don't find the function name pf
very informative. It might mean many things, it might be 'pointer
to function' for example! Perhaps calling it '<tt class=
"function">factorize</tt>' would be better.</p>
<p>There is also a problem with memory allocation. The code
allocates a fixed size buffer in '<tt class="function">pf</tt>'
which it is the caller's responsibility to free. There are two
potential problems with this, firstly it would be easy to leak
memory should the caller forget to free the returned pointer and
secondly memory allocation can be relatively slow. If the caller
passed in the buffer instead then no memory allocation would be
required since a local variable in the caller could be used for the
array.</p>
<p>And what about performance? The code works, but is not very
efficient. The '<tt class="function">pf</tt>' function checks each
possible divisor of the number in turn, incrementing the divisor by
one each time. Try running it over the range 524288 1048575 to see
how long it takes!</p>
<p>Does this matter? We don't know - we do not have the information
about the proposed use of the program. If performance matters then
a different approach to the problem will improve the speed.</p>
<p>One easy way to do this with the current program structure is to
exit the main loop in <tt class="function">pf</tt> prematurely
(with <tt class="varname">flist[0]</tt> set to zero) as soon as the
divisor exceeds the largest ugly factor, since the number cannot be
ugly in this case and further factoring is not necessary for this
program. This of course makes '<tt class="function">pf</tt>' no
longer a general purpose function to obtain all the prime factors
of a number.</p>
<p>However, when I tried it, the time taken to calculate the entire
range above changed to 1.3 seconds - the original algorithm was
still running after 30 minutes (when I got bored and killed it
off).</p>
</li>
</ol>
</div>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e359" id="d0e359"></a>From Nevin Liber
<tt class="email">&lt;<a href=
"mailto:nevin@eviloverlord.com">nevin@eviloverlord.com</a>&gt;</tt></h3>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e364" id="d0e364"></a>Logic
Error:</h4>
</div>
<p>As stated, when number is prime, <tt class=
"function">pf(number)</tt> returns an array whose first element is
0.</p>
<p>Now, let us look at the code which tests this value:</p>
<pre class="programlisting">
for(n = start; n &lt; stop+1; ++n) {
  idx = 0;
  flist = pf(n);
  while(flist[idx]) {
    /* ... */
    /* modify ugly */
    /* ... */
  }
  if(ugly == 1)
    printf(&quot;%d\n&quot;, n);
  /* ... */
}
</pre>
<p>So, when <tt class="varname">n</tt> is prime, <tt class=
"literal">flist[0] == 0</tt>, the entire while loop is skipped, and
ugly erroneously retains its value from the previous iteration of
the for loop. Q.E.D.</p>
<p>Note: it actually doesn't print all the prime numbers. For
instance, 23 is skipped because 22 == 2 * 11 is not ugly.</p>
<p>A way to fix this particular bug is to clear ugly at the
beginning of each iteration; i.e.,</p>
<pre class="programlisting">
for(n = start; n &lt; stop+1; ++n) {
  ugly = 0;
  idx = 0;
  flist = pf(n);
  /* ... */
}
</pre></div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e390" id="d0e390"></a>Code
critique:</h4>
</div>
<p><tt class="literal">#define SIZE 20 /* max number of prime
factors*/</tt> This is a latent bug. Besides the comment being
wrong (the maximum number of prime factors is 19), if a given
number has 20 or more prime factors, the code doesn't work, which
can manifest itself either by incorrect results or by a memory
corruption.</p>
<pre class="programlisting">
#define TWO   2
#define THREE 3
#define FIVE  5
</pre>
<p>These are still &quot;magic numbers&quot;. It is clearer just to use the
numbers directly.</p>
<pre class="programlisting">
int *flist, idx, n, ugly = 0;
int start, stop;
if(argc != 3) exit(EXIT_FAILURE);
</pre>
<p>Always use braces; it makes things far clearer.</p>
<p>Declare one variable per line. It is far more readable and
maintainable. Unless there is a good reason not to, initialize the
variables as you declare them.</p>
<pre class="programlisting">
start = atoi(argv[1]);
stop = atoi(argv[2]);
</pre>
<p>What happens if <tt class="varname">argv[1]</tt> or <tt class=
"varname">argv[2]</tt> is negative? Does the algorithm still work?
What happens if the parameters aren't numbers?</p>
<pre class="programlisting">
for(n = start; n &lt; stop + 1; ++n)
</pre>
<p><tt class="literal">n &lt;= stop</tt> is more readable; the
<tt class="literal">+1</tt> tends to throw people off. What happens
when <tt class="varname">stop</tt> is the maximum value an
<span class="type">int</span> can hold?</p>
<pre class="programlisting">
flist = pf(n);
</pre>
<p>Need some comments that the ownership of the array that
<tt class="function">pf()</tt> returns needs to be managed by the
caller. This technique is highly error prone in non-trivial
projects.</p>
<pre class="programlisting">
while(flist[idx]) {
  if(flist[idx] == TWO ||
     flist[idx] == THREE ||
     flist[idx] == FIVE) {
    ugly = 1;
    ++idx;
  }
  else {
    ugly = 0;
    ++idx;
  }
}
</pre>
<p>Note: Kudos for using pre-increment over post-increment. This is
a good habit to get into, especially if you ever move to C++, since
pre-increment performs at least as well as post-increment.</p>
<p>Since <tt class="literal">++idx</tt> is in both clauses of the
<tt class="literal">if</tt> statement, factor it out. I might write
this as:</p>
<pre class="programlisting">
while(flist[idx]) {
  ugly = 2 == flist[idx] ||
         3 == flist[idx] ||
         5 == flist[idx];
  ++idx;
}
</pre>
<p>What this <tt class="literal">while</tt> loop does is test the
last non-zero value of <tt class="varname">flist</tt> to see if it
is 2, 3, or 5; if it isn't, then the number isn't ugly (since it
has other prime factors). This works for the problem as stated
because 2, 3, and 5 are the lowest sequential primes. If, for
instance, 11 were added to the ugly prime set, it isn't obvious how
to extend this algorithm, as just adding <tt class="literal">|| 11
== flist[idx]</tt> doesn't work.</p>
<pre class="programlisting">
if(ugly == 1)
printf(&quot;%d &quot;, n);
free(flist);
</pre>
<p>Good: no memory leak.</p>
<p>Again, use braces. Since the indentation is wrong (and something
that is not enforced by the language), to the casual observer it
looks like <tt class="function">printf()</tt> is always called.</p>
<pre class="programlisting">
/* find the prime factors of number */
int *pf(int number)
</pre>
<p>Need a better interface. What happens when number is prime?
Unless the implementation is studied, it is unexpected that no
prime factors are returned for prime numbers. While you can convey
this in comments (as well as that the caller has to <tt class=
"function">free()</tt> the returned array, don't pass in a number
with SIZE or more prime factors, etc.), it is better to make an
interface that does what is expected.</p>
<pre class="programlisting">
while(divisor &lt; number + 1) {
  if (divisor == number) {
    flist[idx] = quotient;
    break;
  }
}
</pre>
<p>The implementation just isn't obvious. Sometimes quotient means
the previous quotient (when the initial value of number isn't
prime); sometimes it means 0 (when the initial value of number is
prime). Make these kinds of things explicit. Also, <tt class=
"literal">while (divisor &lt;= number)</tt> is more readable.</p>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e487" id="d0e487"></a>Approach
Critique:</h4>
</div>
<p>There is a lot of messy, error-prone bookkeeping involved with
calculating the prime factors. Yet the problem isn't asking for the
prime factors; it is just asking for compound numbers that aren't
solely made up of ugly primes.</p>
<p>Plus, the code which checks for ugliness is tightly coupled with
the return value from <tt class="literal">pf();</tt> i.e., it
assumes <tt class="function">pf()</tt> returns prime factors in
ascending order, returns 0 as the first element in the array when
the input is prime, the caller is responsible for <tt class=
"function">free()</tt> ing the array, etc. That behaviour should
all be encapsulated in a function, not spread across <tt class=
"function">main()</tt> and <tt class="function">pf()</tt>.</p>
<p>It also isn't data driven; if the definition of ugly primes
changes, more code needs to be added. Right now, the algorithm is
dependent on the ugly primes being the lowest valued and
sequential. If that constraint is violated, the entire algorithm
has to be rewritten. We can be more resilient.</p>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e511" id="d0e511"></a>Alternate
Implementation:</h4>
</div>
<p>We don't need to know all the prime factors; we just need to
check that:</p>
<div class="orderedlist">
<ol type="a">
<li>
<p>The only prime factors are 2, 3, and 5</p>
</li>
<li>
<p>The number has at least 2 prime factors.</p>
</li>
</ol>
</div>
<p>If both of those hold, the number is ugly.</p>
<p>If I were to implement it, I would do so as follows:</p>
<pre class="programlisting">
int IsUgly(unsigned long number) {
  unsigned long uglyFactorsCount = 0;
  if(number) {
    static const unsigned long uglyPrimes[] = { 2, 3, 5 };
    size_t p = 0;
    for(; sizeof(uglyPrimes) /
        sizeof(uglyPrimes[0]) != p; ++p) {
      unsigned long prime = uglyPrimes[p];
      while(0 == number % prime) {
        number /= prime;
        ++uglyFactorsCount;
      }
    }
  }
  return 1 == number &amp;&amp;
         1 &lt; uglyFactorsCount;
}
</pre>
<p>The algorithm iterates over all the primes in <tt class=
"varname">uglyPrimes</tt> and factors them out of number, counting
(in <tt class="varname">uglyFactorsCount</tt>) the number of
factors that are divided out along the way. If the result of number
is 1, then all of its prime factors are in <tt class=
"varname">uglyPrimes</tt>, and all that is left is to make sure
that there were at least two factors divided out.</p>
<p>Some details:</p>
<pre class="programlisting">
int IsUgly(unsigned long number)
</pre>
<p>I pass in an <span class="type">unsigned long</span> so I don't
have to deal with negative numbers.</p>
<pre class="programlisting">
if(number)
</pre>
<p>If I didn't check for <tt class="literal">0 != number</tt>,
<tt class="literal">while(0 == number % prime)</tt> would always be
true, and there would be an infinite loop bug. This check is needed
for correctness.</p>
<p>At this point, I started to micro-optimize. Since I have to
check number anyway, and I know that 1 cannot be ugly (no matter
what numbers are in <tt class="varname">uglyPrimes</tt>), there is
no reason to go through the factoring code, and I could say
<tt class="literal">if (1 &lt; number)</tt>. Since no prime can be
ugly, I could have used <tt class="literal">if (3 &lt;
number)</tt>, but then the value of <tt class=
"varname">uglyFactorsCount</tt> isn't technically correct in those
circumstances, and even though I only care that it has a value less
than 2 (which would still hold) in order for the algorithm to give
the correct answer, it started feeling messy. I remembered the old
adage &quot;measure, then optimize&quot;, and abandoned this path.</p>
<pre class="programlisting">
if(number) {
  static const unsigned long uglyPrimes[]
            = { 2, 3, 5 };
</pre>
<p>I declare variables as close to their use as possible, and try
and limit their scope as much as possible. Also, I declared it
<tt class="literal">const</tt>, as I want the compiler to enforce
that I don't modify the values in the array.</p>
<pre class="programlisting">
size_t p = 0;
for(; sizeof(uglyPrimes) /
  sizeof(uglyPrimes[0]) != p; ++p)
</pre>
<p>By using <tt class="function">sizeof</tt> in this fashion, the
code is always right no matter how many elements are in <tt class=
"varname">uglyPrimes</tt>.</p>
<p>Note: this works because <tt class="varname">uglyPrimes</tt> is
the whole array. If it were passed in to the function instead, it
would decay into a pointer, and the result would not be what was
expected.</p>
<p>Note: I prefer <tt class="literal">sizeof(uglyPrimes[0])</tt> to
<tt class="literal">sizeof(*uglyPrimes)</tt>, as there can be
unexpected results with the latter when programming in C++ (then
again, there are better ways of doing this kind of thing in C++). I
used <tt class="literal">!= p</tt> instead of <tt class=
"literal">&gt; p</tt> , since the former is more general when using
with iterators in C++. But I digress...</p>
<p>Note: I tend to put l-values on the right side of expressions.
In case I accidentally write something like <tt class="literal">if
(0 = a)</tt> instead of <tt class="literal">if (0 == a)</tt>, I get
a compile time error.</p>
<p>For completeness, main() would look something like:</p>
<pre class="programlisting">
int main(int argc, char * argv[]) {
  if(3 == argc) {
    unsigned long number
      = strtoul(argv[1], NULL, 0);
    unsigned long stop
      = strtoul(argv[2], NULL, 0);
    for(; number &lt; stop; ++number) {
      if(IsUgly(number)) {
        printf(&quot;%lu\n&quot;, number);
      }
    }
    if(number == stop &amp;&amp; IsUgly(number)) {
      printf(&quot;%lu\n&quot;, number);
    }
    return 0;
  }
  else {
    return 1;
  }
}
</pre>
<p>Note: The reason there is an extra <tt class="literal">if
(number == stop /* ... */)</tt> is to avoid the infinite loop bug
when stop contains the largest possible <span class="type">unsigned
long</span> value.</p>
</div>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e629" id="d0e629"></a>From Duncan
Booth <tt class="email">&lt;<a href=
"mailto:duncan.booth@suttoncourtenay.org.uk">duncan.booth@suttoncourtenay.org.uk</a>&gt;</tt></h3>
</div>
<p>The first thing that strikes me about this code is that the
structure does not obviously relate to the question. The question
asks for a list of 'ugly numbers', so I would expect to see at
least one function with the word 'ugly' somewhere in its name.
Instead there is a function which sort of produces a list of prime
factors, and the rest of the code is all bundled into main.</p>
<p>The student wonders why some additional numbers are output. This
is because for any prime number the <tt class="literal">while</tt>
loop never executes, so the variable <tt class="varname">ugly</tt>
is never reset. This is a direct result of putting too much logic
into the <tt class="function">main</tt> function - extracting the
test for ugliness to a separate function would have prevented this
particular error ever happening.</p>
<p>The function to extract prime factors has several problems of
its own: it uses a fixed length array for the factors with no check
for overflow and the length chosen is too short even for 32 bit
integers; if it is given a large prime number to factorise it will
test every possible divisor up to the number (which could take a
while) when it only needs to test divisors up to the square root of
the number to determine the prime factors, or up to five to
determine whether the number is ugly. The function also doesn't do
what the comment at the top says: if it is given a prime number to
factorise then instead of returning the number itself it returns an
empty list as a special case. This is likely to surprise anyone
trying to use the function, so it would be good if the behaviour
were documented, but better still if the special behaviour for
primes was removed altogether.</p>
<p>Rather than just showing a working program, I will show the
steps I use to get to a solution to the problem. I am going to use
Python rather than C since that lets me ignore issues like memory
management and overflows and also lets me try a variety of
algorithms more quickly than I could in C.</p>
<p>When I have a working solution, then if it needs speeding up, or
if there is another reason for requiring a C solution the code can
be translated to C fairly easily.</p>
<p>Here is my first effort in Python. It follows the student's
logic fairly closely in so far as it counts through all the numbers
in the range and tests each one for ugliness. The test is a bit
different though, instead of extracting all the prime factors, we
just look for the factors 2, 3 and 5 and then see if there is any
unfactorised residue.</p>
<p>The main code converts its arguments to integers using the eval
functions. This makes it easy for me to test comparatively large
numbers as I can type an expression as the argument (say 2**29
instead of having to enter 536870912).</p>
<pre class="programlisting">
# File ugly.py

import sys

BADFACTORS = 2, 3, 5

def isUgly(n):
  if n in BADFACTORS or n in (0, 1):
    return False
  for factor in BADFACTORS:
    while n%factor == 0:
      n = n/factor
  return n == 1

def printUglyRange(start, end):
  print &quot;Ugly numbers from&quot;,start,&quot;to&quot;,end
  for i in xrange(start, end):
    if isUgly(i):
      print i
  if name__=='__main__':
    if len(sys.argv) != 3:
      sys.exit(&quot;Usage: %s start end&quot; % sys.argv[0])
    start, end = eval(sys.argv[1]), eval(sys.argv[2])
    printUglyRange(start, end+1)
</pre>
<p>I don't feel this code quite expresses my intent yet, so the
next step is to refactor <tt class=
"function">printUglyRange</tt>:</p>
<pre class="programlisting">
def uglyRange(start, end):
  for i in xrange(start, end):
    if isUgly(i):
      yield i

def printUglyRange(start, end):
  print &quot;Ugly numbers from&quot;,start,&quot;to&quot;,end
  for i in uglyRange(start, end):
    print I
</pre>
<p>For consistency with how Python works generally, the <tt class=
"function">uglyRange</tt> function includes its start value but
excludes the end value, so 1 is added to the end value to get the
same output as the student expected. The <tt class=
"literal">yield</tt> statement may be unfamiliar to C programmers:
when executed it suspends execution of the generator function it is
in and returns its argument to the <tt class="literal">for</tt>
loop that invoked it; each time the <tt class="literal">for</tt>
loop needs another value the generator is resumed exactly where it
was suspended and another value calculated.</p>
<p>This separates the printing of the ugly numbers from the logic,
and the program seems to run, but when we get up to large numbers
(like 2**29) it takes a long time to output each number. The
problem is that we are searching an increasingly sparse space for
each ugly number instead of going directly to the next value. A
better solution would be to generate only the ugly numbers and
completely ignore other numbers. First though, I suggest writing
some tests in another file <tt class=
"filename">testugly.py</tt>:</p>
<pre class="programlisting">
import unittest
class TestUgly(unittest.TestCase):
UGLYTO11 = [ 4, 6, 8, 9, 10, ]
UGLY100TO130 = [ 100, 108, 120, 125, 128, ]

  def setUp(self):
    import ugly
    self.uglyRange = ugly.uglyRange

  def test0to11(self):
    expected = self.UGLYTO11
    actual = list(self.uglyRange(0, 11))
    self.assertEquals(expected, actual)

  def test100to130(self):
    expected = self.UGLY100TO130
    actual = list(self.uglyRange(100, 130))
    self.assertEquals(expected, actual)

if name__=='__main__':
  unittest.main()
</pre>
<p>The tests allow us to modify the code with confidence that it
will continue working, so we can move from an implementation which
is easy to understand to one that is much more complex. I tried a
few different algorithms, but the version below is my favourite. It
generates ugly numbers in ascending order with the numbers
partitioned into three lists according to the smallest factor
present in that number:</p>
<pre class="programlisting">
import sys

BADFACTORS = 2, 3, 5

class UglyFifo:
  '''Stores a list of ugly numbers,
     first in first out. Fifos are
     chained so that pushes ripple
     down the chain.'''

  def __init__(self, factor, nextFifo):
    self.head, self.tail = [], []
    self.factor = factor
    if nextFifo:
      self.callNext = nextFifo.push
    else:
      self.callNext = None
    self.push(factor)

  def push(self, n):
    '''Append n multiplied by the
       factor for this fifo, then
       propagate n to the next
       queue.'''
    self.tail.append(n * self.factor)
    if self.callNext:
      self.callNext(n)

  def pop(self):
    '''Returns the oldest (i.e.
       smallest) ugly number from
       the fifo'''
    if not self.head:
      self.head, self.tail = self.tail,self.head
      self.head.reverse()
    return self.head.pop()

  def pushThenPop(self, n):
    self.push(n)
    return self.pop()

def generateUgly():
  '''Generate a potentially infinite
     sequence of ugly numbers, in
     increasing order.'''
  values = []
  fifo = None

def processLowest(lowest):
  '''Push a new value into a fifo,
     update the working values and
     return an ugly number'''
  ugly, fifo = lowest
  lowest[0] = fifo.pushThenPop(ugly)
  return ugly
  for factor in BADFACTORS:
    while values:
      lowest = min(values)
      if lowest[0] &gt; factor:
        break
      yield processLowest(lowest)
    fifo = UglyFifo(factor, fifo)
    values.append([fifo.pop(), fifo])
  while 1:
    yield processLowest(min(values))

def uglyRange(lo, hi):
  '''Generate all ugly numbers from lo
     (inclusive) to hi exclusive.'''
  for i in generateUgly():
    if i &gt;= hi:
      break
    if i &gt;= lo:
      yield i

def main(start, end):
  print &quot;Ugly numbers from&quot;,start,&quot;to&quot;,end
  for i in uglyRange(start, end+1):
    print i
  if __name__=='__main__':
    if len(sys.argv) != 3:
      sys.exit(&quot;Usage: %s start end&quot; % sys.argv[0])
    main(eval(sys.argv[1]), eval(sys.argv[2]))
</pre>
<p>Perhaps this seems like overkill for a simple problem, but this
version of the program works up to quite large ugly numbers, albeit
with a delay if the starting value is large. On my system it takes
just over 10 seconds to calculate the 1.7 million values up to
10**100 which is probably fast enough for most purposes and
therefore doesn't really need converting back to C.</p>
<p>If the student wants to convert this to C (or is compelled to do
so by the teacher), there are several ways to do it, but the one I
would recommend would be to use the Python program to write all
ugly numbers up to some arbitrary limit into a file (there are 1844
up to 2**32, or 13278 up to 2**64) then write a program to print
ugly numbers by reading them from the file and printing those in
the required range. The code could handle the numbers as strings
which would allow even a simple C program to work with arbitrarily
large values, but I'll leave this as an exercise for the
student.</p>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e695" id="d0e695"></a>From Margaret
Wood <tt class="email">&lt;<a href=
"mailto:margaretwood@pocketmail.com.au">margaretwood@pocketmail.com.au</a>&gt;</tt></h3>
</div>
<p>The student is quite correct in stating that any prime number
should fail the <tt class="literal">while()</tt> test. The problem
is that the value of ugly is only set within the <tt class=
"literal">while</tt> loop. When n is a prime number, the value of
ugly remains at what it was set to on the previous trip through the
<tt class="literal">while</tt> loop. Thus any prime number which
immediately follows an ugly number will also be printed. To fix the
problem it is just necessary to set <tt class="varname">ugly</tt>
to 0 at the start of each iteration through the <tt class=
"literal">for</tt> loop.</p>
<p>Now to look at improvements to the code in general. I'll start
with the function to calculate prime factors. This could be a
useful general purpose function if it did what the comment claims
it does, namely to find the prime factors of a number. As it
stands, however, it only finds the prime factors of compound
numbers, returning 0 for prime numbers. The student has introduced
a special behaviour for primes. I would prefer to modify the
function to:</p>
<pre class="programlisting">
/* find the prime factors of number */
int *pf(int number) {
  int *flist, quotient=0, divisor=2, idx=0;
  flist = calloc(SIZE, sizeof(int));
  while(divisor &lt; number + 1) {
    if(divisor == number) {
      flist[idx] = divisor;
      /* add last factor to list */
      break;
    }
    if(number % divisor == 0) {
      flist[idx++] = divisor;
      quotient = number/divisor;
      number = quotient;
    }
    else ++divisor;
  }
  return flist;
}
</pre>
<p>then add the special treatment in the main function</p>
<pre class="programlisting">
if(flist[1] == 0) {
  ugly = 0;
else {
  while flist[idx]) {
    ...
  }
}
</pre>
<p>Ideally the <tt class="function">pf()</tt> function should also
ensure that the factorisation does not go beyond the end of the
array, either by checking that <tt class="varname">idx</tt> remains
less than SIZE, or by choosing SIZE so that the array is large
enough to hold the maximum possible number of factors of any number
that will fit in an <span class="type">int</span>. (Since
<tt class="constant">MAXINT</tt> is always 2n-1, where n will
depend on how many bytes make up an int, any number that can be
stored in an <span class="type">int</span> can have at most (n-1)
prime factors).</p>
<p>However, we don't actually need to know all the prime factors of
a compound number to determine whether it is ugly or not. We just
need to know whether it has at least one prime factor that is
different from 2, 3 and 5. For all numbers &gt; 5 we can determine
this without storing the factors as follows.</p>
<pre class="programlisting">
while(n % 2 == 0) {
  n /= 2;
}

while(n % 3 == 0) {
  n /= 3;
}

while(n % 5 == 0) {
  n /= 5;
}

if(n == 1) {
  ugly = 1;
}
</pre>
<p>The numbers &lt; 6 can be treated as special cases, 4 is the
only ugly one:</p>
<pre class="programlisting">
if(n == 4) {
  ugly = 1;
}
</pre>
<p>(Remember that ugly is initialised to 0 at the start of the for
loop, so 1, 2, 3, 5 will not become ugly)</p>
<p>Thus all that is required (apart from checking that <tt class=
"varname">start</tt> and <tt class="varname">stop</tt> are valid
numbers, with <tt class="literal">stop &gt;= start</tt>, and
printing some helpful message if the user has not supplied 2
correct arguments) is:</p>
<pre class="programlisting">
/* find &quot;ugly numbers&quot;: their prime factors
   are all 2, 3, or 5 */
#include &lt;stdio.h&gt;
#include &lt;stdlib.h&gt;

int main(int argc, char *argv[]) {
  int n, ugly, number;
  int start, stop;
  if(argc != 3) {
    /* print helpful message */
    exit(EXIT_FAILURE);
  }
  start = atoi(argv[1]); /*enter a range */
  stop = atoi(argv[2]);
  if(start &gt; stop) {
    n = stop;
    stop = start;
    start = n;
  }
  for(number = start; number &lt; stop +1; ++number) {
    n = number;
    ugly = 0;
    if(n == 4) {
      ugly = 1;
    }
    else if(n &gt; 5) {
      while(n % 2 == 0) {
        n /= 2;
      }
      while(n % 3 == 0) {
        n /= 3;
      }
      while(n % 5 == 0) {
        n /= 5;
      }
      if(n == 1) {
        ugly = 1;
      }
    }
    if(ugly == 1) {
      printf(&quot;%d\n&quot;, number);
    }
  }
  exit(0);
}
</pre></div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e765" id="d0e765"></a>From Simon
Sebright <tt class="email">&lt;<a href=
"mailto:simonsebright@hotmail.com">simonsebright@hotmail.com</a>&gt;</tt></h3>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e770" id="d0e770"></a>Prologue</h4>
</div>
<p>I always feel slightly awkward when writing these things.
Ideally the student would be with the critiquer and the result
would be a dialogue. Instead, they have to be monologues and as
such are not tempered by little indicators of reasons why things
were done or not done in a certain way.</p>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e775" id=
"d0e775"></a>Introduction</h4>
</div>
<p>Regardless of what comes next (which I have at this stage
already written), I have to ask why this student did not find the
answer to his or her own problem. A simple mental run through the
code, or use of a debugger should have left the matter high and
dry. Again this is an issue about which I can only write from my
immediate perspective, with no feedback. My four year old daughter
has just spent the evening asking me why, why, why? I wouldn't
expect a student to have the same naivety.</p>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e780" id="d0e780"></a>Part I</h4>
</div>
<p>The immediate logic error. I haven't run the code, but an
inspection reveals that the variable ugly will not be set for the
current number if the statement <tt class=
"literal">while(flist[idx])</tt> never lets flow into the while
loop. This is the case if the number is prime, so prime numbers
have their ugliness determined by the last number to be processed.
I won't proceed any further with this section because I feel that
corrections to the logic are pointless without some design
changes.</p>
</div>
<div class="sect3" lang="en">
<div class="titlepage">
<h3><a name="d0e788" id="d0e788"></a>Part II</h4>
</div>
<p>It's true there are some aspects of the code I could criticise
on a low level, but I fear that would negate what I think are more
important high level concerns. For example, I don't think
<tt class="literal">#define THREE 3</tt> is adding anything, but my
suggestions below don't use a direct replacement. I'd prefer a
<span class="type">static const int</span>, but as in the classic
town's person giving directions &quot;I wouldn't start from here&quot;. The
code appears to be C, although the question did not stipulate. C++
would give us better idioms for things, as I've mentioned below,
but I'll stick to a functional approach for the bulk of the
critique.</p>
<p>I think the main reason for the occurrence of the logic error is
the lack of clarity of the function <tt class="function">pf()</tt>.
First of all, let's not be lazy and call it <tt class=
"function">GetPrimeFactors()</tt>. Well, what are prime factors? We
have to decide whether or not they should include 1 and the number
itself (if prime). I'm not familiar with the mathematical
definition, so we'll err on the side of the student and say that
these are not prime factors. What is <tt class="function">pf()</tt>
returning? Well, it's a list of prime factors. There's a lack of
symmetry here. A C++ solution would have the function return a list
containing the prime factors, here <tt class="function">main()</tt>
has to know how the list is allocated (if at all). Likewise, it has
to know that the signal for the end of list is a zero (which can
not be prime factor either way). <tt class=
"classname">list&lt;&gt;</tt> wins hands down.</p>
<p>Now, let's take a step back. What are we trying to achieve? The
user wants to supply a numeric range. Within that range, we want to
output all ugly numbers. Straight away, we could write some pseudo
code here, not getting excited about the algorithm for prime
factors, after all, I haven't needed to mention them yet:</p>
<pre class="programlisting">
main
get range to test with validation
for(each number in range)
if current number is ugly
output current number
end if
end for
end main
</pre>
<p>Well, now I think we need a function to see if a number is
ugly:</p>
<pre class="programlisting">
bool IsUgly(int n);
</pre>
<p>Here, we get a chance to condense the ugliness of numbers into
one place and to get rid of those silly <tt class=
"literal">#define</tt>s. A number is ugly if its prime factors are
only 2, 3 or 5. Hmm, let's abstract that. A number is ugly if all
its prime factors (here is where we find it handy that 1 and self
are not prime factors) are to be found in the set 2, 3, 5. So, the
<tt class="function">IsUgly()</tt> function needs two things - a
list of prime factors and a set of ugly prime factors to test
against. Now, we could keep abstracting and have the <tt class=
"function">IsUgly()</tt> function defer to a generalised list
intersection algorithm passing in the ugly prime factors. For this
exercise, that's probably going too far, but after all, we might
change the definition of ugly (or generalise later to prettiness,
etc.) How about this:</p>
<pre class="programlisting">
bool IsUgly(int n) {
  static const int UglyPrimeFactors[]
    = { 2, 3, 5, 0 };
  // again, note the need for a
  // termination condition, something not
  // necessary in a list&lt;&gt;
  // Get prime factors
  // See if all prime factors are one
  // of ugly prime factors. In C++,
  // this could be some sort of
  // intersection call on the list of
  // prime factors and the list of ugly
  // prime factors
}
</pre>
<p>Once and once only, and preferably without the need for
comments, that's my motto.</p>
<p>I have to say that in my professional life, I rarely come across
<tt class="function">main()</tt> or command line arguments, so I
won't go into too much detail here.</p>
<p>There does seem to be a rather user-unfriendly approach with
neither help text available nor error messages in response to
&quot;invalid&quot; input. I think I'd like to have <tt class=
"function">main()</tt> process input, help text and the like and if
all OK, call a function to do the meat of the program, that way we
have a function which can be called from <tt class=
"function">main()</tt> here, or some UI dialog class, etc. And,
test harnesses. So, we can write a test harness which tests a large
range of numbers against known ugliness. Ditto for the <tt class=
"function">GetPrimeFactors()</tt> function, which we can sort of
test through the testing of I<tt class="function">sUgly()</tt>, but
to be sure, we'd again test it with known input/output
combinations.</p>
<p>I've now lost the code as my wife has tidied up (put her things
on the desk), so nitty gritty comments are out of the window. From
what I remember, I'd like to see the word ugly mentioned in code,
not comments. My pseudo code above never had an issue with
uninitialised variables, I like to declare them where needed. I
know in C this was not always possible, but my pseudo code was not
in C and didn't have the given logic problem. I still feel like the
student ought to be here and contribute or sob. By now, I've
totally lost the plot, beer goggles fogging the monitor, but I'll
tender one last point - don't get too excited about implementation
details. For me the exciting thing is planning what details are
going to be needed. It seems as if the student was hell bent on
writing a wicked prime factoring function. When you are a
professional programmer, that's the last of your worries, or you
really are locked away in a darkened room. Rather, you need to step
back, look at the view and take it in (understand it).</p>
</div>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e860" id="d0e860"></a>The Winner of
SCC 27</h3>
</div>
<p>The editor's choice is: <span class="bold"><b>Nevin
Liber</b></span></p>
<p>Please email <tt class="email">&lt;<a href=
"mailto:francis@robinton.demon.co.uk">francis@robinton.demon.co.uk</a>&gt;</tt>
to arrange for your prize.</p>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e872" id="d0e872"></a>Francis'
Commentary</h3>
</div>
<p>I chose the student code for this critique because there was a
point that I wanted to make. The student is more competent than
most in so far as coding in C is concerned. Magic numbers are
avoided, all uppercase is used for pre-processor constants and uses
lower case for other variables. EXIT_FAILURE is used after checking
for the correct number of command line arguments fails. However
there are a couple of points about the code:</p>
<div class="itemizedlist">
<ul type="disc">
<li>
<p>I do not think naming 2, 3, 5 actually adds anything in this
case.</p>
</li>
<li>
<p>replacing <tt class="literal">return 0</tt> with <tt class=
"literal">return EXIT_SUCCESS</tt> would add even more polish.</p>
</li>
<li>
<p>the code does not validate that the command line arguments are
actually suitable ones.</p>
</li>
</ul>
</div>
<p>Once the logic error has been dealt with the program illustrates
reasonable competence with C and from that respect I would give a
good grade. However it still, in my opinion, is poor programming
because it is a very heavy handed solution to the problem. That is
the main point I wanted to make, there is a great deal more to
programming than writing syntactically correct source code that
produces the correct answer. So let me tackle the problem from the
start.</p>
<p>The definition of an ugly number is one that has no prime
factors other than 2, 3 and 5 [that is not how I would have defined
an ugly number but that is irrelevant]. What the student has done
is to reduce each number to its prime factors (not very efficiently
as it happens, but that is another artefact of lack of clarity of
thought). Then the code checks to see if any of the factors are
other than the specified 2, 3 and 5.</p>
<p>Let us step back and think a little. What the problem requires
is that we ignore all factors that are 2, 3 or 5 and see if there
are any others. We can simply discard the factors in which we are
not interested. That idea leads me to write the following little
function:</p>
<pre class="programlisting">
int remove_factor(int number, int factor) {
  while((number % factor) == 0)
    number /= factor;
  return number;
}
</pre>
<p>In other words as long as the number is exactly divisible by
<i class="parameter"><tt>factor</tt></i> (not a perfect name, can
you suggest a better one?) reduce number by dividing by <i class=
"parameter"><tt>factor</tt></i>.</p>
<p>Now look at that little bit of code and decide if there are any
ways in which it could fail. OK, it assumes that neither <i class=
"parameter"><tt>number</tt></i> nor <i class=
"parameter"><tt>factor</tt></i> is zero. The reason for failure
will be different in the two cases. If <i class=
"parameter"><tt>number</tt></i> is zero the function is well
defined, it simply goes into an infinite loop. If factor is zero we
have a divide by zero error. Should <tt class=
"function">remove_factor()</tt> handle either of those problems?
Doing so is not cost free. It is a design decision, but one that
can now be clearly identified and handled as the programmer
chooses.</p>
<p>We can use this little function to determine if a given number
is an ugly one:</p>
<pre class="programlisting">
bool is_ugly(int number) {
  number = remove_factor(number, 2);
  number = remove_factor(number, 3);
  number = remove_factor(number, 5);
  return (number == 1);
}
</pre>
<p>You might not want to use <span class="type">bool</span> as the
return type but that is your choice. Again there is the issue of
whether number is a suitable candidate. We have two issues here: it
must not be negative and it must be a compound number (i.e. it must
have more than one prime factor). As the second is a defining
property of being 'ugly' I think it should be dealt with here. So
our function gets modified to:</p>
<pre class="programlisting">
bool is_ugly(int number) {
  if(number == 4) return TRUE;
  // direct test for smallest composite
  if(number &lt; 6) return FALSE;
  number = remove_factor(number, 2);
  number = remove_factor(number, 3);
  number = remove_factor(number, 5);
  return (number == 1);
  // only 2, 3 and 5 were factors
}
</pre>
<p>Note that the second test deals with all the other cases (number
being zero or negative) and also deals with one of the possible
problems with <tt class="function">remove_factor()</tt>. The other
problem with <tt class="function">remove_factor()</tt> is
eliminated because we haven't actually tried to remove zero as a
factor. Deal with problems at an appropriate level and assume that
the caller of a function knows the pre-conditions (because they
have been documented in the manual.)</p>
<p>Now I am ready to write my program:</p>
<pre class="programlisting">
#include &lt;stdio.h&gt;
#include &lt;stdlib.h&gt;
#include &lt;stdbool.h&gt;

int main(int argc, char *argv[]){
  if(argc != 3) {
    bad_command_line_args(&quot;Wrong number&quot;);
    return EXIT_FAILURE;
  }
  int first = atoi(argv[1]);
  int last = atoi(argv[2]);
  if((first &lt; 1) || (first &gt; last)) {
    bad_command_line_args(&quot;Bad range&quot;);
    return EXIT_FAILURE;
  }
  for(int i = first; i &lt;= last; ++i) {
    if(is_ugly(i)) printf(&quot;%d\n&quot;, i);
  }
  return EXIT_SUCCESS
}
</pre>
<p>I haven't supplied the code for <tt class=
"function">bad_command_line_args()</tt> but writing it should be
trivial, certainly for a student who wrote the code we are
critiquing. Note that this program is considerably shorter than the
original even though it does a great deal to trap errors. All the
code conforms to the C99 Standard though some, such as late
declarations does not conform to the older standard.</p>
<p>The interesting feature of the above code is that it uses less C
technology than the original yet, I hope you will agree, it is a
much better program. One of the arts of programming is to use
simple things well.</p>
</div>
</div>
<div class="sect1" lang="en">
<div class="titlepage">
<h2><a name="d0e953" id="d0e953"></a>Student Code
Critique 28</h2>
</div>
<p>(Submissions to <tt class="email">&lt;<a href=
"mailto:caabeiro@vodafone.es">caabeiro@vodafone.es</a>&gt;</tt> by
July 10th)</p>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e961" id="d0e961"></a>Program 1</h3>
</div>
<p><span class="emphasis"><em>I'm newbie to C++ and I would like to
know which would be the best (elegant and correct) solution for the
following small (string) read problem with gets.</em></span></p>
<pre class="programlisting">
#include &lt;iostream&gt;
using namespace std;
#include &lt;cstdio&gt;
main() {
  int n;
  int waste; // needs this to work
             // (read) properly!!
  char name[51];
  cout &lt;&lt; &quot;Enter any integer number...\n&quot;;
  cin &gt;&gt; n;
  cout &lt;&lt; &quot;Enter your name...\n&quot;;
  cin &gt;&gt; waste; // 'gets' does not read the
                // name without this line!!
  gets(name);
}
</pre>
<p>Mixing C and C++ functions doesn't seem the best way to write
this program. Please provide alternatives, taking also into account
its security implications.</p>
</div>
<div class="sect2" lang="en">
<div class="titlepage">
<h3><a name="d0e971" id="d0e971"></a>Program 2</h3>
</div>
<p><span class="emphasis"><em>If I enter 23 and 5 the answer should
be 23 * 5 = 115 my answer is off by five or whatever number 2 is. I
was told I am not including the first two numbers in the loop. I
thought when I cin the numbers it is including them. Does anyone
have any suggestions on how I can fix this?</em></span></p>
<pre class="programlisting">
#include&lt;iostream&gt;
#include&lt;iomanip&gt;
#include&lt;string&gt;

using namespace std;

int main()
{
  while (1) {
int num1, num2, total = 0;
cout&lt;&lt;&quot;Enter two numbers: &quot;;
cin&gt;&gt;num1&gt;&gt;num2;
while (num1 != 1)
cout&lt;&lt;setw(5)&lt;&lt;num1&lt;&lt;setw(5)&lt;&lt;num2&lt;&lt;endl;
  num1 /= 2;
  num2 *= 2;
  if (num1 % 2 != 0)
    total += num2;
}
  cout&lt;&lt;&quot;the total is &quot;&lt;&lt;total &lt;&lt;endl;
} //End While 1
return 0;
}
</pre>
<p>There are numerous errors in both the code and the student's
understanding. Please address these comprehensively.</p>
</div>
</div>
</p>
<p><strong>Notes:</strong>&nbsp;</p>
<p><em>More fields may be available via dynamicdata ..</em></p>
</div>
</channel>
</rss>
