This repository has been archived on 2025-08-18. You can view files and clone it, but you cannot make any changes to it's state, such as pushing and creating new issues, pull requests or comments.
GGS/lib/eqc/doc/eqc_symbolic.html
2011-05-05 02:46:21 +02:00

156 lines
7.8 KiB
HTML

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>Module eqc_symbolic</title>
<link rel="stylesheet" type="text/css" href="stylesheet.css" title="EDoc">
</head>
<body bgcolor="white">
<div class="navbar"><a name="#navbar_top"></a><table width="100%" border="0" cellspacing="0" cellpadding="2" summary="navigation bar"><tr><td><a href="overview-summary.html" target="overviewFrame">Overview</a></td><td><a href="http://www.erlang.org/"><img src="erlang.png" align="right" border="0" alt="erlang logo"></a></td></tr></table></div>
<hr>
<h1>Module eqc_symbolic</h1>
<ul class="index"><li><a href="#description">Description</a></li><li><a href="#index">Function Index</a></li><li><a href="#functions">Function Details</a></li></ul>
This module implements QuickCheck generators and utility functions for
symbolic calls.
<p><b>Version:</b> 1.0.1</p>
<h2><a name="description">Description</a></h2><p>
This module implements QuickCheck generators and utility functions for
symbolic calls.</p>
<p>In test case generation it is often an advantage to postpone calling
functions in the subject under test. In a test one is interested in
the actual function that is called as well as its evaluated result.
If one would evaluate the result already at generation time, then the actual
call is not visible in the QuickCheck counter example shown in a
failing test.</p>
<p>For example, when testing a data structure like the OTP library sets.erl,
one may need more information than just the value to detect what goes
wrong with the following property:</p>
<pre>
prop_sets() -&gt;
?FORALL({S1,S2},{set(),set()},
begin
L1 = sets:to_list(S1),
L2 = sets:to_list(S2),
sets:intersection(S1,S2) ==
sets:from_list(L1--(L1--L2))
end).
</pre>
which will fail with for example the following counter example:
<pre>
Failed! After 132 tests.
Shrinking.......(7 times)
{{set,2,16,16,8,80,48,
{[],[],[],[],[],[],[],[],[],[],[],[],[],[],[],[]},
{{[],[],[],[],[],[],[],[],[],[],[],[-15,33],[],[],[],[]}}},
{set,3,16,16,8,80,48,
{[],[],[],[],[],[],[],[],[],[],[],[],[],[],[],[]},
{{[0],[],[],[],[],[],[],[],[],[],[],[33,-15],[],[],[],[]}}}}
false
</pre>
We would really need to understand the internal representation of sets in order to understand which
sets we have generated and even if we know that, we have no clue which operations were used to
create those sets.
This is were symbolic representations help a lot. We would create a recursive generator that
creates symbolic sets and use the following property instead:
<pre>
prop_sets() -&gt;
?FORALL({SymbS1,SymbS2},{set(),set()},
begin
S1 = eval(SymbS1),
S2 = eval(SymbS2),
L1 = sets:to_list(S1),
L2 = sets:to_list(S2),
sets:intersection(S1,S2) ==
sets:from_list(L1--(L1--L2))
end).
This would then result in a more readable error message:
Shrinking..........(10 times)
{{call,sets,from_list,[[6,-10]]},{call,sets,from_list,[[0,-10,6]]}}
false
</pre>
Symbolic representation of function calls provides us with
<ul>
<li>Better readable counter examples</li>
<li>No need to break abstraction by using clean interface to code
under test</li>
<li>Better possibilities for shrinking when defining generators</li>
</ul>
<h2><a name="index">Function Index</a></h2>
<table width="100%" border="1" cellspacing="0" cellpadding="2" summary="function index"><tr><td valign="top"><a href="#defined-1">defined/1</a></td><td>Checks whether a term can be evaluated without raising an exception.</td></tr>
<tr><td valign="top"><a href="#eval-1">eval/1</a></td><td>Evaluates terms of the form <tt>{call,Module,Function,Args}</tt> anywhere in its
argument, replacing them by the result of the corresponding function call.</td></tr>
<tr><td valign="top"><a href="#eval-2">eval/2</a></td><td>Like <a href="#eval-1"><code>eval/1</code></a>, but also replaces symbolic variables, that is,
terms of the form <tt>{var,V}</tt>, by their corresponding values in the
property list.</td></tr>
<tr><td valign="top"><a href="#pretty_print-1">pretty_print/1</a></td><td>Pretty printing of symbolic terms.</td></tr>
<tr><td valign="top"><a href="#pretty_print-2">pretty_print/2</a></td><td>Pretty printing of symbolic terms within given environment.</td></tr>
<tr><td valign="top"><a href="#well_defined-1">well_defined/1</a></td><td>Generates a well defined symbolic value.</td></tr>
</table>
<h2><a name="functions">Function Details</a></h2>
<h3 class="function"><a name="defined-1">defined/1</a></h3>
<div class="spec">
<p><tt>defined(E::term()) -&gt; bool()</tt></p>
</div><p>Checks whether a term can be evaluated without raising an exception.
Some symbolic terms may raise an exception when evaluating, e.g., division by zero would
raise an exception, thus <tt>eval({call,erlang,'div',[1,0]})</tt> raises an exception as well.</p>
<h3 class="function"><a name="eval-1">eval/1</a></h3>
<div class="spec">
<p><tt>eval(Term::term()) -&gt; term()</tt></p>
</div><p>Evaluates terms of the form <tt>{call,Module,Function,Args}</tt> anywhere in its
argument, replacing them by the result of the corresponding function call.
This is useful when, for example, test data is of an abstract datatype, and
we want to know how it was generated, rather than its representation--it is
much clearer to see that a test failed for <tt>sets:new()</tt> (that is
<tt>{call,sets,new,[]}</tt>), for example,
than for its representation.
We write <tt>?FORALL(X,TGen,...eval(X)...)</tt>, where <tt>TGen</tt>
generates terms containing calls, so that test cases are displayed in this
form, but the actual test data is the result of evaluating the calls.</p>
<h3 class="function"><a name="eval-2">eval/2</a></h3>
<div class="spec">
<p><tt>eval(Env::<a href="#type-proplist">proplist()</a>, T::term()) -&gt; term()</tt></p>
</div><p>Like <a href="#eval-1"><code>eval/1</code></a>, but also replaces symbolic variables, that is,
terms of the form <tt>{var,V}</tt>, by their corresponding values in the
property list. This should be a list of pairs of atoms and values. For example,
<tt>eval([{x,3}],{var,x})</tt> evaluates to 3.</p>
<h3 class="function"><a name="pretty_print-1">pretty_print/1</a></h3>
<div class="spec">
<p><tt>pretty_print(Symb::term()) -&gt; string()</tt></p>
</div><p>Pretty printing of symbolic terms.
A symbolic value like <tt>{call,sets,union,[{call,sets,new,[]},{call,sets,from_list,[[1,2]]}]}</tt>
is transformed to the string \"sets:union(sets:new(),from_list([1,2]))\".</p>
<h3 class="function"><a name="pretty_print-2">pretty_print/2</a></h3>
<div class="spec">
<p><tt>pretty_print(Env::<a href="#type-proplist">proplist()</a>, Symb::term()) -&gt; string()</tt></p>
</div><p>Pretty printing of symbolic terms within given environment.
Like <a href="#pretty_print-1"><code>pretty_print/1</code></a>, but also replaces symbolic variables, that is,
terms of the form <tt>{var,V}</tt>, by their corresponding values in the
property list. This should be a list of pairs of atoms and values. For example,
<tt>eval([{x,3}],{var,x})</tt> is pretty printed to \"3\".</p>
<h3 class="function"><a name="well_defined-1">well_defined/1</a></h3>
<div class="spec">
<p><tt>well_defined(G::<a href="#type-gen">gen(A)</a>) -&gt; A</tt></p>
</div><p>Generates a well defined symbolic value.
A value is well defined if evaluating it does not raise an exception.</p>
<hr>
<div class="navbar"><a name="#navbar_bottom"></a><table width="100%" border="0" cellspacing="0" cellpadding="2" summary="navigation bar"><tr><td><a href="overview-summary.html" target="overviewFrame">Overview</a></td><td><a href="http://www.erlang.org/"><img src="erlang.png" align="right" border="0" alt="erlang logo"></a></td></tr></table></div>
<p><i>Generated by EDoc, Jun 13 2010, 13:15:30.</i></p>
</body>
</html>