Skip to content
Snippets Groups Projects
Commit 3864a048 authored by Goik Martin's avatar Goik Martin
Browse files

Tic-tac-toe HAL version, recursive programming factorial example

parent 8adbf696
No related branches found
No related tags found
No related merge requests found
Showing with 1078 additions and 23 deletions
File added
File added
File added
...@@ -261,6 +261,374 @@ ...@@ -261,6 +261,374 @@
</qandaset> </qandaset>
</section> </section>
<section xml:id="sd1SectTicTacToePart">
<title>Tic-tac-toe</title>
<section xml:id="sd1SectTicTacToeTwodimensional">
<title>Tic-tac-toe using a two-dimensional array</title>
<qandaset defaultlabel="qanda" xml:id="sd1QandaTicTacToeTwodimensional">
<qandadiv>
<qandaentry>
<question>
<para>This exercise exclusively deals with the visualization and
bookkeeping of two humans playing <link
xlink:href="https://en.wikipedia.org/wiki/Tic-tac-toe">Tic-tac-toe</link>
against each other. For the sake of clarification: It is not
about humans playing a computer. So you do not (yet) have to
implement an algorithm finding a player's best possible moves.
The following video shows the intended behaviour:</para>
<figure xml:id="sd1FigTicTacToe">
<title>Two Tic-tac-toe players fighting each other.</title>
<mediaobject>
<videoobject>
<videodata fileref="Ref/Video/tttEclipse.webm"/>
</videoobject>
</mediaobject>
</figure>
<para>Use a two-dimensional array to represent a game's
state:</para>
<programlisting language="java">final char[][] board = new char[3][3];</programlisting>
<para>Depending on your choice you may also use a class
<classname>Player</classname> containing additional information
like the player's name. In this case you'll probably need two
instances representing both players and in turn a 3 x 3 array
holding references to them:</para>
<programlisting language="java">final Player[][] board = new Player[3][3];</programlisting>
<para>Discovering a <quote>win</quote> situation will be an
essential part of this exercise. The following situations define
a <quote>win</quote> state:</para>
<glosslist>
<glossentry>
<glossterm>Row occupation</glossterm>
<glossdef>
<informaltable border="1">
<tr>
<td><programlisting language="none">xxx
...
...</programlisting></td>
<td><programlisting language="none">...
xxx
...</programlisting></td>
<td><programlisting language="none">...
...
xxx</programlisting></td>
</tr>
</informaltable>
</glossdef>
</glossentry>
</glosslist>
</question>
<answer>
<para>Consider the following Maven project:</para>
<annotation role="make">
<para role="eclipse">Sd1/TicTacToe/V1</para>
</annotation>
<para>This implementation already uses a so called
<code>enum</code> to be discussed later during an upcoming
lecture:</para>
<programlisting language="java">public enum Player {
PLAYER1("Jim", 'O'), PLAYER2("Eve", 'X');
public final String nickname;
public final char representation;
Player(final String nickname, final char representation) {
this.nickname = nickname;
this.representation = representation;
}
public Player getOtherPlayer() {
switch (this) {
case PLAYER1:
return PLAYER2;
case PLAYER2:
return PLAYER1;
default:
return null;
}
}
@Override
public String toString() {
return "" + representation;
}
}</programlisting>
<para>A <xref linkend="glo_Java"/> <code>enum</code> essentially
is a specialized class. If you don't like this yet you may
safely replace the given <code>enum</code> by the following
class:</para>
<programlisting language="java">public class Player {
final public static Player
PLAYER1 = new Player ("Jim", 'O'),
PLAYER2 = new Player("Eve", 'X');
public final String nickname;
public final char representation;
Player(final String nickname, final char representation) {
this.nickname = nickname;
this.representation = representation;
}
public Player getOtherPlayer() {
if (PLAYER1 == this) {
return PLAYER2;
} else if (PLAYER2 == this) {
return PLAYER1;
} else {
return null;
}
}
@Override
public String toString() {
return "" + representation;
}
}</programlisting>
<para>It is possible to wrap this solution into an executable
<xref linkend="glo_Jar"/> archive by adding:</para>
<programlisting language="none"> &lt;plugin&gt;
&lt;groupId&gt;org.apache.maven.plugins&lt;/groupId&gt;
&lt;artifactId&gt;maven-jar-plugin&lt;/artifactId&gt;
&lt;version&gt;2.6&lt;/version&gt;
&lt;configuration&gt;
&lt;archive&gt;
&lt;manifest&gt;
&lt;addClasspath&gt;true&lt;/addClasspath&gt;
&lt;!-- Class containing desired entry method public static void main(String[] args) --&gt;
&lt;mainClass&gt;de.hdm_stuttgart.mi.sd1.tictactoe.TicTacToe&lt;/mainClass&gt;
&lt;/manifest&gt;
&lt;/archive&gt;
&lt;/configuration&gt;
&lt;/plugin&gt;</programlisting>
<para>This allows for console execution rather than using
Eclipse:</para>
<programlisting language="none">goik@mi-ESPRIMO-P910 V1&gt; mvn install
[INFO] Scanning for projects...
...
-------------------------------------------------------
T E S T S
-------------------------------------------------------
Running de.hdm_stuttgart.mi.sd1.connectfour.AppTest
Tests run: 2, Failures: 0, Errors: 0, Skipped: 0, Time elapsed: 0.051 sec
Results :
Tests run: 2, Failures: 0, Errors: 0, Skipped: 0
[INFO]
<emphasis role="bold">[INFO] --- maven-jar-plugin:2.6:jar (default-jar) @ tictactoe ---
[INFO] Building jar: /ma/goik/workspace/GoikLectures/P/Sd1/TicTacToe/V1/target/tictactoe-0.9.jar
[INFO]
[INFO] --- maven-install-plugin:2.5.2:install (default-install) @ tictactoe ---
[INFO] Installing /ma/goik/workspace/GoikLectures/P/Sd1/TicTacToe/V1/target/tictactoe-0.9.jar to /ma/goik/.m2/repository/de/hdm-stuttgart/mi/sd1/tictactoe/0.9/tictactoe-0.9.jar
</emphasis>[INFO] Installing /ma/goik/workspace/GoikLectures/P/Sd1/TicTacToe/V1/pom.xml to /ma/goik/.m2/repository/de/hdm-stuttgart/mi/sd1/tictactoe/0.9/tictactoe-0.9.pom
[INFO] ------------------------------------------------------------------------
[INFO] BUILD SUCCESS
[INFO] ------------------------------------------------------------------------
[INFO] Total time: 2.242s
[INFO] Finished at: Wed Sep 23 12:54:34 CEST 2015
[INFO] Final Memory: 18M/196M
[INFO] ------------------------------------------------------------------------
</programlisting>
<para>As you can see this creates
<filename>/ma/goik/.m2/repository/de/hdm-stuttgart/mi/sd1/tictactoe/0.9/tictactoe-0.9.jar</filename>.
This may be executed similar to a <quote>true</quote> binary
executable:</para>
<programlisting language="none">goik@mi-ESPRIMO-P910 ~&gt; java -jar /ma/goik/.m2/.../tictactoe-0.9.jar
Numbering scheme:
0|1|2
-+-+-
3|4|5
-+-+-
6|7|8
Jim, please enter next field's number:</programlisting>
</answer>
</qandaentry>
</qandadiv>
</qandaset>
</section>
<section xml:id="sd1SectTicTacToeOnedimensional">
<title>Changing the game's internal representation</title>
<qandaset defaultlabel="qanda" xml:id="sd1QandaTicTacToeOnedimensional">
<qandadiv>
<qandaentry>
<question>
<para>This exercise aims at changing the subsequent items with
respect to the previous Tic-tac-toe solution:</para>
<glosslist>
<glossentry>
<glossterm>End user perspective</glossterm>
<glossdef>
<orderedlist>
<listitem>
<para>End users are used to count from 1 to 9 rather
than from 0 to 8. Consequently we should supply a
different hint regarding the fields' numbering
scheme:</para>
<informaltable border="1">
<tr>
<td><programlisting language="none">012
345
678</programlisting></td>
<td></td>
<td><programlisting language="none">123
456
789</programlisting></td>
</tr>
</informaltable>
</listitem>
<listitem>
<para>The two players should have a choice about who
is to start a game:</para>
<programlisting language="none">Numbering scheme:
1|2|3
-+-+-
4|5|6
-+-+-
7|8|9
Who is going to start? 0 = June, other = Bill
0
June, please enter next field's number:</programlisting>
</listitem>
<listitem>
<para>The numbering hints should appear
<quote>right</quote> to the current tic-tac-toe board
rather than on top of it. Furthermore only the
remaining free fields shall be on offer. In the next
example this restriction excludes position
<quote>4</quote>:</para>
<programlisting language="none">Player June(O)
vs. Bill(X) Free fields
| | 1|2|3
-+-+- -+-+-
O| | |5|6
-+-+- -+-+-
| | 7|8|9
Bill, please enter next field's number:</programlisting>
</listitem>
</orderedlist>
</glossdef>
</glossentry>
</glosslist>
</question>
<answer>
<annotation role="make">
<para role="eclipse">Sd1/TicTacToe/V2</para>
</annotation>
</answer>
</qandaentry>
</qandadiv>
</qandaset>
</section>
<section xml:id="sd1SectTicTacToeComputerVsHuman">
<title>Tic-tac-toe, Computer vs. human</title>
<qandaset defaultlabel="qanda" xml:id="sd1QandaTicTacToeComputerVsHuman">
<qandadiv>
<qandaentry>
<question>
<para>This exercise allows a human playing tic-tac-toe against a
computer. It is intended four those course members who are
looking for a more challenging problem:</para>
<figure xml:id="sd1FigTicTacToeHumanVsComputer">
<title>Two Tic-tac-toe players fighting each other.</title>
<mediaobject>
<videoobject>
<videodata fileref="Ref/Video/tttHumanVsComputer.webm"/>
</videoobject>
</mediaobject>
</figure>
<para>The underlying logic is considerately more difficult to
implement and requires recursion as being introduced in <xref
linkend="sd1SectFactorialRecursive"/>. You may want to
read:</para>
<itemizedlist>
<listitem>
<para><link
xlink:href="http://web.stanford.edu/~msirota/soco/minimax.html">Strategies
and tactics for intelligent search</link></para>
</listitem>
<listitem>
<para><link
xlink:href="http://www.flyingmachinestudios.com/programming/minimax">An
Exhaustive Explanation of Minimax, a Staple AI
Algorithm</link></para>
</listitem>
<listitem>
<para><link
xlink:href="http://neverstopbuilding.com/minimax">Tic Tac
Toe: Understanding The Minimax Algorithm</link></para>
</listitem>
</itemizedlist>
</question>
<answer>
<annotation role="make">
<para role="eclipse">Sd1/TicTacToe/V4</para>
</annotation>
</answer>
</qandaentry>
</qandadiv>
</qandaset>
</section>
</section>
<section xml:id="sd1SummingUpValues"> <section xml:id="sd1SummingUpValues">
<title>Summing up values</title> <title>Summing up values</title>
......
...@@ -1518,7 +1518,7 @@ Is 2016 a leap year? true</programlisting> ...@@ -1518,7 +1518,7 @@ Is 2016 a leap year? true</programlisting>
} }
}</programlisting> }</programlisting>
<para>Re-implement the above code two times as:</para> <para>Re-implement the above code in two different ways:</para>
<orderedlist> <orderedlist>
<listitem> <listitem>
...@@ -2530,9 +2530,12 @@ long sum = (long)a + b;</programlisting> ...@@ -2530,9 +2530,12 @@ long sum = (long)a + b;</programlisting>
<qandadiv> <qandadiv>
<qandaentry> <qandaentry>
<question> <question>
<para>Implement two class methods double abs(double) and double <para>Implement a class method methods <methodname>double
max(double, double, double) in a class math living in a package abs(double)</methodname> and two overloaded methods
of your choice:</para> <methodname>double max(double, double)</methodname> and
<methodname>double max(double, double, double)</methodname> in a
class <classname>Math</classname> living in a package of your
choice:</para>
<programlisting language="java">package de.hdm_stuttgart.de.sd1.math; <programlisting language="java">package de.hdm_stuttgart.de.sd1.math;
...@@ -2573,7 +2576,7 @@ public class Math { ...@@ -2573,7 +2576,7 @@ public class Math {
} }
}</programlisting> }</programlisting>
<para>Test these functions using appropriate data.</para> <para>Provide at at least 8 unit tests.</para>
</question> </question>
<answer> <answer>
...@@ -2589,6 +2592,563 @@ public class Math { ...@@ -2589,6 +2592,563 @@ public class Math {
</qandadiv> </qandadiv>
</qandaset> </qandaset>
<section xml:id="sd1SectFactorialDirect">
<title>Factorial, the direct way</title>
<qandaset defaultlabel="qanda" xml:id="sd1QandaFactorialDirect">
<qandadiv>
<qandaentry>
<question>
<para>Compute the factorial of a given integer value:</para>
<informalequation>
<m:math display="block">
<m:mrow>
<m:mrow>
<m:mi>4</m:mi>
<m:mo>!</m:mo>
</m:mrow>
<m:mo>=</m:mo>
<m:mrow>
<m:mi>4</m:mi>
<m:mo>×</m:mo>
<m:mi>3</m:mi>
<m:mo>×</m:mo>
<m:mi>2</m:mi>
<m:mo>×</m:mo>
<m:mi>1</m:mi>
</m:mrow>
</m:mrow>
</m:math>
</informalequation>
<para>Implement the following method:</para>
<programlisting language="java"> /**
* Computing the factorial of a given argument.
*
* @param n
* Zero or any positive integer
*
* @return
* The product 1 x 2 x 3 x ... x n or 1 in case of n == 0.
* In case of an arithmetic overflow a value of {@link Long#MAX_VALUE} is being returned.
*/
static public long factorial(int n) {
// TODO: implement me!
}</programlisting>
<orderedlist>
<listitem>
<para>The method's signature looks slightly weird: It does
expect an argument of type <code>int</code> but returns a
<code>long</code> value. Explain the underlying
ratio.</para>
</listitem>
<listitem>
<para>Mind the above <xref linkend="glo_Javadoc"/> passage
concerning integer overflow related problems with respect
to your own implementation.</para>
</listitem>
<listitem>
<para>Provide adequate unit tests. Do not forget special
values and handling of arithmetic overflow
problems.</para>
</listitem>
</orderedlist>
</question>
<answer>
<annotation role="make">
<para role="eclipse">Sd1/math/V0_7</para>
</annotation>
<para>We address all three questions individually:</para>
<orderedlist>
<listitem>
<para>Returning a long is sensible since even small
argument values in return yield large factorials.
<code>long</code> is the best (largest) choice among the
<xref linkend="glo_Java"/> built-in integer types.
Consider the following example code:</para>
<programlisting language="java"> public static void main(String[] args) {
System.out.println("Max long value:" + Long.MAX_VALUE + "\n");
for (int i = 15; i &lt; 23; i++) {
System.out.println(i + ":" + factorial(i));
}
}
static public long factorial(int n) {
long ret = 1;
for (int i = n; 1 &lt; i; i--) {
ret *= i;
}
return ret;
}</programlisting>
<para>This yields:</para>
<programlisting language="none">Max long value:9223372036854775807
15:1307674368000
16:20922789888000
17:355687428096000
18:6402373705728000
19:121645100408832000
20:2432902008176640000
21:-4249290049419214848
22:-1250660718674968576</programlisting>
<para>So starting from <inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>21</m:mi>
<m:mo>!</m:mo>
</m:mrow>
</m:math>
</inlineequation> we already see <code>long</code>
overflow related errors. Thus allowing for even larger
<code>long</code> arguments instead of <code>int</code>
does not make sense at all.</para>
<para>Since <quote>21</quote> is pretty small we might
favour <code>short</code> (or even <code>char</code>) as
argument type:</para>
<programlisting language="java">static public long factorial(short n) { ... }</programlisting>
<para>This however is a bad idea: Even simple expressions
would be flagged as compile time errors since both integer
literals and arithmetic expressions in <xref
linkend="glo_Java"/> evaluate to the data type
<code>int</code>:</para>
<programlisting language="java">// Compile time error:
// The method factorial(short) in the type
// App is not applicable for the arguments (int)
System.out.println(factorial(3));</programlisting>
<para>BTW: If we choose <methodname>static public int
factorial(short n)</methodname> (int return type) the
first overflow error happens already when trying to
calculate <inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>13</m:mi>
<m:mo>!</m:mo>
</m:mrow>
</m:math>
</inlineequation>.</para>
</listitem>
<listitem>
<para>We have to handle:</para>
<itemizedlist>
<listitem>
<para>Argument value 0.</para>
</listitem>
<listitem>
<para>Overflow related results.</para>
</listitem>
</itemizedlist>
</listitem>
<listitem>
<para>Tests must address regular, special and overflow
related argument values.</para>
</listitem>
</orderedlist>
</answer>
</qandaentry>
</qandadiv>
</qandaset>
</section>
<section xml:id="sd1SectFactorialRecursive">
<title>Factorial, the recursive way</title>
<qandaset defaultlabel="qanda" xml:id="sd1QandaFactorialRecursive">
<qandadiv>
<qandaentry>
<question>
<para>We introduce a second strategy calculating a given
argument's factorial by introducing recursive methods.
Recursive programming is also a prerequisite for the later
<link linkend="sd1SectTicTacToeComputerVsHuman">tic-tac-toe
strategy exercise</link>.</para>
<para>Recursive methods will call themselves. Recursive
methods typically have:</para>
<orderedlist>
<listitem>
<para>A recursive expression reducing a problem step by
step.</para>
</listitem>
<listitem>
<para>A termination condition.</para>
</listitem>
</orderedlist>
<para>With respect to calculating factorials the former may be
expresses as:</para>
<glosslist>
<glossentry>
<glossterm>Reducing statement</glossterm>
<glossdef>
<para><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>n</m:mi>
<m:mo>!</m:mo>
<m:mo>=</m:mo>
<m:mrow>
<m:mi>n</m:mi>
<m:mo></m:mo>
<m:mrow>
<m:mo>(</m:mo>
<m:mrow>
<m:mi>n</m:mi>
<m:mo>-</m:mo>
<m:mi>1</m:mi>
</m:mrow>
<m:mo>)</m:mo>
</m:mrow>
</m:mrow>
</m:mrow>
</m:math>
</inlineequation> .</para>
</glossdef>
</glossentry>
<glossentry>
<glossterm>Termination condition</glossterm>
<glossdef>
<para><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mrow>
<m:mi>0</m:mi>
<m:mo>!</m:mo>
</m:mrow>
<m:mo>=</m:mo>
<m:mi>1</m:mi>
</m:mrow>
</m:math>
</inlineequation>.</para>
</glossdef>
</glossentry>
</glosslist>
<para>This allows for calculating e.g. 4! in a recursive
fashion:</para>
<informaltable border="1">
<tr>
<td><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>4</m:mi>
<m:mo>!</m:mo>
</m:mrow>
</m:math>
</inlineequation></td>
<td><inlineequation>
<m:math display="inline">
<m:mo>=</m:mo>
</m:math>
</inlineequation></td>
<td><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>4</m:mi>
<m:mo>×</m:mo>
<m:mrow>
<m:mrow>
<m:mo>(</m:mo>
<m:mrow>
<m:mi>4</m:mi>
<m:mo>-</m:mo>
<m:mi>1</m:mi>
</m:mrow>
<m:mo>)</m:mo>
</m:mrow>
<m:mo>!</m:mo>
</m:mrow>
</m:mrow>
</m:math>
</inlineequation></td>
<td>Recursion 4 - &gt; 3</td>
</tr>
<tr>
<td/>
<td><inlineequation>
<m:math display="inline">
<m:mo>=</m:mo>
</m:math>
</inlineequation></td>
<td><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>4</m:mi>
<m:mo>×</m:mo>
<m:mi>3</m:mi>
<m:mo>×</m:mo>
<m:mrow>
<m:mrow>
<m:mo>(</m:mo>
<m:mrow>
<m:mi>3</m:mi>
<m:mo>-</m:mo>
<m:mi>1</m:mi>
</m:mrow>
<m:mo>)</m:mo>
</m:mrow>
<m:mo>!</m:mo>
</m:mrow>
</m:mrow>
</m:math>
</inlineequation></td>
<td>Recursion 3 -&gt; 2</td>
</tr>
<tr>
<td/>
<td><inlineequation>
<m:math display="inline">
<m:mo>=</m:mo>
</m:math>
</inlineequation></td>
<td><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>4</m:mi>
<m:mo>×</m:mo>
<m:mi>3</m:mi>
<m:mo>×</m:mo>
<m:mi>2</m:mi>
<m:mo>×</m:mo>
<m:mrow>
<m:mrow>
<m:mo>(</m:mo>
<m:mrow>
<m:mi>2</m:mi>
<m:mo>-</m:mo>
<m:mi>1</m:mi>
</m:mrow>
<m:mo>)</m:mo>
</m:mrow>
<m:mo>!</m:mo>
</m:mrow>
</m:mrow>
</m:math>
</inlineequation></td>
<td>Recursion 2 -&gt; 1</td>
</tr>
<tr>
<td/>
<td><inlineequation>
<m:math display="inline">
<m:mo>=</m:mo>
</m:math>
</inlineequation></td>
<td><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>4</m:mi>
<m:mo>×</m:mo>
<m:mi>3</m:mi>
<m:mo>×</m:mo>
<m:mi>2</m:mi>
<m:mo>×</m:mo>
<m:mi>1</m:mi>
<m:mo>×</m:mo>
<m:mrow>
<m:mrow>
<m:mo>(</m:mo>
<m:mrow>
<m:mi>1</m:mi>
<m:mo>-</m:mo>
<m:mi>1</m:mi>
</m:mrow>
<m:mo>)</m:mo>
</m:mrow>
<m:mo>!</m:mo>
</m:mrow>
</m:mrow>
</m:math>
</inlineequation></td>
<td>Recursion 1 -&gt; 0</td>
</tr>
<tr>
<td/>
<td><inlineequation>
<m:math display="inline">
<m:mo>=</m:mo>
</m:math>
</inlineequation></td>
<td><inlineequation>
<m:math display="inline">
<m:mrow>
<m:mi>4</m:mi>
<m:mo>×</m:mo>
<m:mi>3</m:mi>
<m:mo>×</m:mo>
<m:mi>2</m:mi>
<m:mo>×</m:mo>
<m:mi>1</m:mi>
<m:mo>×</m:mo>
<m:mi>1</m:mi>
</m:mrow>
</m:math>
</inlineequation></td>
<td>Termination condition <inlineequation>
<m:math display="inline">
<m:mrow>
<m:mrow>
<m:mi>0</m:mi>
<m:mo>!</m:mo>
</m:mrow>
<m:mo>=</m:mo>
<m:mi>1</m:mi>
</m:mrow>
</m:math>
</inlineequation>.</td>
</tr>
</informaltable>
<para>Use the above scheme for implementing a second method
<methodname>static public long factorialRecurse(int
n)</methodname>. The implementation should only use recursion
and termination conditions but no kind of loops whatsoever.
You may disregard the arithmetic overflow problem.</para>
<para>BTW: The concept of recursion in computer science is
closely related to the <link
xlink:href="https://en.wikipedia.org/wiki/Mathematical_induction">mathematical
concept of induction</link>.</para>
</question>
<answer>
<para>The implementation is surprisingly simple:</para>
<programlisting language="java"> static public long factorialRecurse(int n) {
if (0 == n) {
return 1; // Termination condition
} else {
return n * factorialRecurse(n - 1); // Reducing step: n! = n * (n - 1)!
}</programlisting>
</answer>
</qandaentry>
</qandadiv>
</qandaset>
</section>
<section xml:id="sd1SecExp"> <section xml:id="sd1SecExp">
<title>Implementing exponentials.</title> <title>Implementing exponentials.</title>
......
...@@ -21,23 +21,6 @@ ...@@ -21,23 +21,6 @@
<build> <build>
<plugins> <plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.1</version>
<configuration>
<source>1.8</source>
<target>1.8</target>
</configuration>
</plugin>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-javadoc-plugin</artifactId>
<version>2.10.1</version>
<configuration/>
</plugin>
<plugin> <plugin>
<groupId>org.apache.maven.plugins</groupId> <groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-jar-plugin</artifactId> <artifactId>maven-jar-plugin</artifactId>
...@@ -46,6 +29,7 @@ ...@@ -46,6 +29,7 @@
<archive> <archive>
<manifest> <manifest>
<addClasspath>true</addClasspath> <addClasspath>true</addClasspath>
<!-- Class containing desired entry method public static void main(String[] args) -->
<mainClass>de.hdm_stuttgart.mi.sd1.tictactoe.TicTacToe</mainClass> <mainClass>de.hdm_stuttgart.mi.sd1.tictactoe.TicTacToe</mainClass>
</manifest> </manifest>
</archive> </archive>
......
...@@ -2,7 +2,7 @@ package de.hdm_stuttgart.mi.sd1.tictactoe; ...@@ -2,7 +2,7 @@ package de.hdm_stuttgart.mi.sd1.tictactoe;
public enum Player { public enum Player {
YOU("You", 'O', 1), COM("Me (computer)", 'X', -1); YOU("You", 'O', 1), COM("Me (HAL 9000)", 'X', -1);
public final String nickname; public final String nickname;
public final char representation; public final char representation;
......
/.settings
/target
/.classpath
/.project
/A1.log
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>de.hdm-stuttgart.mi</groupId>
<artifactId>lecturenotes-pom</artifactId>
<version>1.0</version>
<relativePath>../../../pom.xml</relativePath>
</parent>
<groupId>de.hdm-stuttgart.de.sd1</groupId>
<artifactId>math</artifactId>
<version>0.7</version>
<packaging>jar</packaging>
<name>math_v0.7</name>
<url>http://www.mi.hdm-stuttgart.de/freedocs</url>
</project>
package de.hdm_stuttgart.de.sd1.math;
/**
* Testing
*
*/
public class Driver {
/**
* @param args Unused
*/
public static void main(String[] args) {
System.out.println(Math.factorial(20));
System.out.println(Math.factorialRecurse(20));
}
}
package de.hdm_stuttgart.de.sd1.math;
/**
* Computing the factorial.
*/
public class Math {
/**
* Computing the factorial of a given argument.
*
* @param n
* Zero or any positive integer
*
* @return
* The product 1 x 2 x 3 x ... x n or 1 in case of n == 0.
* In case of an arithmetic overflow a value of {@link Long#MAX_VALUE} is being returned.
*/
static public long factorial(int n) {
long ret = 1;
for (int i = n; 1 < i; i--) {
// Alternate use of exceptions see related discussion in
// http://stackoverflow.com/questions/1657834/how-can-i-check-if-multiplying-two-numbers-in-java-will-cause-an-overflow
if (i < Long.MAX_VALUE / ret ) {// Expecting overflow??
ret *= i;
} else {
return Long.MAX_VALUE; // Multiplication overflow error
}
}
return ret;
}
/**
* Computing the factorial of a given argument.
*
* @param n
* Zero or any positive integer
*
* @return
* The product 1 x 2 x 3 x ... x n or 1 in case of n == 0.
* In case of an arithmetic overflow a value of {@link Long#MAX_VALUE} is being returned.
*/
static public long factorialRecurse(int n) {
if (0 == n) {
return 1; // Termination condition
} else {
return n * factorialRecurse(n - 1); // Reducing step: n! = n * (n - 1)!
}
}
}
package de.hdm_stuttgart.de.sd1.math;
import org.junit.Assert;
import org.junit.Test;
/**
* Testing factorial implementation
*
*/
public class MaxFactorialTest{
/**
* Handling zero argument.
*/
@Test
public void testZero() {
Assert.assertEquals(1, Math.factorial(0));
}
@Test
public void testOne() {
Assert.assertEquals(1, Math.factorial(1));
}
@Test
public void testTwo() {
Assert.assertEquals(2, Math.factorial(2));
}
@Test
public void testThree() {
Assert.assertEquals(6, Math.factorial(3));
}
@Test
public void testSix() {
Assert.assertEquals(720, Math.factorial(6));
}
@Test
public void testOverflowLimit() {
Assert.assertTrue(Long.MAX_VALUE > Math.factorial(20));
Assert.assertEquals(Long.MAX_VALUE, Math.factorial(21));
}
}
...@@ -68,6 +68,7 @@ ...@@ -68,6 +68,7 @@
<module>Sd1/Marks/Solution2</module> <module>Sd1/Marks/Solution2</module>
<module>Sd1/math/V0_5</module> <module>Sd1/math/V0_5</module>
<module>Sd1/math/V0_7</module>
<module>Sd1/math/V1</module> <module>Sd1/math/V1</module>
<module>Sd1/math/V2</module> <module>Sd1/math/V2</module>
<module>Sd1/math/V3</module> <module>Sd1/math/V3</module>
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment