PLplot  5.10.0
tclMatrix.h
Go to the documentation of this file.
00001 // -*-C++-*-
00002 //  Copyright 1994, 1995
00003 //  Maurice LeBrun                      mjl@dino.ph.utexas.edu
00004 //  Institute for Fusion Studies        University of Texas at Austin
00005 //
00006 //  Copyright (C) 2004  Maurice LeBrun
00007 //
00008 //  This file is part of PLplot.
00009 //
00010 //  PLplot is free software; you can redistribute it and/or modify
00011 //  it under the terms of the GNU General Public License as published by
00012 //  the Free Software Foundation; either version 2 of the License, or
00013 //  (at your option) any later version.
00014 //
00015 //  PLplot is distributed in the hope that it will be useful,
00016 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
00017 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00018 //  GNU General Public License for more details.
00019 //
00020 //  You should have received a copy of the GNU General Public License
00021 //  along with PLplot; if not, write to the Free Software
00022 //  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
00023 //
00024 //--------------------------------------------------------------------------
00025 //
00026 //  Contains declarations for Tcl "Matrix" command.
00027 //  C functions that need access to the matrix data will need
00028 //  to include this file.
00029 //
00030 
00031 #ifndef __TCLMATRIX_H__
00032 #define __TCLMATRIX_H__
00033 
00034 #include "plplot.h"
00035 #include <tcl.h>
00036 
00037 typedef PLFLT   Mat_float;
00038 
00039 #if defined ( MSDOS )
00040 typedef long    Mat_int;
00041 #else
00042 typedef int     Mat_int;
00043 #endif
00044 
00045 enum { TYPE_FLOAT, TYPE_INT };
00046 
00047 // Arrays are column dominant (normal C ordering)
00048 // Array elements are stored contiguously
00049 // Require dimension <= 3 for simplicity
00050 
00051 #define MAX_ARRAY_DIM    3
00052 
00053 // Useful macros for index calculations
00054 
00055 #define I3D( i, j, k )    k + matPtr->n[2] * ( I2D( i, j ) )
00056 #define I2D( i, j )       j + matPtr->n[1] * ( I1D( i ) )
00057 #define I1D( i )          i
00058 
00059 // Matrix operator data
00060 
00061 typedef struct
00062 {
00063     int        type;             // Data type
00064     int        len;              // Total length of array
00065     int        dim;              // Number of dimensions
00066     int        n[MAX_ARRAY_DIM]; // Holds array length in each dimension
00067     int        tracing;          // Set if not persistent
00068 
00069     char       *name;            // Matrix operator name, malloc'ed
00070 
00071     Mat_float  *fdata;           // Floating point data, malloc'ed
00072     Mat_int    *idata;           // Integer data, malloc'ed
00073 
00074     Tcl_Interp *interp;          // Interpreter where command is installed
00075 
00076 // These do the put/get operations for each supported type
00077 
00078     void ( *put )( ClientData clientData, Tcl_Interp* interp, int index, const char *string );
00079     void ( *get )( ClientData clientData, Tcl_Interp* interp, int index, char *string );
00080 } tclMatrix;
00081 
00082 // Function prototypes
00083 
00084 #ifdef __cplusplus
00085 //--------------------------------------------------------------------------
00086 // // Since C++ does not generally have a per-platform ABI the way C
00087 // // does, we stick to a totally inline class declaration and
00088 // // definition.  That way you don't have to keep a separate version of
00089 // // libplplot*.a for each compiler you'd like to use.
00090 //
00091 // // Start by setting up some important macros.
00092 //
00093 
00094 #include <iostream>
00095 
00096 #ifdef throw
00097 #define TCL_NO_UNDEF
00098 #endif
00099 
00100 #ifndef throw
00101 #ifdef __hpux
00102 #if defined ( __GNUC__ ) || defined ( __lucid ) || defined ( __CENTERLINE__ ) \
00103     || defined ( CENTERLINE_CLPP )
00104 #define NO_XCPT
00105 #endif
00106 #else
00107 #define NO_XCPT
00108 #endif
00109 
00110 #ifdef NO_XCPT
00111 #define try
00112 #define throw( a )                                     \
00113     { cerr << "THROW: " << # a << " from " << __FILE__ \
00114            << " line " << __LINE__ << endl << flush; abort(); }
00115 #define catch( a )    if ( 0 )
00116 #define Throw
00117 #else
00118 #define Throw    throw
00119 #endif
00120 #endif
00121 
00122 #define tMat_Assert( a, b )    if ( !( a ) )                   \
00123     { using namespace std;                                     \
00124       cerr << "Assertion " << # a << " failed in " << __FILE__ \
00125            << " at line " << __LINE__ << endl << flush;        \
00126       throw( b ); }
00127 
00128 //--------------------------------------------------------------------------
00129 // // class TclMatFloat
00130 //
00131 // // This class provides a convenient way to access the data of a
00132 // // tclMatrix from within compiled code.  Someone should make clones of
00133 // // this class for the other tclMatrix supported data types.
00134 //--------------------------------------------------------------------------
00135 
00136 class TclMatFloat {
00137     tclMatrix *matPtr;
00138 public:
00139     TclMatFloat( tclMatrix * ptm )
00140         : matPtr( ptm )
00141     {
00142         tMat_Assert( matPtr->type == TYPE_FLOAT, "Type mismatch" );
00143     }
00144 
00145     int Dimensions() const
00146     {
00147         return matPtr->dim;
00148     }
00149 
00150     int dim_size( int d ) const
00151     {
00152         tMat_Assert( d < matPtr->dim, "Range error." );
00153         return matPtr->n[d];
00154     }
00155 
00156     void redim( int nx )
00157     {
00158         free( matPtr->fdata );
00159         matPtr->dim   = 1;
00160         matPtr->n[0]  = nx;
00161         matPtr->len   = nx;
00162         matPtr->fdata = (Mat_float *) malloc( matPtr->len *
00163             sizeof ( Mat_float ) );
00164     }
00165 
00166     void redim( int nx, int ny )
00167     {
00168         free( matPtr->fdata );
00169         matPtr->dim   = 2;
00170         matPtr->n[0]  = nx;
00171         matPtr->n[1]  = ny;
00172         matPtr->len   = nx * ny;
00173         matPtr->fdata = (Mat_float *) malloc( matPtr->len *
00174             sizeof ( Mat_float ) );
00175     }
00176 
00177     void redim( int nx, int ny, int nz )
00178     {
00179         free( matPtr->fdata );
00180         matPtr->dim   = 3;
00181         matPtr->n[0]  = nx;
00182         matPtr->n[1]  = ny;
00183         matPtr->n[2]  = nz;
00184         matPtr->len   = nx * ny * nz;
00185         matPtr->fdata = (Mat_float *) malloc( matPtr->len *
00186             sizeof ( Mat_float ) );
00187     }
00188 
00189     Mat_float& operator() ( int i )
00190     {
00191         tMat_Assert( matPtr->dim == 1, "Wrong number of indicies." );
00192         tMat_Assert( i >= 0 && i < matPtr->n[0],
00193             "Out of bounds reference" );
00194 
00195         return matPtr->fdata[i];
00196     }
00197 
00198     Mat_float& operator() ( int i, int j )
00199     {
00200         tMat_Assert( matPtr->dim == 2, "Wrong number of indicies." );
00201         tMat_Assert( i >= 0 && i < matPtr->n[0] &&
00202             j >= 0 && j < matPtr->n[1],
00203             "Out of bounds reference" );
00204 
00205         return matPtr->fdata[I2D( i, j )];
00206     }
00207 
00208     Mat_float& operator() ( int i, int j, int k )
00209     {
00210         tMat_Assert( matPtr->dim == 3, "Wrong number of indicies." );
00211         tMat_Assert( i >= 0 && i < matPtr->n[0] &&
00212             j >= 0 && j < matPtr->n[1] &&
00213             k >= 0 && k < matPtr->n[2],
00214             "Out of bounds reference" );
00215 
00216         return matPtr->fdata[I3D( i, j, k )];
00217     }
00218 };
00219 
00220 //--------------------------------------------------------------------------
00221 // // class TclMatInt
00222 //
00223 // // This class provides a convenient way to access the data of a
00224 // // tclMatrix from within compiled code.  This is just like TclMatFloat above,
00225 // // but for ints.
00226 //--------------------------------------------------------------------------
00227 
00228 class TclMatInt {
00229     tclMatrix *matPtr;
00230 public:
00231     TclMatInt( tclMatrix * ptm )
00232         : matPtr( ptm )
00233     {
00234         tMat_Assert( matPtr->type == TYPE_INT, "Type mismatch" );
00235     }
00236 
00237     int Dimensions() const
00238     {
00239         return matPtr->dim;
00240     }
00241 
00242     int dim_size( int d ) const
00243     {
00244         tMat_Assert( d < matPtr->dim, "Range error." );
00245         return matPtr->n[d];
00246     }
00247 
00248     void redim( int nx )
00249     {
00250         free( matPtr->idata );
00251         matPtr->dim   = 1;
00252         matPtr->n[0]  = nx;
00253         matPtr->len   = nx;
00254         matPtr->idata = (Mat_int *) malloc( matPtr->len * sizeof ( Mat_int ) );
00255     }
00256 
00257     void redim( int nx, int ny )
00258     {
00259         free( matPtr->idata );
00260         matPtr->dim   = 2;
00261         matPtr->n[0]  = nx;
00262         matPtr->n[1]  = ny;
00263         matPtr->len   = nx * ny;
00264         matPtr->idata = (Mat_int *) malloc( matPtr->len * sizeof ( Mat_int ) );
00265     }
00266 
00267     void redim( int nx, int ny, int nz )
00268     {
00269         free( matPtr->idata );
00270         matPtr->dim   = 3;
00271         matPtr->n[0]  = nx;
00272         matPtr->n[1]  = ny;
00273         matPtr->n[2]  = nz;
00274         matPtr->len   = nx * ny * nz;
00275         matPtr->idata = (Mat_int *) malloc( matPtr->len * sizeof ( Mat_int ) );
00276     }
00277 
00278     Mat_int& operator() ( int i )
00279     {
00280         tMat_Assert( matPtr->dim == 1, "Wrong number of indicies." );
00281         tMat_Assert( i >= 0 && i < matPtr->n[0],
00282             "Out of bounds reference" );
00283 
00284         return matPtr->idata[i];
00285     }
00286 
00287     Mat_int& operator() ( int i, int j )
00288     {
00289         tMat_Assert( matPtr->dim == 2, "Wrong number of indicies." );
00290         tMat_Assert( i >= 0 && i < matPtr->n[0] &&
00291             j >= 0 && j < matPtr->n[1],
00292             "Out of bounds reference" );
00293 
00294         return matPtr->idata[I2D( i, j )];
00295     }
00296 
00297     Mat_int& operator() ( int i, int j, int k )
00298     {
00299         tMat_Assert( matPtr->dim == 3, "Wrong number of indicies." );
00300         tMat_Assert( i >= 0 && i < matPtr->n[0] &&
00301             j >= 0 && j < matPtr->n[1] &&
00302             k >= 0 && k < matPtr->n[2],
00303             "Out of bounds reference" );
00304 
00305         return matPtr->idata[I3D( i, j, k )];
00306     }
00307 };
00308 
00309 #ifndef TCL_NO_UNDEF
00310 
00311 #ifdef NO_XCPT
00312 #undef NO_XCPT
00313 #undef try
00314 #undef throw
00315 #undef Throw
00316 #undef catch
00317 #endif
00318 
00319 #endif
00320 
00321 #undef tMat_Assert
00322 
00323 extern "C" {
00324 //--------------------------------------------------------------------------
00325 #endif
00326 
00327 // Tcl package initialisation function
00328 
00329 int PLDLLIMPEXP_TCLMAT Matrix_Init( Tcl_Interp* );
00330 
00331 // This procedure is invoked to process the "matrix" Tcl command.
00332 
00333 int
00334 Tcl_MatrixCmd( ClientData clientData, Tcl_Interp *interp,
00335                int argc, const char **argv );
00336 
00337 // Returns a pointer to the specified matrix operator's data.
00338 
00339 tclMatrix PLDLLIMPEXP_TCLMAT *
00340 Tcl_GetMatrixPtr( Tcl_Interp *interp, const char *matName );
00341 
00342 // Some stuff for handling extension subcommands.
00343 
00344 typedef int ( *tclMatrixXtnsnProc )( tclMatrix *pm, Tcl_Interp *interp,
00345                                      int argc, const char *argv[] );
00346 
00347 typedef struct tclMatrixXtnsnDescr
00348 {
00349     char *cmd;
00350     tclMatrixXtnsnProc cmdproc;
00351     struct tclMatrixXtnsnDescr *next;
00352 } tclMatrixXtnsnDescr;
00353 
00354 int PLDLLIMPEXP_TCLMAT Tcl_MatrixInstallXtnsn( const char *cmd, tclMatrixXtnsnProc proc );
00355 
00356 #ifdef __cplusplus
00357 }
00358 #endif
00359 
00360 #endif  // __TCLMATRIX_H__
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Defines