1 // xId: plmem.c 11966 2011-10-14 07:10:05Z andrewross $
2 //
3 //  plmem.c
4 //
5 //  Copyright (C) 1992, 1993, 1994, 1995
6 //  Maurice LeBrun			mjl@dino.ph.utexas.edu
7 //  Institute for Fusion Studies	University of Texas at Austin
8 //
9 //  Copyright (C) 2004 Joao Cardoso
10 //  Copyright (C) 2004-2018 Alan W. Irwin
11 //  Copyright (C) 2004 Andrew Ross
12 //
13 //  This file is part of PLplot.
14 //
15 //  PLplot is free software; you can redistribute it and/or modify
16 //  it under the terms of the GNU Library General Public License as published
17 //  by the Free Software Foundation; either version 2 of the License, or
18 //  (at your option) any later version.
19 //
20 //  PLplot is distributed in the hope that it will be useful,
21 //  but WITHOUT ANY WARRANTY; without even the implied warranty of
22 //  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
23 //  GNU Library General Public License for more details.
24 //
25 //  You should have received a copy of the GNU Library General Public License
26 //  along with PLplot; if not, write to the Free Software
27 //  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
28 //
29 //--------------------------------------------------------------------------
30 //
31 
32 //! @file
33 //!  These functions provide allocation and deallocation of two-dimensional
34 //!  arrays.
35 //!
36 
37 #include "plplotP.h"
38 
39 //--------------------------------------------------------------------------
40 //
41 //! Determine the Iliffe column vector of pointers to PLFLT row
42 //! vectors corresponding to a 2D matrix of PLFLT's that is statically
43 //! allocated. As a result the matrix can be accessed using C/C++
44 //! syntax like zIliffe[i][j].
45 //! Example usage:
46 //!
47 //!   PLFLT zStatic[XPTS][YPTS];
48 //!   PLFLT_NC_VECTOR zIliffe[XPTS];
49 //!
50 //!   plStatic2dGrid((PLFLT_NC_MATRIX)zIliffe, (PLFLT_VECTOR)(&zStatic[0][0]), XPTS, YPTS);
51 //!   plshade((PLFLT_NC_MATRIX)zIliffe,....);
52 //!
53 //! @param zIliffe Pre-existing location of the storage for the Iliffe column vectors.
54 //! @param zStatic Pre-existing location of the storage for the 2D z array that is statically allocated.
55 //! @param nx Size of the grid in x = length of the (Iliffe) column vectors.
56 //! @param ny Size of the grid in y = length of the row vectors.
57 //!
58 //--------------------------------------------------------------------------
59 
60 void
plStatic2dGrid(PLFLT_NC_MATRIX zIliffe,PLFLT_VECTOR zStatic,PLINT nx,PLINT ny)61 plStatic2dGrid( PLFLT_NC_MATRIX zIliffe, PLFLT_VECTOR zStatic, PLINT nx, PLINT ny )
62 {
63     PLINT i;
64 
65     for ( i = 0; i < nx; i++ )
66     {
67         zIliffe[i] = (PLFLT_NC_SCALAR) ( zStatic + i * ny );
68     }
69 }
70 
71 //--------------------------------------------------------------------------
72 //
73 //! Allocate a block of memory for use as a matrix of type
74 //! PLFLT_MATRIX (organized as an Iliffe column vector of pointers to
75 //! row vectors).  As a result the matrix can be accessed using C/C++
76 //! syntax like *f[i][j]. The memory associated with this matrix must
77 //! be freed by calling plFree2dGrid once it is no longer required.
78 //! Example usage:
79 //!
80 //!   PLFLT **z;
81 //!
82 //!   plAlloc2dGrid(&z, XPTS, YPTS);
83 //!
84 //! @param f Location of the storage (address of a **).
85 //! @param nx Size of the grid in x.
86 //! @param ny Size of the grid in y.
87 //!
88 //--------------------------------------------------------------------------
89 
90 void
plAlloc2dGrid(PLFLT *** f,PLINT nx,PLINT ny)91 plAlloc2dGrid( PLFLT ***f, PLINT nx, PLINT ny )
92 {
93     PLINT i;
94 
95     if ( ( *f = (PLFLT **) calloc( (size_t) nx, sizeof ( PLFLT * ) ) ) == NULL )
96         plexit( "Memory allocation error in \"plAlloc2dGrid\"" );
97 
98     for ( i = 0; i < nx; i++ )
99     {
100         if ( ( ( *f )[i] = (PLFLT *) calloc( (size_t) ny, sizeof ( PLFLT ) ) ) == NULL )
101             plexit( "Memory allocation error in \"plAlloc2dGrid\"" );
102     }
103 }
104 
105 //--------------------------------------------------------------------------
106 // plFree2dGrid()
107 //
108 //! Frees a block of memory allocated with plAlloc2dGrid().
109 //!
110 //! @param f The [][] to the storage.
111 //! @param nx Size of the grid in x.
112 //! @param PL_UNUSED( ny) Not used.
113 //--------------------------------------------------------------------------
114 
115 void
plFree2dGrid(PLFLT ** f,PLINT nx,PLINT PL_UNUSED (ny))116 plFree2dGrid( PLFLT **f, PLINT nx, PLINT PL_UNUSED( ny ) )
117 {
118     PLINT i;
119 
120     for ( i = 0; i < nx; i++ )
121         free( (void *) f[i] );
122 
123     free( (void *) f );
124 }
125 
126 //--------------------------------------------------------------------------
127 // plMinMax2dGrid()
128 //
129 //! Finds the maximum and minimum of a 2d matrix allocated with plAlloc2dGrid().
130 //! NaN and +/- infinity values are ignored.
131 //!
132 //! param f 2d matrix pointer.
133 //! param nx Size of the grid in x.
134 //! param ny Size of the grid in y.
135 //! param fnmax Maximum value in the matrix.
136 //! param fnmin Minimum value in the matrix.
137 //!
138 //--------------------------------------------------------------------------
139 
140 void
plMinMax2dGrid(PLFLT_MATRIX f,PLINT nx,PLINT ny,PLFLT * fnmax,PLFLT * fnmin)141 plMinMax2dGrid( PLFLT_MATRIX f, PLINT nx, PLINT ny, PLFLT *fnmax, PLFLT *fnmin )
142 {
143     int   i, j;
144     PLFLT m, M;
145 
146     if ( !isfinite( f[0][0] ) )
147     {
148         M = -HUGE_VAL;
149         m = HUGE_VAL;
150     }
151     else
152         M = m = f[0][0];
153 
154     for ( i = 0; i < nx; i++ )
155     {
156         for ( j = 0; j < ny; j++ )
157         {
158             if ( !isfinite( f[i][j] ) )
159                 continue;
160             if ( f[i][j] > M )
161                 M = f[i][j];
162             if ( f[i][j] < m )
163                 m = f[i][j];
164         }
165     }
166     *fnmax = M;
167     *fnmin = m;
168 }
169