(*^
::[ Information =
"This is a Mathematica Notebook file. It contains ASCII text, and can be
transferred by email, ftp, or other text-file transfer utility. It should
be read or edited using a copy of Mathematica or MathReader. If you
received this as email, use your mail application or copy/paste to save
everything from the line containing (*^ down to the line containing ^*)
into a plain text file. On some systems you may have to give the file a
name ending with ".ma" to allow Mathematica to recognize it as a Notebook.
The line below identifies what version of Mathematica created this file,
but it can be opened using any other version as well.";
FrontEndVersion = "NeXT Mathematica Notebook Front End Version 2.2";
NeXTStandardFontEncoding;
fontset = title, inactive, noPageBreakBelow, noPageBreakInGroup, nohscroll, preserveAspect, groupLikeTitle, center, M7, bold, L1, e8, 24, "Times"; ;
fontset = subtitle, inactive, noPageBreakBelow, noPageBreakInGroup, nohscroll, preserveAspect, groupLikeTitle, center, M7, bold, L1, e6, 18, "Times"; ;
fontset = subsubtitle, inactive, noPageBreakBelow, noPageBreakInGroup, nohscroll, preserveAspect, groupLikeTitle, center, M7, italic, L1, e6, 14, "Times"; ;
fontset = section, inactive, noPageBreakBelow, nohscroll, preserveAspect, groupLikeSection, grayBox, M22, bold, L1, a20, 18, "Times"; ;
fontset = subsection, inactive, noPageBreakBelow, nohscroll, preserveAspect, groupLikeSection, blackBox, M19, bold, L1, a15, 14, "Times"; ;
fontset = subsubsection, inactive, noPageBreakBelow, nohscroll, preserveAspect, groupLikeSection, whiteBox, M18, bold, L1, a12, 12, "Times"; ;
fontset = text, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = smalltext, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 10, "Times"; ;
fontset = input, noPageBreakInGroup, nowordwrap, preserveAspect, groupLikeInput, M42, N23, bold, L1, 12, "Courier"; ;
fontset = output, output, inactive, noPageBreakInGroup, nowordwrap, preserveAspect, groupLikeOutput, M42, N23, L-5, 12, "Courier"; ;
fontset = message, inactive, noPageBreakInGroup, nowordwrap, preserveAspect, groupLikeOutput, M42, N23, L1, 12, "Courier"; ;
fontset = print, inactive, noPageBreakInGroup, nowordwrap, preserveAspect, groupLikeOutput, M42, N23, L1, 12, "Courier"; ;
fontset = info, inactive, noPageBreakInGroup, nowordwrap, preserveAspect, groupLikeOutput, M42, N23, L1, 12, "Courier"; ;
fontset = postscript, PostScript, formatAsPostScript, output, inactive, noPageBreakInGroup, nowordwrap, preserveAspect, groupLikeGraphics, M7, l34, w282, h287, L1, 12, "Courier"; ;
fontset = name, inactive, noPageBreakInGroup, nohscroll, preserveAspect, M7, italic, B65535, L1, 10, "Times"; ;
fontset = header, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, italic, L1, 12, "Times"; ;
fontset = leftheader, 12;
fontset = footer, inactive, nohscroll, noKeepOnOnePage, preserveAspect, center, M7, italic, L1, 12, "Times"; ;
fontset = leftfooter, 12;
fontset = help, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = clipboard, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = completions, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12, "Courier"; ;
fontset = special1, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = special2, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = special3, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = special4, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
fontset = special5, inactive, nohscroll, noKeepOnOnePage, preserveAspect, M7, L1, 12;
showRuler; automaticGrouping; currentKernel;
]
:[font = title; inactive; preserveAspect; startGroup]
Two Rectangles are Constructable with Tangrams:
An Enumeration Proof using Mathematica
:[font = subtitle; inactive; preserveAspect]
Mathematica in Education
Vol.2 No.4
(October 1993)
;[s]
2:0,0;24,1;52,-1;
2:1,17,13,Times,3,18,0,0,0;1,16,12,Times,1,18,0,0,0;
:[font = subsubtitle; inactive; preserveAspect]
by
Joseph Sloan
Department of Mathematics and Computer Science
Lander University
joeslon@hubcap.clemson.edu
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
Introduction
:[font = text; inactive; preserveAspect]
An enumeration proof is a proof that generates and then
analyzes all possible cases for a problem or some aspect of
a problem. If the number of cases is large, computer
assistance becomes indispensible. This paper gives an
example of a proof by enumeration using Mathematica.
:[font = text; inactive; preserveAspect]
Perhaps the best example of a computer generated enumeration
proof is the solution to the four-color map problem by Appel
and Haken [1976]. They demonstrated that four colors are
sufficient to color any planar map so that no countries
sharing a border will share the same color. The technique
for the proof was suggested by A. B. Kempe in 1879. But,
because of the large number of cases that needed to be
considered, the actual proof did not appear until 1976.
:[font = text; inactive; preserveAspect; endGroup]
While worthy of study, the proof is too complex for
students to attempt replicating it. The Appel and Haken
proof would have taken 300 hours of CPU time on a
supercomputer of that era. (Lacking access to such a
machine, it took closer to 1200 hours [Kolata, 1976].)
Fortunately, there are other enumeration proofs accessible
to students. Such a proof, based on tangrams and using
Mathematica, is given here.
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
The problem
:[font = text; inactive; preserveAspect]
A tangram is an ancient oriental puzzle obtained by cutting
a square into seven pieces [Gardner, 1976a--c]. (See
Figure 1.) The pieces are a square, a parallelogram, two
small triangles, a medium triangle, and two large triangles.
The object of the puzzle is to assemble these pieces into
various figures, most typically, the original square. (See
Figure 2.) It is also possible to construct a second
rectangle that is twice as long as it is tall. (See
Figure 3.) But can other rectangles be constructed? None
have been found, but how can we be sure?
:[font = postscript; PostScript; formatAsPostScript; output; inactive; Cclosed; pageBreak; preserveAspect; pictureLeft = 0; pictureWidth = 207; pictureHeight = 300; startGroup]
%!
%%Creator: Mathematica
%%AspectRatio: 1.44772
MathPictureStart
%% Graphics
/Courier findfont 10 scalefont setfont
% Scaling calculations
0.0238095 0.185964 0.0344694 0.185964 [
[ 0 0 0 0 ]
[ 1 1.44772 0 0 ]
] MathScale
% Start of Graphics
1 setlinecap
1 setlinejoin
newpath
[ ] 0 setdash
0 g
p
P
0 0 m
1 0 L
1 1.44772 L
0 1.44772 L
closepath
clip
newpath
p
.008 w
.02381 1.22728 m
.20977 1.22728 L
.20977 1.41325 L
.02381 1.41325 L
.02381 1.22728 L
s
.39574 1.22728 m
.5817 1.22728 L
.39574 1.41325 L
.39574 1.22728 L
s
.76767 1.22728 m
.95363 1.22728 L
.76767 1.41325 L
.76767 1.22728 L
s
.02381 .77833 m
.2868 .77833 L
.02381 1.04132 L
.02381 .77833 L
s
.7132 .77833 m
.97619 .77833 L
.84469 .90982 L
.5817 .90982 L
.7132 .77833 L
s
.02381 .22043 m
.39574 .22043 L
.02381 .59236 L
.02381 .22043 L
s
.5817 .22043 m
.95363 .22043 L
.5817 .59236 L
.5817 .22043 L
s
p
/Times-Bold findfont 10 scalefont setfont
[(Figure 1: Tangram Pieces)] .02381 .12745 -1 0 Mshowa
P
P
% End of Graphics
MathPictureEnd
:[font = postscript; PostScript; formatAsPostScript; output; inactive; preserveAspect; pictureLeft = 100; pictureWidth = 240; pictureHeight = 300]
%!
%%Creator: Mathematica
%%AspectRatio: 1.25
MathPictureStart
%% Graphics
/Courier findfont 10 scalefont setfont
% Scaling calculations
0.0238095 0.238095 0.0297619 0.238095 [
[ 0 0 0 0 ]
[ 1 1.25 0 0 ]
] MathScale
% Start of Graphics
1 setlinecap
1 setlinejoin
newpath
[ ] 0 setdash
0 g
p
P
0 0 m
1 0 L
1 1.25 L
0 1.25 L
closepath
clip
newpath
p
.008 w
.02381 .26786 m
.5 .74405 L
.02381 1.22024 L
.02381 .26786 L
s
.02381 .26786 m
.97619 .26786 L
.5 .74405 L
s
.2619 .98214 m
.7381 .98214 L
.5 1.22024 L
.02381 1.22024 L
s
.5 .74405 m
.7381 .98214 L
s
.7381 .50595 m
.97619 .74405 L
.7381 .98214 L
s
.97619 .26786 m
.97619 .74405 L
s
.97619 .74405 m
.97619 1.22024 L
.5 1.22024 L
s
p
/Times-Bold findfont 10 scalefont setfont
[(Figure 2: Original Square)] .02381 .14881 -1 0 Mshowa
P
P
% End of Graphics
MathPictureEnd
:[font = postscript; PostScript; formatAsPostScript; output; inactive; preserveAspect; pictureLeft = 97; pictureWidth = 300; pictureHeight = 225; endGroup]
%!
%%Creator: Mathematica
%%AspectRatio: .75
MathPictureStart
%% Graphics
/Courier findfont 10 scalefont setfont
% Scaling calculations
0.0238095 0.238095 0.0178571 0.238095 [
[ 0 0 0 0 ]
[ 1 .75 0 0 ]
] MathScale
% Start of Graphics
1 setlinecap
1 setlinejoin
newpath
[ ] 0 setdash
0 g
p
P
0 0 m
1 0 L
1 .75 L
0 .75 L
closepath
clip
newpath
p
.006 w
.02381 .25595 m
.2619 .49405 L
.2619 .73214 L
.02381 .49405 L
.02381 .25595 L
s
.02381 .49405 m
.2619 .73214 L
.02381 .73214 L
.02381 .49405 L
s
.02381 .25595 m
.5 .25595 L
.2619 .49405 L
.02381 .25595 L
s
.2619 .49405 m
.5 .25595 L
.5 .49405 L
.2619 .49405 L
s
.2619 .49405 m
.5 .49405 L
.5 .73214 L
.2619 .73214 L
.2619 .49405 L
s
.5 .25595 m
.97619 .73214 L
.5 .73214 L
.5 .25595 L
s
.5 .25595 m
.97619 .25595 L
.97619 .73214 L
.5 .25595 L
s
p
/Times-Bold findfont 10 scalefont setfont
[(Figure 3: Second Rectangle)] .02381 .1369 -1 0 Mshowa
P
P
% End of Graphics
MathPictureEnd
:[font = text; inactive; preserveAspect; endGroup]
We will demonstrate that these are the only two rectangles
that can be constructed. Our general approach is to
1) list the lengths of all possible sides with which a
rectangle can be constructed,
2) find those combinations that give the correct area, and,
3) analyze each of these rectangles individually.
Because of the number of combinations, this would be too
tedious and error prone for a manual approach.
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
The Proof
:[font = text; inactive; preserveAspect]
We begin by examining the pieces. If we take the edge of
the square piece as our basic unit of length, we can specify
the dimensions of the other pieces in terms of this unit.
The square is 1 by 1, of course. The parallelogram has
adjacent edges of 1 and Sqrt[2] separated by a 45 degree
angle. All five triangles are isosceles. The two small
triangles have legs of 1 and hypotenuses of Sqrt[2]. The
medium triangle has legs of Sqrt[2] and a hypotenuse of 2.
The two large triangles have legs of 2 and hypotenuses of
2 Sqrt[2]. Observe that the edges fall into two disjoint
sets---integers and integer multiples of Sqrt[2], that the
total area of the pieces is 8 square units, and that the
total perimeter for all the pieces is 20 + 10 Sqrt[2].
:[font = text; inactive; preserveAspect]
Next, we construct a list of all possible edge combinations
that can be used as a side for a rectangle. Since pieces
cannot overlap, each side of a rectangle must be formed by
joining the edges of individual tangram pieces end-to-end.
:[font = text; inactive; preserveAspect]
We assign to the variable Pieces a list composed of the lists
of edges of each tangram piece. Thus, the side of our
rectangle is constructed by using one value from each piece
(each inner list). We include 0 in each list since a piece
may not be used.
:[font = input; preserveAspect]
Pieces =
{{0, 1, 1, Sqrt[2]}, (* small triangle *)
{0, 1, 1, Sqrt[2]}, (* second small triangle *)
{0, 1, 1, 1, 1}, (* square *)
{0, 1, Sqrt[2], 1, Sqrt[2]}, (* parallelogram *)
{0, Sqrt[2], Sqrt[2], 2} , (* medium triangle *)
{0, 2, 2, 2 Sqrt[2]}, (* large triangle *)
{0, 2, 2, 2 Sqrt[2]}}; (* second large triangle *)
:[font = text; inactive; preserveAspect]
Next, we construct a list of all possible sums obtained by
taking one value from each of the inner lists. This new
list gives the lengths of all the possible ways we can line
up edges of our tangram pieces to form the side of a
rectangle.
:[font = text; inactive; preserveAspect]
This will be clearer if we first consider just two pieces.
Let P1 and P2 be a small triangle and a large triangle
respectively.
:[font = input; preserveAspect]
P1 = {0,1, 1, Sqrt[2]};
P2 = {0,2, 2, 2 Sqrt[2]};
:[font = text; inactive; preserveAspect]
Outer can be used to construct a list of all possible
combinations drawing one element from each.
:[font = input; Cclosed; preserveAspect; startGroup]
Data1 = Flatten[Outer[List, P1, P2],1]
:[font = output; output; inactive; preserveAspect; endGroup]
{{0, 0}, {0, 2}, {0, 2}, {0, 2*2^(1/2)}, {1, 0},
{1, 2}, {1, 2}, {1, 2*2^(1/2)}, {1, 0}, {1, 2},
{1, 2}, {1, 2*2^(1/2)}, {2^(1/2), 0}, {2^(1/2), 2},
{2^(1/2), 2}, {2^(1/2), 2*2^(1/2)}}
;[o]
{{0, 0}, {0, 2}, {0, 2}, {0, 2 Sqrt[2]}, {1, 0},
{1, 2}, {1, 2}, {1, 2 Sqrt[2]}, {1, 0}, {1, 2},
{1, 2}, {1, 2 Sqrt[2]}, {Sqrt[2], 0}, {Sqrt[2], 2},
{Sqrt[2], 2}, {Sqrt[2], 2 Sqrt[2]}}
:[font = text; inactive; preserveAspect]
We apply Plus to obtain the lengths for the various
combinations.
:[font = input; Cclosed; preserveAspect; startGroup]
Data2 = Apply[Plus, Data1, {1}]
:[font = output; output; inactive; preserveAspect; endGroup]
{0, 2, 2, 2*2^(1/2), 1, 3, 3, 1 + 2*2^(1/2), 1, 3, 3,
1 + 2*2^(1/2), 2^(1/2), 2 + 2^(1/2), 2 + 2^(1/2),
3*2^(1/2)}
;[o]
{0, 2, 2, 2 Sqrt[2], 1, 3, 3, 1 + 2 Sqrt[2], 1, 3, 3,
1 + 2 Sqrt[2], Sqrt[2], 2 + Sqrt[2], 2 + Sqrt[2],
3 Sqrt[2]}
:[font = text; inactive; preserveAspect]
Finally,Union is used next to eliminate duplicates and sort
the data.
:[font = input; Cclosed; preserveAspect; startGroup]
Data3 = Union[Data2]
:[font = output; output; inactive; preserveAspect; endGroup]
{0, 1, 2, 3, 2^(1/2), 2*2^(1/2), 3*2^(1/2),
2 + 2^(1/2), 1 + 2*2^(1/2)}
;[o]
{0, 1, 2, 3, Sqrt[2], 2 Sqrt[2], 3 Sqrt[2],
2 + Sqrt[2], 1 + 2 Sqrt[2]}
:[font = text; inactive; preserveAspect]
Thus, there are nine possible ways to line up edges from
these two pieces to form sides for a rectangle counting
those cases where one or both pieces are omitted.
:[font = text; inactive; preserveAspect]
The function FindCombinations combines these operations.
:[font = input; preserveAspect]
FindCombinations[Lst1_List, Lst2_List] :=
Union[
Apply[Plus, Flatten[Outer[List, Lst1, Lst2], 1], {1}]]
:[font = text; inactive; preserveAspect]
We use a For loop to iterate over all seven tangram pieces.
:[font = input; preserveAspect]
For[Data=Pieces[[1]]; i=2,
i<=7,
i++,
Data = FindCombinations[Data, Pieces[[i]]]]
:[font = input; Cclosed; preserveAspect; startGroup]
Length[Data]
:[font = output; output; inactive; preserveAspect; endGroup]
62
;[o]
62
:[font = text; inactive; preserveAspect]
This gives a total of 62 possible sides for our rectangles.
Since candidate rectangles must have both their length and
width taken from this list, this gives 3844 possible
rectangles. Fortunately, we can easily reduce the number.
:[font = text; inactive; preserveAspect]
First, we eliminate the first length, 0.
:[font = input; preserveAspect]
Data = Rest[Data];
:[font = text; inactive; preserveAspect]
Since the shortest edge is now 1 and the total area is 8,
we can exclude all sides longer than 8 because the area of
any rectangle using one of these edges would be greater
than 8.
:[font = input; preserveAspect]
Data = Select[Data,N[#]<=8&];
:[font = input; Cclosed; preserveAspect; startGroup]
Length[Data]
:[font = output; output; inactive; preserveAspect; endGroup]
29
;[o]
29
:[font = text; inactive; preserveAspect]
We have reduced the number of possible rectangles to 29^2 or
841.
:[font = text; inactive; preserveAspect]
Our next step is to enumerate all possible edge pairs for
rectangles. First, we pair each possible edge with every
other possible edge in PossibleShapes. Sort and Union are
used to remove duplicates.
:[font = input; preserveAspect]
PossibleShapes = Flatten[Outer[List, Data, Data],1];
:[font = input; preserveAspect]
PossibleShapes = Union[Map[Sort, PossibleShapes]];
:[font = text; inactive; preserveAspect]
Once we have our candidate shapes, we look to see which pairs
give an area of 8 by calculating the area for each pair.
:[font = input; Cclosed; preserveAspect; startGroup]
ViableRectangles =
Select[PossibleShapes, (#[[1]] * #[[2]] == 8)&] //
TableForm
:[font = output; output; inactive; preserveAspect; endGroup]
TableForm[{{1, 8}, {2, 4}, {2^(1/2), 4*2^(1/2)},
{2*2^(1/2), 2*2^(1/2)}}]
;[o]
1 8
2 4
Sqrt[2] 4 Sqrt[2]
2 Sqrt[2] 2 Sqrt[2]
:[font = text; inactive; preserveAspect]
We now have only four candidates. Each row gives the
dimensions of a possible rectangle. The last row,
2 Sqrt[2] by 2 Sqrt[2], is the original square. The second
row, 2 by 4, is the other known rectangle. That the other
two rectangles cannot be formed is clear when we compare
their dimensions to the individual pieces.
:[font = text; inactive; preserveAspect; endGroup]
A 1 by 8 rectangle simply could not contain either of the
large triangles since their minimum height is the Sqrt[2].
The Sqrt[2] by 4 Sqrt[2] rectangle must have a perimeter
of 10 Sqrt[2]. Thus, all of the edges that are multiples
of Sqrt[2] must lie on the perimeter of the rectangle.
Moreover, none of the integer edges can be used in the
perimeter since the sum of a nonzero integer and a nonzero
integer multiple of Sqrt[2] will never be an integer multiple
of Sqrt[2]. But the edges that are multiples of Sqrt[2] on
the parallelogram are on parallel sides separated by
Sqrt[2]/2. To use both would require that they be on
opposite sides of the rectangle. This is impossible since
their separation does not match either dimension of the
rectangle.
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
Efficiency
:[font = text; inactive; preserveAspect]
For a proof, efficiency is only an issue if the code fails
to produce an answer. As long as the memory requirements
of the code does not exceed the memory of the computer used
and as long as the time required does not exceed the user's
patience, the code is "efficient enough."
:[font = text; inactive; preserveAspect]
If the code is not acceptable, the place to start is with
the basic algorithm. This particular proof works because
it enumerates, not all possible shapes, but one aspect of
the shape in question. That is, it enumerates possible edge
lengths for rectangles. This choice reduces both space and
time complexity. Additional reductions in space complexity
were given in In[10], and In[11] to satisfy the memory
constraints of the computer used. Another such reduction,
not needed here, would be to reduce the number of sides
considered by eliminating duplicate edges for each piece.
The following statement could be added after In[1]:
:[font = input; preserveAspect; backColorRed = 65280; backColorGreen = 65280; backColorBlue = 65280]
Pieces = Map[Union, Pieces];
:[font = text; inactive; preserveAspect]
Although not necessary, the space requirements could have
been considerably reduced by combining the generation and
selection processes. In In[1] Outer is used to generate
all edge pairs at once. This could have been replaced with
two nested loops, both over Data, generating candidates
one at a time. Then, by testing within the inner loop, the
collection of data could have been restricted to just the
dimensions of viable rectangles.
:[font = input; preserveAspect]
Shapes = {};
:[font = input; preserveAspect]
For[i=1, i < Length[Data], i++,
For[j=1, j < Length[Data], j++,
If[(Data[[i]] * Data[[j]]) == 8,
Shapes =
Union[Append[Shapes,
Sort[{Data[[i]], Data[[j]]}]]]]]]
:[font = text; inactive; preserveAspect; endGroup]
The list Shapes contains the dimensions of candidate
rectangles.
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
Discussion
:[font = text; inactive; preserveAspect]
I have used this proof as a demonstration in a course in
Mathematica programming with good results. The class was
composed of junior and senior mathematics, computer science,
and engineering students. Since the proof requires only
elementary high school mathematics, students were able to
focus on the proof technique and the programming style. The
proof was easily followed and served as a useful example
of both exploratory mathematics and functional programming
constructs.
:[font = text; inactive; preserveAspect; endGroup]
Considering the number of edge combinations involved, trying
to solve this manually would be tedious at best and highly
error prone. By using Mathematica, we were able to construct
all possible combinations and then reduce the problem to one
that was easily analyzed. I do not wish to suggest that this
could not have been done without Mathematica. Nonetheless,
this particular proof was the result of explorations with
Mathematica.
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
References
:[font = text; inactive; preserveAspect]
Apple, K. and W. Haken, "Every Planar Map is Four Colorable,"
Bulletin of the American Mathematical Society, 82:5,
711--712.
:[font = text; inactive; preserveAspect]
Gardner, Martin. 1974. "Mathematical Games", Scientific
American, 231:2, 98--103.
:[font = text; inactive; preserveAspect]
Gardner, Martin. 1974. "Mathematical Games", Scientific
American, 231:3, 187--191.
:[font = text; inactive; preserveAspect]
Gardner, Martin. 1974. "Mathematical Games", Scientific
American, 231:4, 124--125.
:[font = text; inactive; preserveAspect; backColorRed = 65280; backColorGreen = 65280; endGroup]
Kolata, G. B. 1976. "Four-color Conjecture: A Computer
Aided Proof", Science, 193:564--5.
:[font = section; inactive; Cclosed; preserveAspect; startGroup]
About the Author
:[font = text; inactive; preserveAspect; endGroup; endGroup]
Joseph Sloan is Assistant Professor of Mathematics and
Computer Science at Lander University. He received a M.S.
in Mathematics from Duke University in 1981. In 1987 he
received a Ph.D in Biomedical Engineering from Duke
University for his work on computer modeling of the
electrical properties of the heart.
^*)