Imported Upstream version 1.51.0
[platform/upstream/boost.git] / libs / math / doc / sf_and_dist / html / math_toolkit / toolkit / internals2 / test_data.html
1 <html>
2 <head>
3 <meta http-equiv="Content-Type" content="text/html; charset=US-ASCII">
4 <title>Graphing, Profiling, and Generating Test Data for Special Functions</title>
5 <link rel="stylesheet" href="../../../../../../../../doc/src/boostbook.css" type="text/css">
6 <meta name="generator" content="DocBook XSL Stylesheets V1.76.1">
7 <link rel="home" href="../../../index.html" title="Math Toolkit">
8 <link rel="up" href="../internals2.html" title="Testing and Development">
9 <link rel="prev" href="error_test.html" title="Relative Error and Testing">
10 <link rel="next" href="../../using_udt.html" title="Use with User-Defined Floating-Point Types">
11 </head>
12 <body bgcolor="white" text="black" link="#0000FF" vlink="#840084" alink="#0000FF">
13 <table cellpadding="2" width="100%"><tr>
14 <td valign="top"><img alt="Boost C++ Libraries" width="277" height="86" src="../../../../../../../../boost.png"></td>
15 <td align="center"><a href="../../../../../../../../index.html">Home</a></td>
16 <td align="center"><a href="../../../../../../../../libs/libraries.htm">Libraries</a></td>
17 <td align="center"><a href="http://www.boost.org/users/people.html">People</a></td>
18 <td align="center"><a href="http://www.boost.org/users/faq.html">FAQ</a></td>
19 <td align="center"><a href="../../../../../../../../more/index.htm">More</a></td>
20 </tr></table>
21 <hr>
22 <div class="spirit-nav">
23 <a accesskey="p" href="error_test.html"><img src="../../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../internals2.html"><img src="../../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../../index.html"><img src="../../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../using_udt.html"><img src="../../../../../../../../doc/src/images/next.png" alt="Next"></a>
24 </div>
25 <div class="section math_toolkit_toolkit_internals2_test_data">
26 <div class="titlepage"><div><div><h4 class="title">
27 <a name="math_toolkit.toolkit.internals2.test_data"></a><a class="link" href="test_data.html" title="Graphing, Profiling, and Generating Test Data for Special Functions">Graphing,
28         Profiling, and Generating Test Data for Special Functions</a>
29 </h4></div></div></div>
30 <p>
31           The class <code class="computeroutput"><span class="identifier">test_data</span></code> and
32           associated helper functions are designed so that in just a few lines of
33           code you should be able to:
34         </p>
35 <div class="itemizedlist"><ul class="itemizedlist" type="disc">
36 <li class="listitem">
37               Profile a continued fraction, or infinite series for convergence and
38               accuracy.
39             </li>
40 <li class="listitem">
41               Generate csv data from a special function that can be imported into
42               your favorite graphing program (or spreadsheet) for further analysis.
43             </li>
44 <li class="listitem">
45               Generate high precision test data.
46             </li>
47 </ul></div>
48 <h5>
49 <a name="math_toolkit.toolkit.internals2.test_data.h0"></a>
50           <span><a name="math_toolkit.toolkit.internals2.test_data.synopsis"></a></span><a class="link" href="test_data.html#math_toolkit.toolkit.internals2.test_data.synopsis">Synopsis</a>
51         </h5>
52 <pre class="programlisting"><span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">{</span> <span class="keyword">namespace</span> <span class="identifier">math</span><span class="special">{</span> <span class="keyword">namespace</span> <span class="identifier">tools</span><span class="special">{</span>
53
54 <span class="keyword">enum</span> <span class="identifier">parameter_type</span>
55 <span class="special">{</span>
56    <span class="identifier">random_in_range</span> <span class="special">=</span> <span class="number">0</span><span class="special">,</span>
57    <span class="identifier">periodic_in_range</span> <span class="special">=</span> <span class="number">1</span><span class="special">,</span>
58    <span class="identifier">power_series</span> <span class="special">=</span> <span class="number">2</span><span class="special">,</span>
59    <span class="identifier">dummy_param</span> <span class="special">=</span> <span class="number">0x80</span><span class="special">,</span>
60 <span class="special">};</span>
61
62 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
63 <span class="keyword">struct</span> <span class="identifier">parameter_info</span><span class="special">;</span>
64
65 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
66 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">make_random_param</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">start_range</span><span class="special">,</span> <span class="identifier">T</span> <span class="identifier">end_range</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">n_points</span><span class="special">);</span>
67
68 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
69 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">make_periodic_param</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">start_range</span><span class="special">,</span> <span class="identifier">T</span> <span class="identifier">end_range</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">n_points</span><span class="special">);</span>
70
71 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
72 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">make_power_param</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">basis</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">start_exponent</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">end_exponent</span><span class="special">);</span>
73
74 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
75 <span class="keyword">bool</span> <span class="identifier">get_user_parameter_info</span><span class="special">(</span><span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">info</span><span class="special">,</span> <span class="keyword">const</span> <span class="keyword">char</span><span class="special">*</span> <span class="identifier">param_name</span><span class="special">);</span>
76
77 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
78 <span class="keyword">class</span> <span class="identifier">test_data</span>
79 <span class="special">{</span>
80 <span class="keyword">public</span><span class="special">:</span>
81    <span class="keyword">typedef</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">vector</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">row_type</span><span class="special">;</span>
82    <span class="keyword">typedef</span> <span class="identifier">row_type</span> <span class="identifier">value_type</span><span class="special">;</span>
83 <span class="keyword">private</span><span class="special">:</span>
84    <span class="keyword">typedef</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">set</span><span class="special">&lt;</span><span class="identifier">row_type</span><span class="special">&gt;</span> <span class="identifier">container_type</span><span class="special">;</span>
85 <span class="keyword">public</span><span class="special">:</span>
86    <span class="keyword">typedef</span> <span class="keyword">typename</span> <span class="identifier">container_type</span><span class="special">::</span><span class="identifier">reference</span> <span class="identifier">reference</span><span class="special">;</span>
87    <span class="keyword">typedef</span> <span class="keyword">typename</span> <span class="identifier">container_type</span><span class="special">::</span><span class="identifier">const_reference</span> <span class="identifier">const_reference</span><span class="special">;</span>
88    <span class="keyword">typedef</span> <span class="keyword">typename</span> <span class="identifier">container_type</span><span class="special">::</span><span class="identifier">iterator</span> <span class="identifier">iterator</span><span class="special">;</span>
89    <span class="keyword">typedef</span> <span class="keyword">typename</span> <span class="identifier">container_type</span><span class="special">::</span><span class="identifier">const_iterator</span> <span class="identifier">const_iterator</span><span class="special">;</span>
90    <span class="keyword">typedef</span> <span class="keyword">typename</span> <span class="identifier">container_type</span><span class="special">::</span><span class="identifier">difference_type</span> <span class="identifier">difference_type</span><span class="special">;</span>
91    <span class="keyword">typedef</span> <span class="keyword">typename</span> <span class="identifier">container_type</span><span class="special">::</span><span class="identifier">size_type</span> <span class="identifier">size_type</span><span class="special">;</span>
92
93    <span class="comment">// creation:</span>
94    <span class="identifier">test_data</span><span class="special">(){}</span>
95    <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">F</span><span class="special">&gt;</span>
96    <span class="identifier">test_data</span><span class="special">(</span><span class="identifier">F</span> <span class="identifier">func</span><span class="special">,</span> <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg1</span><span class="special">);</span>
97
98    <span class="comment">// insertion:</span>
99    <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">F</span><span class="special">&gt;</span>
100    <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">insert</span><span class="special">(</span><span class="identifier">F</span> <span class="identifier">func</span><span class="special">,</span> <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg1</span><span class="special">);</span>
101
102    <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">F</span><span class="special">&gt;</span>
103    <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">insert</span><span class="special">(</span><span class="identifier">F</span> <span class="identifier">func</span><span class="special">,</span> <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg1</span><span class="special">,</span>
104                      <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg2</span><span class="special">);</span>
105
106    <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">F</span><span class="special">&gt;</span>
107    <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">insert</span><span class="special">(</span><span class="identifier">F</span> <span class="identifier">func</span><span class="special">,</span> <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg1</span><span class="special">,</span>
108                      <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg2</span><span class="special">,</span>
109                      <span class="keyword">const</span> <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">arg3</span><span class="special">);</span>
110
111    <span class="keyword">void</span> <span class="identifier">clear</span><span class="special">();</span>
112
113    <span class="comment">// access:</span>
114    <span class="identifier">iterator</span> <span class="identifier">begin</span><span class="special">();</span>
115    <span class="identifier">iterator</span> <span class="identifier">end</span><span class="special">();</span>
116    <span class="identifier">const_iterator</span> <span class="identifier">begin</span><span class="special">()</span><span class="keyword">const</span><span class="special">;</span>
117    <span class="identifier">const_iterator</span> <span class="identifier">end</span><span class="special">()</span><span class="keyword">const</span><span class="special">;</span>
118    <span class="keyword">bool</span> <span class="keyword">operator</span><span class="special">==(</span><span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">d</span><span class="special">)</span><span class="keyword">const</span><span class="special">;</span>
119    <span class="keyword">bool</span> <span class="keyword">operator</span><span class="special">!=(</span><span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">d</span><span class="special">)</span><span class="keyword">const</span><span class="special">;</span>
120    <span class="keyword">void</span> <span class="identifier">swap</span><span class="special">(</span><span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">other</span><span class="special">);</span>
121    <span class="identifier">size_type</span> <span class="identifier">size</span><span class="special">()</span><span class="keyword">const</span><span class="special">;</span>
122    <span class="identifier">size_type</span> <span class="identifier">max_size</span><span class="special">()</span><span class="keyword">const</span><span class="special">;</span>
123    <span class="keyword">bool</span> <span class="identifier">empty</span><span class="special">()</span><span class="keyword">const</span><span class="special">;</span>
124
125    <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">&lt;</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">dat</span><span class="special">)</span><span class="keyword">const</span><span class="special">;</span>
126    <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">&lt;=</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">dat</span><span class="special">)</span><span class="keyword">const</span><span class="special">;</span>
127    <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">&gt;</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">dat</span><span class="special">)</span><span class="keyword">const</span><span class="special">;</span>
128    <span class="keyword">bool</span> <span class="keyword">operator</span> <span class="special">&gt;=</span> <span class="special">(</span><span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&amp;</span> <span class="identifier">dat</span><span class="special">)</span><span class="keyword">const</span><span class="special">;</span>
129 <span class="special">};</span>
130
131 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">charT</span><span class="special">,</span> <span class="keyword">class</span> <span class="identifier">traits</span><span class="special">,</span> <span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
132 <span class="identifier">std</span><span class="special">::</span><span class="identifier">basic_ostream</span><span class="special">&lt;</span><span class="identifier">charT</span><span class="special">,</span> <span class="identifier">traits</span><span class="special">&gt;&amp;</span> <span class="identifier">write_csv</span><span class="special">(</span>
133             <span class="identifier">std</span><span class="special">::</span><span class="identifier">basic_ostream</span><span class="special">&lt;</span><span class="identifier">charT</span><span class="special">,</span> <span class="identifier">traits</span><span class="special">&gt;&amp;</span> <span class="identifier">os</span><span class="special">,</span>
134             <span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">data</span><span class="special">);</span>
135
136 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">charT</span><span class="special">,</span> <span class="keyword">class</span> <span class="identifier">traits</span><span class="special">,</span> <span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
137 <span class="identifier">std</span><span class="special">::</span><span class="identifier">basic_ostream</span><span class="special">&lt;</span><span class="identifier">charT</span><span class="special">,</span> <span class="identifier">traits</span><span class="special">&gt;&amp;</span> <span class="identifier">write_csv</span><span class="special">(</span>
138             <span class="identifier">std</span><span class="special">::</span><span class="identifier">basic_ostream</span><span class="special">&lt;</span><span class="identifier">charT</span><span class="special">,</span> <span class="identifier">traits</span><span class="special">&gt;&amp;</span> <span class="identifier">os</span><span class="special">,</span>
139             <span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">data</span><span class="special">,</span>
140             <span class="keyword">const</span> <span class="identifier">charT</span><span class="special">*</span> <span class="identifier">separator</span><span class="special">);</span>
141
142 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
143 <span class="identifier">std</span><span class="special">::</span><span class="identifier">ostream</span><span class="special">&amp;</span> <span class="identifier">write_code</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">ostream</span><span class="special">&amp;</span> <span class="identifier">os</span><span class="special">,</span>
144                          <span class="keyword">const</span> <span class="identifier">test_data</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">data</span><span class="special">,</span>
145                          <span class="keyword">const</span> <span class="keyword">char</span><span class="special">*</span> <span class="identifier">name</span><span class="special">);</span>
146
147 <span class="special">}}}</span> <span class="comment">// namespaces</span>
148 </pre>
149 <h5>
150 <a name="math_toolkit.toolkit.internals2.test_data.h1"></a>
151           <span><a name="math_toolkit.toolkit.internals2.test_data.description"></a></span><a class="link" href="test_data.html#math_toolkit.toolkit.internals2.test_data.description">Description</a>
152         </h5>
153 <p>
154           This tool is best illustrated with the following series of examples.
155         </p>
156 <p>
157           The functionality of test_data is split into the following parts:
158         </p>
159 <div class="itemizedlist"><ul class="itemizedlist" type="disc">
160 <li class="listitem">
161               A functor that implements the function for which data is being generated:
162               this is the bit you have to write.
163             </li>
164 <li class="listitem">
165               One of more parameters that are to be passed to the functor, these
166               are described in fairly abstract terms: give me N points distributed
167               like <span class="emphasis"><em>this</em></span> etc.
168             </li>
169 <li class="listitem">
170               The class test_data, that takes the functor and descriptions of the
171               parameters and computes how ever many output points have been requested,
172               these are stored in a sorted container.
173             </li>
174 <li class="listitem">
175               Routines to iterate over the test_data container and output the data
176               in either csv format, or as C++ source code (as a table using Boost.Array).
177             </li>
178 </ul></div>
179 <h6>
180 <a name="math_toolkit.toolkit.internals2.test_data.h2"></a>
181           <span><a name="math_toolkit.toolkit.internals2.test_data.example_1__output_data_for_graph_plotting"></a></span><a class="link" href="test_data.html#math_toolkit.toolkit.internals2.test_data.example_1__output_data_for_graph_plotting">Example
182           1: Output Data for Graph Plotting</a>
183         </h6>
184 <p>
185           For example, lets say we want to graph the lgamma function between -3 and
186           100, one could do this like so:
187         </p>
188 <pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">test_data</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
189 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">special_functions</span><span class="special">/</span><span class="identifier">gamma</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
190
191 <span class="keyword">int</span> <span class="identifier">main</span><span class="special">()</span>
192 <span class="special">{</span>
193    <span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">tools</span><span class="special">;</span>
194
195    <span class="comment">// create an object to hold the data:</span>
196    <span class="identifier">test_data</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">&gt;</span> <span class="identifier">data</span><span class="special">;</span>
197
198    <span class="comment">// insert 500 points at uniform intervals between just after -3 and 100:</span>
199    <span class="keyword">double</span> <span class="special">(*</span><span class="identifier">pf</span><span class="special">)(</span><span class="keyword">double</span><span class="special">)</span> <span class="special">=</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">lgamma</span><span class="special">;</span>
200    <span class="identifier">data</span><span class="special">.</span><span class="identifier">insert</span><span class="special">(</span><span class="identifier">pf</span><span class="special">,</span> <span class="identifier">make_periodic_param</span><span class="special">(-</span><span class="number">3.0</span> <span class="special">+</span> <span class="number">0.00001</span><span class="special">,</span> <span class="number">100.0</span><span class="special">,</span> <span class="number">500</span><span class="special">));</span>
201
202    <span class="comment">// print out in csv format:</span>
203    <span class="identifier">write_csv</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span><span class="special">,</span> <span class="identifier">data</span><span class="special">,</span> <span class="string">", "</span><span class="special">);</span>
204    <span class="keyword">return</span> <span class="number">0</span><span class="special">;</span>
205 <span class="special">}</span>
206 </pre>
207 <p>
208           Which, when plotted, results in:
209         </p>
210 <p>
211           <span class="inlinemediaobject"><img src="../../../../graphs/lgamma.png" align="middle"></span>
212         </p>
213 <h6>
214 <a name="math_toolkit.toolkit.internals2.test_data.h3"></a>
215           <span><a name="math_toolkit.toolkit.internals2.test_data.example_2__creating_test_data"></a></span><a class="link" href="test_data.html#math_toolkit.toolkit.internals2.test_data.example_2__creating_test_data">Example
216           2: Creating Test Data</a>
217         </h6>
218 <p>
219           As a second example, let's suppose we want to create highly accurate test
220           data for a special function. Since many special functions have two or more
221           independent parameters, it's very hard to effectively cover all of the
222           possible parameter space without generating gigabytes of data at great
223           computational expense. A second best approach is to provide the tools by
224           which a user (or the library maintainer) can quickly generate more data
225           on demand to probe the function over a particular domain of interest.
226         </p>
227 <p>
228           In this example we'll generate test data for the beta function using <a href="http://shoup.net/ntl/doc/RR.txt" target="_top">NTL::RR</a> at 1000 bit precision.
229           Rather than call our generic version of the beta function, we'll implement
230           a deliberately naive version of the beta function using lgamma, and rely
231           on the high precision of the data type used to get results accurate to
232           at least 128-bit precision. In this way our test data is independent of
233           whatever clever tricks we may wish to use inside the our beta function.
234         </p>
235 <p>
236           To start with then, here's the function object that creates the test data:
237         </p>
238 <pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">ntl</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
239 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">special_functions</span><span class="special">/</span><span class="identifier">gamma</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
240 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">test_data</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
241 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">fstream</span><span class="special">&gt;</span>
242
243 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">test_data</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
244
245 <span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">tools</span><span class="special">;</span>
246
247 <span class="keyword">struct</span> <span class="identifier">beta_data_generator</span>
248 <span class="special">{</span>
249    <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span> <span class="keyword">operator</span><span class="special">()(</span><span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span> <span class="identifier">a</span><span class="special">,</span> <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span> <span class="identifier">b</span><span class="special">)</span>
250    <span class="special">{</span>
251       <span class="comment">//</span>
252       <span class="comment">// If we throw a domain error then test_data will</span>
253       <span class="comment">// ignore this input point. We'll use this to filter</span>
254       <span class="comment">// out all cases where a &lt; b since the beta function</span>
255       <span class="comment">// is symmetrical in a and b:</span>
256       <span class="comment">//</span>
257       <span class="keyword">if</span><span class="special">(</span><span class="identifier">a</span> <span class="special">&lt;</span> <span class="identifier">b</span><span class="special">)</span>
258          <span class="keyword">throw</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">domain_error</span><span class="special">(</span><span class="string">""</span><span class="special">);</span>
259
260       <span class="comment">// very naively calculate spots with lgamma:</span>
261       <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span> <span class="identifier">g1</span><span class="special">,</span> <span class="identifier">g2</span><span class="special">,</span> <span class="identifier">g3</span><span class="special">;</span>
262       <span class="keyword">int</span> <span class="identifier">s1</span><span class="special">,</span> <span class="identifier">s2</span><span class="special">,</span> <span class="identifier">s3</span><span class="special">;</span>
263       <span class="identifier">g1</span> <span class="special">=</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">lgamma</span><span class="special">(</span><span class="identifier">a</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">s1</span><span class="special">);</span>
264       <span class="identifier">g2</span> <span class="special">=</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">lgamma</span><span class="special">(</span><span class="identifier">b</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">s2</span><span class="special">);</span>
265       <span class="identifier">g3</span> <span class="special">=</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">lgamma</span><span class="special">(</span><span class="identifier">a</span><span class="special">+</span><span class="identifier">b</span><span class="special">,</span> <span class="special">&amp;</span><span class="identifier">s3</span><span class="special">);</span>
266       <span class="identifier">g1</span> <span class="special">+=</span> <span class="identifier">g2</span> <span class="special">-</span> <span class="identifier">g3</span><span class="special">;</span>
267       <span class="identifier">g1</span> <span class="special">=</span> <span class="identifier">exp</span><span class="special">(</span><span class="identifier">g1</span><span class="special">);</span>
268       <span class="identifier">g1</span> <span class="special">*=</span> <span class="identifier">s1</span> <span class="special">*</span> <span class="identifier">s2</span> <span class="special">*</span> <span class="identifier">s3</span><span class="special">;</span>
269       <span class="keyword">return</span> <span class="identifier">g1</span><span class="special">;</span>
270    <span class="special">}</span>
271 <span class="special">};</span>
272 </pre>
273 <p>
274           To create the data, we'll need to input the domains for a and b for which
275           the function will be tested: the function <code class="computeroutput"><span class="identifier">get_user_parameter_info</span></code>
276           is designed for just that purpose. The start of main will look something
277           like:
278         </p>
279 <pre class="programlisting"><span class="comment">// Set the precision on RR:</span>
280 <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span><span class="special">::</span><span class="identifier">SetPrecision</span><span class="special">(</span><span class="number">1000</span><span class="special">);</span> <span class="comment">// bits.</span>
281 <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span><span class="special">::</span><span class="identifier">SetOutputPrecision</span><span class="special">(</span><span class="number">40</span><span class="special">);</span> <span class="comment">// decimal digits.</span>
282
283 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span><span class="special">&gt;</span> <span class="identifier">arg1</span><span class="special">,</span> <span class="identifier">arg2</span><span class="special">;</span>
284 <span class="identifier">test_data</span><span class="special">&lt;</span><span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span><span class="special">&gt;</span> <span class="identifier">data</span><span class="special">;</span>
285
286 <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"Welcome.\n"</span>
287    <span class="string">"This program will generate spot tests for the beta function:\n"</span>
288    <span class="string">"  beta(a, b)\n\n"</span><span class="special">;</span>
289
290 <span class="keyword">bool</span> <span class="identifier">cont</span><span class="special">;</span>
291 <span class="identifier">std</span><span class="special">::</span><span class="identifier">string</span> <span class="identifier">line</span><span class="special">;</span>
292
293 <span class="keyword">do</span><span class="special">{</span>
294    <span class="comment">// prompt the user for the domain of a and b to test:</span>
295    <span class="identifier">get_user_parameter_info</span><span class="special">(</span><span class="identifier">arg1</span><span class="special">,</span> <span class="string">"a"</span><span class="special">);</span>
296    <span class="identifier">get_user_parameter_info</span><span class="special">(</span><span class="identifier">arg2</span><span class="special">,</span> <span class="string">"b"</span><span class="special">);</span>
297
298    <span class="comment">// create the data:</span>
299    <span class="identifier">data</span><span class="special">.</span><span class="identifier">insert</span><span class="special">(</span><span class="identifier">beta_data_generator</span><span class="special">(),</span> <span class="identifier">arg1</span><span class="special">,</span> <span class="identifier">arg2</span><span class="special">);</span>
300
301    <span class="comment">// see if the user want's any more domains tested:</span>
302    <span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"Any more data [y/n]?"</span><span class="special">;</span>
303    <span class="identifier">std</span><span class="special">::</span><span class="identifier">getline</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">cin</span><span class="special">,</span> <span class="identifier">line</span><span class="special">);</span>
304    <span class="identifier">boost</span><span class="special">::</span><span class="identifier">algorithm</span><span class="special">::</span><span class="identifier">trim</span><span class="special">(</span><span class="identifier">line</span><span class="special">);</span>
305    <span class="identifier">cont</span> <span class="special">=</span> <span class="special">(</span><span class="identifier">line</span> <span class="special">==</span> <span class="string">"y"</span><span class="special">);</span>
306 <span class="special">}</span><span class="keyword">while</span><span class="special">(</span><span class="identifier">cont</span><span class="special">);</span>
307 </pre>
308 <div class="caution"><table border="0" summary="Caution">
309 <tr>
310 <td rowspan="2" align="center" valign="top" width="25"><img alt="[Caution]" src="../../../../../../../../doc/src/images/caution.png"></td>
311 <th align="left">Caution</th>
312 </tr>
313 <tr><td align="left" valign="top"><p>
314             At this point one potential stumbling block should be mentioned: test_data&lt;&gt;::insert
315             will create a matrix of test data when there are two or more parameters,
316             so if we have two parameters and we're asked for a thousand points on
317             each, that's a <span class="emphasis"><em>million test points in total</em></span>. Don't
318             say you weren't warned!
319           </p></td></tr>
320 </table></div>
321 <p>
322           There's just one final step now, and that's to write the test data to file:
323         </p>
324 <pre class="programlisting"><span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span> <span class="special">&lt;&lt;</span> <span class="string">"Enter name of test data file [default=beta_data.ipp]"</span><span class="special">;</span>
325 <span class="identifier">std</span><span class="special">::</span><span class="identifier">getline</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">cin</span><span class="special">,</span> <span class="identifier">line</span><span class="special">);</span>
326 <span class="identifier">boost</span><span class="special">::</span><span class="identifier">algorithm</span><span class="special">::</span><span class="identifier">trim</span><span class="special">(</span><span class="identifier">line</span><span class="special">);</span>
327 <span class="keyword">if</span><span class="special">(</span><span class="identifier">line</span> <span class="special">==</span> <span class="string">""</span><span class="special">)</span>
328    <span class="identifier">line</span> <span class="special">=</span> <span class="string">"beta_data.ipp"</span><span class="special">;</span>
329 <span class="identifier">std</span><span class="special">::</span><span class="identifier">ofstream</span> <span class="identifier">ofs</span><span class="special">(</span><span class="identifier">line</span><span class="special">.</span><span class="identifier">c_str</span><span class="special">());</span>
330 <span class="identifier">write_code</span><span class="special">(</span><span class="identifier">ofs</span><span class="special">,</span> <span class="identifier">data</span><span class="special">,</span> <span class="string">"beta_data"</span><span class="special">);</span>
331 </pre>
332 <p>
333           The format of the test data looks something like:
334         </p>
335 <pre class="programlisting"><span class="preprocessor">#define</span> <span class="identifier">SC_</span><span class="special">(</span><span class="identifier">x</span><span class="special">)</span> <span class="keyword">static_cast</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;(</span><span class="identifier">BOOST_JOIN</span><span class="special">(</span><span class="identifier">x</span><span class="special">,</span> <span class="identifier">L</span><span class="special">))</span>
336    <span class="keyword">static</span> <span class="keyword">const</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">array</span><span class="special">&lt;</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">array</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">,</span> <span class="number">3</span><span class="special">&gt;,</span> <span class="number">1830</span><span class="special">&gt;</span>
337    <span class="identifier">beta_med_data</span> <span class="special">=</span> <span class="special">{</span>
338       <span class="identifier">SC_</span><span class="special">(</span><span class="number">0.4883005917072296142578125</span><span class="special">),</span>
339       <span class="identifier">SC_</span><span class="special">(</span><span class="number">0.4883005917072296142578125</span><span class="special">),</span>
340       <span class="identifier">SC_</span><span class="special">(</span><span class="number">3.245912809500479157065104747353807392371</span><span class="special">),</span>
341       <span class="identifier">SC_</span><span class="special">(</span><span class="number">3.5808107852935791015625</span><span class="special">),</span>
342       <span class="identifier">SC_</span><span class="special">(</span><span class="number">0.4883005917072296142578125</span><span class="special">),</span>
343       <span class="identifier">SC_</span><span class="special">(</span><span class="number">1.007653173802923954909901438393379243537</span><span class="special">),</span>
344       <span class="comment">/* ... lots of rows skipped */</span>
345 <span class="special">};</span>
346 </pre>
347 <p>
348           The first two values in each row are the input parameters that were passed
349           to our functor and the last value is the return value from the functor.
350           Had our functor returned a <a class="link" href="../internals1/tuples.html" title="Tuples">boost::math::tuple</a>
351           rather than a value, then we would have had one entry for each element
352           in the tuple in addition to the input parameters.
353         </p>
354 <p>
355           The first #define serves two purposes:
356         </p>
357 <div class="itemizedlist"><ul class="itemizedlist" type="disc">
358 <li class="listitem">
359               It reduces the file sizes considerably: all those <code class="computeroutput"><span class="keyword">static_cast</span></code>'s
360               add up to a lot of bytes otherwise (they are needed to suppress compiler
361               warnings when <code class="computeroutput"><span class="identifier">T</span></code> is
362               narrower than a <code class="computeroutput"><span class="keyword">long</span> <span class="keyword">double</span></code>).
363             </li>
364 <li class="listitem">
365               It provides a useful customisation point: for example if we were testing
366               a user-defined type that has more precision than a <code class="computeroutput"><span class="keyword">long</span>
367               <span class="keyword">double</span></code> we could change it to:
368             </li>
369 </ul></div>
370 <p>
371           <code class="literal">#define SC_(x) lexical_cast&lt;T&gt;(BOOST_STRINGIZE(x))</code>
372         </p>
373 <p>
374           in order to ensure that no truncation of the values occurs prior to conversion
375           to <code class="computeroutput"><span class="identifier">T</span></code>. Note that this isn't
376           used by default as it's rather hard on the compiler when the table is large.
377         </p>
378 <h6>
379 <a name="math_toolkit.toolkit.internals2.test_data.h4"></a>
380           <span><a name="math_toolkit.toolkit.internals2.test_data.example_3__profiling_a_continued_fraction_for_convergence_and_accuracy"></a></span><a class="link" href="test_data.html#math_toolkit.toolkit.internals2.test_data.example_3__profiling_a_continued_fraction_for_convergence_and_accuracy">Example
381           3: Profiling a Continued Fraction for Convergence and Accuracy</a>
382         </h6>
383 <p>
384           Alternatively, lets say we want to profile a continued fraction for convergence
385           and error. As an example, we'll use the continued fraction for the upper
386           incomplete gamma function, the following function object returns the next
387           a<sub>N </sub> and b<sub>N </sub> of the continued fraction each time it's invoked:
388         </p>
389 <pre class="programlisting"><span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
390 <span class="keyword">struct</span> <span class="identifier">upper_incomplete_gamma_fract</span>
391 <span class="special">{</span>
392 <span class="keyword">private</span><span class="special">:</span>
393    <span class="identifier">T</span> <span class="identifier">z</span><span class="special">,</span> <span class="identifier">a</span><span class="special">;</span>
394    <span class="keyword">int</span> <span class="identifier">k</span><span class="special">;</span>
395 <span class="keyword">public</span><span class="special">:</span>
396    <span class="keyword">typedef</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">pair</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">,</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">result_type</span><span class="special">;</span>
397
398    <span class="identifier">upper_incomplete_gamma_fract</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">a1</span><span class="special">,</span> <span class="identifier">T</span> <span class="identifier">z1</span><span class="special">)</span>
399       <span class="special">:</span> <span class="identifier">z</span><span class="special">(</span><span class="identifier">z1</span><span class="special">-</span><span class="identifier">a1</span><span class="special">+</span><span class="number">1</span><span class="special">),</span> <span class="identifier">a</span><span class="special">(</span><span class="identifier">a1</span><span class="special">),</span> <span class="identifier">k</span><span class="special">(</span><span class="number">0</span><span class="special">)</span>
400    <span class="special">{</span>
401    <span class="special">}</span>
402
403    <span class="identifier">result_type</span> <span class="keyword">operator</span><span class="special">()()</span>
404    <span class="special">{</span>
405       <span class="special">++</span><span class="identifier">k</span><span class="special">;</span>
406       <span class="identifier">z</span> <span class="special">+=</span> <span class="number">2</span><span class="special">;</span>
407       <span class="keyword">return</span> <span class="identifier">result_type</span><span class="special">(</span><span class="identifier">k</span> <span class="special">*</span> <span class="special">(</span><span class="identifier">a</span> <span class="special">-</span> <span class="identifier">k</span><span class="special">),</span> <span class="identifier">z</span><span class="special">);</span>
408    <span class="special">}</span>
409 <span class="special">};</span>
410 </pre>
411 <p>
412           We want to measure both the relative error, and the rate of convergence
413           of this fraction, so we'll write a functor that returns both as a <a class="link" href="../internals1/tuples.html" title="Tuples">boost::math::tuple</a>:
414           class test_data will unpack the tuple for us, and create one column of
415           data for each element in the tuple (in addition to the input parameters):
416         </p>
417 <pre class="programlisting"><span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">test_data</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
418 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">test</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
419 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">special_functions</span><span class="special">/</span><span class="identifier">gamma</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
420 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">ntl</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
421 <span class="preprocessor">#include</span> <span class="special">&lt;</span><span class="identifier">boost</span><span class="special">/</span><span class="identifier">math</span><span class="special">/</span><span class="identifier">tools</span><span class="special">/</span><span class="identifier">tuple</span><span class="special">.</span><span class="identifier">hpp</span><span class="special">&gt;</span>
422
423 <span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
424 <span class="keyword">struct</span> <span class="identifier">profile_gamma_fraction</span>
425 <span class="special">{</span>
426    <span class="keyword">typedef</span> <a class="link" href="../internals1/tuples.html" title="Tuples">boost::math::tuple</a><span class="special">&lt;</span><span class="identifier">T</span><span class="special">,</span> <span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">result_type</span><span class="special">;</span>
427
428    <span class="identifier">result_type</span> <span class="keyword">operator</span><span class="special">()(</span><span class="identifier">T</span> <span class="identifier">val</span><span class="special">)</span>
429    <span class="special">{</span>
430       <span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">tools</span><span class="special">;</span>
431       <span class="comment">// estimate the true value, using arbitary precision</span>
432       <span class="comment">// arithmetic and NTL::RR:</span>
433       <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span> <span class="identifier">rval</span><span class="special">(</span><span class="identifier">val</span><span class="special">);</span>
434       <span class="identifier">upper_incomplete_gamma_fract</span><span class="special">&lt;</span><span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span><span class="special">&gt;</span> <span class="identifier">f1</span><span class="special">(</span><span class="identifier">rval</span><span class="special">,</span> <span class="identifier">rval</span><span class="special">);</span>
435       <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span> <span class="identifier">true_val</span> <span class="special">=</span> <span class="identifier">continued_fraction_a</span><span class="special">(</span><span class="identifier">f1</span><span class="special">,</span> <span class="number">1000</span><span class="special">);</span>
436       <span class="comment">//</span>
437       <span class="comment">// Now get the aproximation at double precision, along with the number of</span>
438       <span class="comment">// iterations required:</span>
439       <span class="identifier">boost</span><span class="special">::</span><span class="identifier">uintmax_t</span> <span class="identifier">iters</span> <span class="special">=</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">numeric_limits</span><span class="special">&lt;</span><span class="identifier">boost</span><span class="special">::</span><span class="identifier">uintmax_t</span><span class="special">&gt;::</span><span class="identifier">max</span><span class="special">();</span>
440       <span class="identifier">upper_incomplete_gamma_fract</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">f2</span><span class="special">(</span><span class="identifier">val</span><span class="special">,</span> <span class="identifier">val</span><span class="special">);</span>
441       <span class="identifier">T</span> <span class="identifier">found_val</span> <span class="special">=</span> <span class="identifier">continued_fraction_a</span><span class="special">(</span><span class="identifier">f2</span><span class="special">,</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">numeric_limits</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;::</span><span class="identifier">digits</span><span class="special">,</span> <span class="identifier">iters</span><span class="special">);</span>
442       <span class="comment">//</span>
443       <span class="comment">// Work out the relative error, as measured in units of epsilon:</span>
444       <span class="identifier">T</span> <span class="identifier">err</span> <span class="special">=</span> <span class="identifier">real_cast</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;(</span><span class="identifier">relative_error</span><span class="special">(</span><span class="identifier">true_val</span><span class="special">,</span> <span class="identifier">NTL</span><span class="special">::</span><span class="identifier">RR</span><span class="special">(</span><span class="identifier">found_val</span><span class="special">))</span> <span class="special">/</span> <span class="identifier">std</span><span class="special">::</span><span class="identifier">numeric_limits</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;::</span><span class="identifier">epsilon</span><span class="special">());</span>
445       <span class="comment">//</span>
446       <span class="comment">// now just return the results as a tuple:</span>
447       <span class="keyword">return</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">make_tuple</span><span class="special">(</span><span class="identifier">err</span><span class="special">,</span> <span class="identifier">iters</span><span class="special">);</span>
448    <span class="special">}</span>
449 <span class="special">};</span>
450 </pre>
451 <p>
452           Feeding that functor into test_data allows rapid output of csv data, for
453           whatever type <code class="computeroutput"><span class="identifier">T</span></code> we may
454           be interested in:
455         </p>
456 <pre class="programlisting"><span class="keyword">int</span> <span class="identifier">main</span><span class="special">()</span>
457 <span class="special">{</span>
458    <span class="keyword">using</span> <span class="keyword">namespace</span> <span class="identifier">boost</span><span class="special">::</span><span class="identifier">math</span><span class="special">::</span><span class="identifier">tools</span><span class="special">;</span>
459    <span class="comment">// create an object to hold the data:</span>
460    <span class="identifier">test_data</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">&gt;</span> <span class="identifier">data</span><span class="special">;</span>
461    <span class="comment">// insert 500 points at uniform intervals between just after 0 and 100:</span>
462    <span class="identifier">data</span><span class="special">.</span><span class="identifier">insert</span><span class="special">(</span><span class="identifier">profile_gamma_fraction</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">&gt;(),</span> <span class="identifier">make_periodic_param</span><span class="special">(</span><span class="number">0.01</span><span class="special">,</span> <span class="number">100.0</span><span class="special">,</span> <span class="number">100</span><span class="special">));</span>
463    <span class="comment">// print out in csv format:</span>
464    <span class="identifier">write_csv</span><span class="special">(</span><span class="identifier">std</span><span class="special">::</span><span class="identifier">cout</span><span class="special">,</span> <span class="identifier">data</span><span class="special">,</span> <span class="string">", "</span><span class="special">);</span>
465    <span class="keyword">return</span> <span class="number">0</span><span class="special">;</span>
466 <span class="special">}</span>
467 </pre>
468 <p>
469           This time there's no need to plot a graph, the first few rows are:
470         </p>
471 <pre class="programlisting"><span class="identifier">a</span> <span class="keyword">and</span> <span class="identifier">z</span><span class="special">,</span>  <span class="identifier">Error</span><span class="special">/</span><span class="identifier">epsilon</span><span class="special">,</span>  <span class="identifier">Iterations</span> <span class="identifier">required</span>
472
473 <span class="number">0.01</span><span class="special">,</span>     <span class="number">9723.14</span><span class="special">,</span>        <span class="number">4726</span>
474 <span class="number">1.0099</span><span class="special">,</span>   <span class="number">9.54818</span><span class="special">,</span>        <span class="number">87</span>
475 <span class="number">2.0098</span><span class="special">,</span>   <span class="number">3.84777</span><span class="special">,</span>        <span class="number">40</span>
476 <span class="number">3.0097</span><span class="special">,</span>   <span class="number">0.728358</span><span class="special">,</span>       <span class="number">25</span>
477 <span class="number">4.0096</span><span class="special">,</span>   <span class="number">2.39712</span><span class="special">,</span>        <span class="number">21</span>
478 <span class="number">5.0095</span><span class="special">,</span>   <span class="number">0.233263</span><span class="special">,</span>       <span class="number">16</span>
479 </pre>
480 <p>
481           So it's pretty clear that this fraction shouldn't be used for small values
482           of a and z.
483         </p>
484 <h5>
485 <a name="math_toolkit.toolkit.internals2.test_data.h5"></a>
486           <span><a name="math_toolkit.toolkit.internals2.test_data.reference"></a></span><a class="link" href="test_data.html#math_toolkit.toolkit.internals2.test_data.reference">reference</a>
487         </h5>
488 <p>
489           <a name="test_data_reference"></a>Most of this tool has been described
490           already in the examples above, we'll just add the following notes on the
491           non-member functions:
492         </p>
493 <pre class="programlisting"><span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
494 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">make_random_param</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">start_range</span><span class="special">,</span> <span class="identifier">T</span> <span class="identifier">end_range</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">n_points</span><span class="special">);</span>
495 </pre>
496 <p>
497           Tells class test_data to test <span class="emphasis"><em>n_points</em></span> random values
498           in the range [start_range,end_range].
499         </p>
500 <pre class="programlisting"><span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
501 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">make_periodic_param</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">start_range</span><span class="special">,</span> <span class="identifier">T</span> <span class="identifier">end_range</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">n_points</span><span class="special">);</span>
502 </pre>
503 <p>
504           Tells class test_data to test <span class="emphasis"><em>n_points</em></span> evenly spaced
505           values in the range [start_range,end_range].
506         </p>
507 <pre class="programlisting"><span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
508 <span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;</span> <span class="identifier">make_power_param</span><span class="special">(</span><span class="identifier">T</span> <span class="identifier">basis</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">start_exponent</span><span class="special">,</span> <span class="keyword">int</span> <span class="identifier">end_exponent</span><span class="special">);</span>
509 </pre>
510 <p>
511           Tells class test_data to test points of the form <span class="emphasis"><em>basis + R *
512           2<sup>expon</sup></em></span> for each <span class="emphasis"><em>expon</em></span> in the range [start_exponent,
513           end_exponent], and <span class="emphasis"><em>R</em></span> a random number in [0.5, 1].
514         </p>
515 <pre class="programlisting"><span class="keyword">template</span> <span class="special">&lt;</span><span class="keyword">class</span> <span class="identifier">T</span><span class="special">&gt;</span>
516 <span class="keyword">bool</span> <span class="identifier">get_user_parameter_info</span><span class="special">(</span><span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="identifier">T</span><span class="special">&gt;&amp;</span> <span class="identifier">info</span><span class="special">,</span> <span class="keyword">const</span> <span class="keyword">char</span><span class="special">*</span> <span class="identifier">param_name</span><span class="special">);</span>
517 </pre>
518 <p>
519           Prompts the user for the parameter range and form to use.
520         </p>
521 <p>
522           Finally, if we don't want the parameter to be included in the output, we
523           can tell test_data by setting it a "dummy parameter":
524         </p>
525 <pre class="programlisting"><span class="identifier">parameter_info</span><span class="special">&lt;</span><span class="keyword">double</span><span class="special">&gt;</span> <span class="identifier">p</span> <span class="special">=</span> <span class="identifier">make_random_param</span><span class="special">(</span><span class="number">2.0</span><span class="special">,</span> <span class="number">5.0</span><span class="special">,</span> <span class="number">10</span><span class="special">);</span>
526 <span class="identifier">p</span><span class="special">.</span><span class="identifier">type</span> <span class="special">|=</span> <span class="identifier">dummy_param</span><span class="special">;</span>
527 </pre>
528 <p>
529           This is useful when the functor used transforms the parameter in some way
530           before passing it to the function under test, usually the functor will
531           then return both the transformed input and the result in a tuple, so there's
532           no need for the original pseudo-parameter to be included in program output.
533         </p>
534 </div>
535 <table xmlns:rev="http://www.cs.rpi.edu/~gregod/boost/tools/doc/revision" width="100%"><tr>
536 <td align="left"></td>
537 <td align="right"><div class="copyright-footer">Copyright &#169; 2006-2010 John Maddock, Paul A. Bristow, Hubert Holin, Xiaogang Zhang, Bruno
538       Lalande, Johan R&#229;de, Gautam Sewani, Thijs van den Berg and Benjamin Sobotta<p>
539         Distributed under the Boost Software License, Version 1.0. (See accompanying
540         file LICENSE_1_0.txt or copy at <a href="http://www.boost.org/LICENSE_1_0.txt" target="_top">http://www.boost.org/LICENSE_1_0.txt</a>)
541       </p>
542 </div></td>
543 </tr></table>
544 <hr>
545 <div class="spirit-nav">
546 <a accesskey="p" href="error_test.html"><img src="../../../../../../../../doc/src/images/prev.png" alt="Prev"></a><a accesskey="u" href="../internals2.html"><img src="../../../../../../../../doc/src/images/up.png" alt="Up"></a><a accesskey="h" href="../../../index.html"><img src="../../../../../../../../doc/src/images/home.png" alt="Home"></a><a accesskey="n" href="../../using_udt.html"><img src="../../../../../../../../doc/src/images/next.png" alt="Next"></a>
547 </div>
548 </body>
549 </html>