cloudy  trunk
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
cont_ipoint.cpp
Go to the documentation of this file.
1 /* This file is part of Cloudy and is copyright (C)1978-2022 by Gary J. Ferland and
2  * others. For conditions of distribution and use see copyright notice in license.txt */
3 /*ipoint returns pointer to any energy within energy mesh */
4 /*ipFineCont returns array index within fine energy mesh */
5 /*ipContEnergy generate pointer to energy within continuum array
6  * continuum energy in Rydbergs */
7 /*ipLineEnergy generate pointer to line energy within energy mesh
8  * line energy in Rydbergs */
9 #include "cddefines.h"
10 #include "ipoint.h"
11 #include "prt.h"
12 #include "rfield.h"
13 
14 /*ipoint returns pointer to any energy within energy mesh */
15 long ipoint(double energy_ryd)
16 {
17  if( energy_ryd < rfield.emm() || energy_ryd > rfield.egamry() )
18  {
19  fprintf( ioQQQ, " ipoint:\n" );
20  fprintf( ioQQQ, " The energy_ryd array is not defined at nu=%11.3e. The bounds are%11.3e%11.3e\n",
21  energy_ryd, rfield.emm(), rfield.egamry() );
22  fprintf( ioQQQ, " ipoint is aborting to get trace, to find how this happened\n" );
23  ShowMe();
25  }
26 
27  return rfield.ipointF(energy_ryd);
28 }
29 
30 /*ipContEnergy generate pointer to energy within continuum array */
32  /* continuum energy in Rydbergs */
33  double energy,
34  /* 4 char label for continuum, like those returned by chLineLbl */
35  const char *chLabel)
36 {
37  long int ipConSafe_v;
38 
39  DEBUG_ENTRY( "ipContEnergy()" );
40 
41  ipConSafe_v = ipoint(energy);
42 
43  /* write label in this cell if not anything there yet */
44  if( strcmp(rfield.chContLabel[ipConSafe_v-1].c_str()," ") == 0 )
45  {
46  rfield.chContLabel[ipConSafe_v-1] = chLabel ;
47  }
48 
49  /* this is a quick way to find all continua that occur within a given cell,
50  * recall the off-by-one aspect of C */
51  {
52  enum {DEBUG_LOC=false};
53  if( DEBUG_LOC )
54  {
55  /* recall the off-by-one aspect of C - the number below is
56  * on the physics scale because this returns the index
57  * on that scale, so the first is 1 for [0] */
58  if( ipConSafe_v == 23 )
59  fprintf(ioQQQ,"%s\n", chLabel );
60  }
61  }
62  return ipConSafe_v;
63 }
64 
65 /*ipLineEnergy generate pointer to line energy within energy mesh
66  * line energy in Rydbergs -
67  * return value is array index on the physics or Fortran scale, counting from 1 */
68 long ipLineEnergy(double energy,
69  /* 4 char label for line, like those returned by chLineLbl */
70  const char *chLabel,
71  /* will make sure energy is <= this array index if greater than 0, does nothing if <= 0*/
72  long ipIonEnergy )
73 {
74  long int ipLine_ret;
75 
76  DEBUG_ENTRY( "ipLineEnergy()" );
77 
78  ipLine_ret = ipoint(energy);
79  ASSERT( ipLine_ret > 0 );
80  /* make sure pointer is below next higher continuum if positive */
81  if( ipIonEnergy > 0 )
82  ASSERT( ipLine_ret <= ipIonEnergy );
83 
84  /* stuff in a label if none there,
85  * note that this is offset one below actual number to be on C scale of arrays */
86  /* >>chng 06 nov 23, faster to use line_count index rather than checking 5 chars
87  * first call will have zero so false */
88  if( !rfield.line_count[ipLine_ret-1] )
89  {
90  rfield.chLineLabel[ipLine_ret-1] = chLabel;
91  }
92  /* this keeps track of the number of lines within this cell */
93  ++rfield.line_count[ipLine_ret-1];
94 
95  /* this is a quick way to find all lines that occur within a given cell,
96  * recall the off-by-one aspect of C */
97  {
98  enum {DEBUG_LOC=false};
99  if( DEBUG_LOC )
100  {
101  /* recall the off-by-one aspect of C - the numbers is one more
102  * than the index on the C scale */
103  if( ipLine_ret == 23 )
104  fprintf(ioQQQ,"%s\n", chLabel );
105  }
106  }
107 
108  /* this implements the print continuum indices command */
109  if( prt.lgPrtContIndices )
110  {
111  /* print header if first time */
112  static bool lgFirst = true;
113  if( lgFirst )
114  {
115  /* print header and set flag so do not do again */
116  fprintf(ioQQQ , "\n\noutput from print continuum indices command follows.\n");
117  fprintf(ioQQQ , "cont ind (F scale)\tenergy(ryd)\tlabel\n");
118  lgFirst = false;
119  }
120  if( energy >= prt.lgPrtContIndices_lo_E && energy <= prt.lgPrtContIndices_hi_E )
121  {
122  /* use varying formats depending on order of magnitude of energy
123  * NB - the ipLine_ret is the index on the physical or Fortran scale,
124  * and is 1 greater than the array element used in the code, which is
125  * on the C scale */
126  if( energy < 1. )
127  {
128  fprintf(ioQQQ , "%li\t%.3e\t%s\n" , ipLine_ret , energy , chLabel);
129  }
130  else if( energy < 10. )
131  {
132  fprintf(ioQQQ , "%li\t%.3f\t%s\n" , ipLine_ret , energy , chLabel);
133  }
134  else if( energy < 100. )
135  {
136  fprintf(ioQQQ , "%li\t%.2f\t%s\n" , ipLine_ret , energy , chLabel);
137  }
138  else
139  {
140  fprintf(ioQQQ , "%li\t%.1f\t%s\n" , ipLine_ret , energy , chLabel);
141  }
142  }
143  }
144 
145  if( prt.lgPrnLineCell )
146  {
147  /* print line cell option - number on command line is cell on Physics scale */
148  if( prt.nPrnLineCell == ipLine_ret )
149  {
150  static bool lgMustPrintHeader = true;
151  if( lgMustPrintHeader )
152  fprintf(ioQQQ, "Lines within cell %li (physics scale) \nLabel\tEnergy(Ryd)\n",prt.nPrnLineCell );
153  lgMustPrintHeader = false;
154  fprintf(ioQQQ,"%s\t%.3e\n" , chLabel , energy );
155  }
156  }
157  return ipLine_ret;
158 }
159 
160 /*ipFineCont returns array index within fine energy mesh */
162  /* energy in Ryd */
163  double energy_ryd )
164 {
165  long int ipoint_v;
166 
167  DEBUG_ENTRY( "ipFineCont()" );
168 
169  if( energy_ryd < rfield.fine_ener_lo || energy_ryd > rfield.fine_ener_hi )
170  {
171  return -1;
172  }
173 
174  /* this is on the Fortran scale of array index counting, so is one above the
175  * c scale. later the -1 will appear on any index references
176  *
177  * 07 Jun 22 testing done to confirm that energy grid is correct: did
178  * same sim with standard fine continuum resolution, and another with 200x
179  * finer resolution, and confirmed that these line up correctly. */
180  ipoint_v = (long int)(log10(energy_ryd*(1.-rfield.fine_resol/2.) /
181  rfield.fine_ener_lo)/log10(1.+rfield.fine_resol));
182 
183  ASSERT( ipoint_v >= 0 && ipoint_v< rfield.nfine );
184  return ipoint_v;
185 }
double emm() const
Definition: mesh.h:93
long int * line_count
Definition: rfield.h:59
realnum lgPrtContIndices_hi_E
Definition: prt.h:203
vector< string > chContLabel
Definition: rfield.h:213
long int nPrnLineCell
Definition: prt.h:256
long ipFineCont(double energy_ryd)
FILE * ioQQQ
Definition: cddefines.cpp:7
double fine_resol
Definition: rfield.h:389
long ipoint(double energy_ryd)
Definition: cont_ipoint.cpp:15
bool lgPrnLineCell
Definition: prt.h:253
long ipContEnergy(double energy, const char *chLabel)
Definition: cont_ipoint.cpp:31
double energy(const genericState &gs)
bool lgPrtContIndices
Definition: prt.h:199
long ipLineEnergy(double energy, const char *chLabel, long ipIonEnergy)
Definition: cont_ipoint.cpp:68
t_rfield rfield
Definition: rfield.cpp:9
#define EXIT_FAILURE
Definition: cddefines.h:168
#define cdEXIT(FAIL)
Definition: cddefines.h:482
size_t ipointF(double anu) const
Definition: mesh.h:168
static bool lgMustPrintHeader
Definition: save_line.cpp:270
vector< string > chLineLabel
Definition: rfield.h:210
t_prt prt
Definition: prt.cpp:14
realnum fine_ener_lo
Definition: rfield.h:385
#define ASSERT(exp)
Definition: cddefines.h:613
realnum fine_ener_hi
Definition: rfield.h:385
long nfine
Definition: rfield.h:387
#define DEBUG_ENTRY(funcname)
Definition: cddefines.h:723
double egamry() const
Definition: mesh.h:97
int fprintf(const Output &stream, const char *format,...)
Definition: service.cpp:1121
realnum lgPrtContIndices_lo_E
Definition: prt.h:203
void ShowMe(void)
Definition: service.cpp:205