displint.h

00001 /*
00002  *
00003  *  Copyright (C) 1996-2005, OFFIS
00004  *
00005  *  This software and supporting documentation were developed by
00006  *
00007  *    Kuratorium OFFIS e.V.
00008  *    Healthcare Information and Communication Systems
00009  *    Escherweg 2
00010  *    D-26121 Oldenburg, Germany
00011  *
00012  *  THIS SOFTWARE IS MADE AVAILABLE,  AS IS,  AND OFFIS MAKES NO  WARRANTY
00013  *  REGARDING  THE  SOFTWARE,  ITS  PERFORMANCE,  ITS  MERCHANTABILITY  OR
00014  *  FITNESS FOR ANY PARTICULAR USE, FREEDOM FROM ANY COMPUTER DISEASES  OR
00015  *  ITS CONFORMITY TO ANY SPECIFICATION. THE ENTIRE RISK AS TO QUALITY AND
00016  *  PERFORMANCE OF THE SOFTWARE IS WITH THE USER.
00017  *
00018  *  Module:  dcmimgle
00019  *
00020  *  Author:  Joerg Riesmeier
00021  *
00022  *  Purpose: DiCubicSpline Function/Interpolation (Header/Implementation)
00023  *
00024  *  Last Update:      $Author: meichel $
00025  *  Update Date:      $Date: 2005/12/08 16:48:10 $
00026  *  CVS/RCS Revision: $Revision: 1.19 $
00027  *  Status:           $State: Exp $
00028  *
00029  *  CVS/RCS Log at end of file
00030  *
00031  */
00032 
00033 
00034 #ifndef DISPLINT_H
00035 #define DISPLINT_H
00036 
00037 #include "dcmtk/config/osconfig.h"
00038 #include "dcmtk/ofstd/ofcast.h"
00039 
00040 
00041 /*--------------------*
00042  *  macro definition  *
00043  *--------------------*/
00044 
00045 // SunCC 4.x does not support default values for template types :-/
00046 #define T3_ double
00047 
00048 
00049 /*------------------*
00050  *  template class  *
00051  *------------------*/
00052 
00055 template <class T1, class T2 /*, class T3 = double*/>
00056 class DiCubicSpline
00057 {
00058 
00059  public:
00060 
00075     static int Function(const T1 *x,
00076                         const T2 *y,
00077                         const unsigned int n,
00078                         T3_ *y2,
00079                         const T3_ yp1 = 1.0e30,
00080                         const T3_ ypn = 1.0e30)
00081     {
00082         if ((x != NULL) && (y != NULL) && (n > 0) && (y2 != NULL))
00083         {
00084             T3_ *u = new T3_[n];                            // temporary vector
00085             if (u != NULL)
00086             {
00087                 register unsigned int i;
00088                 T3_ p, qn, sig, un;
00089                 if (yp1 > 0.99e30)                          // ignore value for first derivative at point 1
00090                     y2[0] = u[0] = 0.0;
00091                 else
00092                 {
00093                     y2[0] = -0.5;
00094                     u[0] = (3.0 / (OFstatic_cast(T3_, x[1]) - OFstatic_cast(T3_, x[0]))) *
00095                            ((OFstatic_cast(T3_, y[1]) - OFstatic_cast(T3_, y[0])) /
00096                            (OFstatic_cast(T3_, x[1]) - OFstatic_cast(T3_, x[0])) - yp1);
00097                 }
00098                 for (i = 1; i < n - 1; ++i)
00099                 {
00100                     sig = (OFstatic_cast(T3_, x[i]) - OFstatic_cast(T3_, x[i - 1])) /
00101                           (OFstatic_cast(T3_, x[i + 1]) - OFstatic_cast(T3_, x[i - 1]));
00102                     p = sig * y2[i - 1] + 2.0;
00103                     y2[i] = (sig - 1.0) / p;
00104                     u[i] = (OFstatic_cast(T3_, y[i + 1]) - OFstatic_cast(T3_, y[i])) /
00105                            (OFstatic_cast(T3_, x[i + 1]) - OFstatic_cast(T3_, x[i])) -
00106                            (OFstatic_cast(T3_, y[i]) - OFstatic_cast(T3_, y[i - 1])) /
00107                            (OFstatic_cast(T3_, x[i]) - OFstatic_cast(T3_, x[i - 1]));
00108                     u[i] = (6.0 * u[i] / (OFstatic_cast(T3_, x[i + 1]) -
00109                             OFstatic_cast(T3_, x[i - 1])) - sig * u[i - 1]) / p;
00110                 }
00111                 if (ypn > 0.99e30)                          // ignore value for first derivative at point 1
00112                     qn = un = 0.0;
00113                 else
00114                 {
00115                     qn = 0.5;
00116                     un = (3.0 / (OFstatic_cast(T3_, x[n - 1]) - OFstatic_cast(T3_, x[n - 2]))) *
00117                          (ypn - (OFstatic_cast(T3_, y[n - 1]) - OFstatic_cast(T3_, y[n - 2])) /
00118                          (OFstatic_cast(T3_, x[n - 1]) - OFstatic_cast(T3_, x[n - 2])));
00119                 }
00120                 y2[n - 1] = (un - qn * u[n - 2]) / (qn * y2[n - 2] + 1.0);
00121                 for (i = n - 1; i > 0; --i)
00122                     y2[i - 1] = y2[i - 1] * y2[i] + u[i - 1];
00123                 delete[] u;
00124                 return 1;
00125             }
00126         }
00127         return 0;
00128     }
00129 
00130 
00146     static int Interpolation(const T1 *xa,
00147                              const T2 *ya,
00148                              const T3_ *y2a,
00149                              const unsigned int na,
00150                              const T1 *x,
00151                              T2 *y,
00152                              const unsigned int n)
00153     {
00154         if ((xa != NULL) && (ya != NULL) && (y2a != NULL) && (na > 0) && (x != NULL) && (y != NULL) && (n > 0))
00155         {
00156             register unsigned int k, i;
00157             register unsigned int klo = 0;
00158             register unsigned int khi = na - 1;
00159             T3_ h, b, a;
00160             for (i = 0; i < n; ++i)
00161             {
00162                 if ((xa[klo] > x[i]) || (xa[khi] < x[i]))       // optimization
00163                 {
00164                     klo = 0;
00165                     khi = na - 1;
00166                 }
00167                 while (khi - klo > 1)                           // search right place in the table, if necessary
00168                 {
00169                     k = (khi + klo) >> 1;
00170                     if (xa[k] > x[i])
00171                         khi = k;
00172                     else
00173                         klo = k;
00174                 }
00175                 if (xa[khi] == x[i])                            // optimization: use known values
00176                     y[i] = ya[khi];
00177                 else
00178                 {
00179                     h = OFstatic_cast(T3_, xa[khi]) - OFstatic_cast(T3_, xa[klo]);
00180                     if (h == 0.0)                               // bad xa input, values must be distinct !
00181                         return 0;
00182                     a = (OFstatic_cast(T3_, xa[khi]) - OFstatic_cast(T3_, x[i])) / h;
00183                     b = (OFstatic_cast(T3_, x[i]) - OFstatic_cast(T3_, xa[klo])) / h;
00184                     y[i] = OFstatic_cast(T2, a * OFstatic_cast(T3_, ya[klo]) + b * OFstatic_cast(T3_, ya[khi]) +
00185                            ((a * a * a - a) * y2a[klo] + (b * b * b - b) * y2a[khi]) * (h * h) / 6.0);
00186                 }
00187             }
00188             return 1;
00189         }
00190         return 0;
00191     }
00192 };
00193 
00194 
00195 #endif
00196 
00197 
00198 /*
00199  *
00200  * CVS/RCS Log:
00201  * $Log: displint.h,v $
00202  * Revision 1.19  2005/12/08 16:48:10  meichel
00203  * Changed include path schema for all DCMTK header files
00204  *
00205  * Revision 1.18  2003/12/23 15:53:22  joergr
00206  * Replaced post-increment/decrement operators by pre-increment/decrement
00207  * operators where appropriate (e.g. 'i++' by '++i').
00208  *
00209  * Revision 1.17  2003/12/08 19:20:47  joergr
00210  * Adapted type casts to new-style typecast operators defined in ofcast.h.
00211  * Removed leading underscore characters from preprocessor symbols (reserved
00212  * symbols). Updated copyright header.
00213  *
00214  * Revision 1.16  2002/07/18 12:30:59  joergr
00215  * Removed unused code.
00216  *
00217  * Revision 1.15  2001/06/01 15:49:51  meichel
00218  * Updated copyright header
00219  *
00220  * Revision 1.14  2000/03/08 16:24:24  meichel
00221  * Updated copyright header.
00222  *
00223  * Revision 1.13  2000/02/02 14:33:54  joergr
00224  * Replaced 'delete' statements by 'delete[]' for objects created with 'new[]'.
00225  *
00226  * Revision 1.12  1999/10/21 08:29:42  joergr
00227  * Renamed template type definition from 'T3' to 'T3_' to avoid naming
00228  * conflicts.
00229  *
00230  * Revision 1.11  1999/10/20 18:38:50  joergr
00231  * Eliminated default values for template types since this features is not
00232  * supported by SunCC 4.x (temporarily introduced '#define' instead).
00233  *
00234  * Revision 1.10  1999/10/15 09:38:31  joergr
00235  * Fixed typos.
00236  *
00237  * Revision 1.9  1999/10/14 19:05:17  joergr
00238  * Fixed typo.
00239  *
00240  * Revision 1.8  1999/10/01 13:25:35  joergr
00241  * Enhanced template class for cubic spline interpolation to support
00242  * non-floating point classes/types as y-coordinates.
00243  *
00244  * Revision 1.7  1999/07/23 14:11:25  joergr
00245  * Added preliminary support for 2D bi-cubic spline interpolation (currently
00246  * not used).
00247  *
00248  * Revision 1.6  1999/05/03 11:09:31  joergr
00249  * Minor code purifications to keep Sun CC 2.0.1 quiet.
00250  *
00251  * Revision 1.5  1999/04/29 13:49:08  joergr
00252  * Renamed class CubicSpline to DiCubicSpline.
00253  *
00254  * Revision 1.4  1999/03/24 17:20:26  joergr
00255  * Added/Modified comments and formatting.
00256  *
00257  * Revision 1.3  1999/03/22 08:52:43  joergr
00258  * Added/Changed comments.
00259  *
00260  * Revision 1.2  1999/02/25 16:17:16  joergr
00261  * Initialize local variables to avoid compiler warnings (reported by gcc
00262  * 2.7.2.1 on Linux).
00263  *
00264  * Revision 1.1  1999/02/11 16:36:29  joergr
00265  * Renamed file to indicate the use of templates.
00266  *
00267  * Revision 1.2  1999/02/09 14:21:54  meichel
00268  * Removed default parameters from template functions, required for Sun CC 4.2
00269  *
00270  * Revision 1.1  1999/02/04 17:59:23  joergr
00271  * Added support for calibration according to Barten transformation (incl.
00272  * a DISPLAY file describing the monitor characteristic).
00273  *
00274  *
00275  */


Generated on 20 Dec 2005 for OFFIS DCMTK Version 3.5.4 by Doxygen 1.4.5