gphys 1.5.0 → 1.5.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (94) hide show
  1. checksums.yaml +7 -0
  2. data/ChangeLog +7414 -0
  3. data/LICENSE.txt +1 -1
  4. data/Rakefile +0 -2
  5. data/doc/derivative/math-doc/document/images.log +385 -0
  6. data/doc/ep_flux/math-doc/document/images.log +1375 -0
  7. data/doc/ganalysis/doc/NumRu.html +203 -0
  8. data/doc/ganalysis/doc/NumRu/GAnalysis.html +931 -0
  9. data/doc/ganalysis/doc/NumRu/GAnalysis/BetaPlane.html +574 -0
  10. data/doc/ganalysis/doc/NumRu/GAnalysis/Fitting.html +576 -0
  11. data/doc/ganalysis/doc/NumRu/GAnalysis/LogP.html +425 -0
  12. data/doc/ganalysis/doc/NumRu/GAnalysis/Met.html +2021 -0
  13. data/doc/ganalysis/doc/NumRu/GAnalysis/MetZ.html +524 -0
  14. data/doc/ganalysis/doc/NumRu/GAnalysis/Planet.html +1047 -0
  15. data/doc/ganalysis/doc/NumRu/GAnalysis/QG.html +794 -0
  16. data/doc/ganalysis/doc/NumRu/GAnalysis/QG/Uninitialized.html +215 -0
  17. data/doc/ganalysis/doc/NumRu/GAnalysis/QG_common.html +603 -0
  18. data/doc/ganalysis/doc/NumRu/GAnalysis/QG_sphere.html +760 -0
  19. data/doc/ganalysis/doc/NumRu/GAnalysis/QG_sphere_common.html +251 -0
  20. data/doc/ganalysis/doc/NumRu/GAnalysis/QG_sphere_div.html +424 -0
  21. data/doc/ganalysis/doc/NumRu/GAnalysis/SigmaCoord.html +321 -0
  22. data/doc/ganalysis/doc/NumRu/GGraph.html +334 -0
  23. data/doc/ganalysis/doc/NumRu/GPhys.html +579 -0
  24. data/doc/ganalysis/doc/Object.html +210 -0
  25. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/beta_plane_rb.html +60 -0
  26. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/covariance_rb.html +56 -0
  27. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/eof_rb.html +64 -0
  28. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/fitting_rb.html +54 -0
  29. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/histogram_rb.html +58 -0
  30. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/log_p_rb.html +60 -0
  31. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/met_rb.html +60 -0
  32. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/met_z_rb.html +58 -0
  33. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/planet_rb.html +58 -0
  34. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/qg_rb.html +64 -0
  35. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis/sigma_coord_rb.html +56 -0
  36. data/doc/ganalysis/doc/__/__/lib/numru/ganalysis_rb.html +98 -0
  37. data/doc/ganalysis/doc/created.rid +13 -0
  38. data/doc/ganalysis/doc/images/brick.png +0 -0
  39. data/doc/ganalysis/doc/images/brick_link.png +0 -0
  40. data/doc/ganalysis/doc/images/bug.png +0 -0
  41. data/doc/ganalysis/doc/images/bullet_black.png +0 -0
  42. data/doc/ganalysis/doc/images/bullet_toggle_minus.png +0 -0
  43. data/doc/ganalysis/doc/images/bullet_toggle_plus.png +0 -0
  44. data/doc/ganalysis/doc/images/date.png +0 -0
  45. data/doc/ganalysis/doc/images/find.png +0 -0
  46. data/doc/ganalysis/doc/images/loadingAnimation.gif +0 -0
  47. data/doc/ganalysis/doc/images/macFFBgHack.png +0 -0
  48. data/doc/ganalysis/doc/images/package.png +0 -0
  49. data/doc/ganalysis/doc/images/page_green.png +0 -0
  50. data/doc/ganalysis/doc/images/page_white_text.png +0 -0
  51. data/doc/ganalysis/doc/images/page_white_width.png +0 -0
  52. data/doc/ganalysis/doc/images/plugin.png +0 -0
  53. data/doc/ganalysis/doc/images/ruby.png +0 -0
  54. data/doc/ganalysis/doc/images/tag_green.png +0 -0
  55. data/doc/ganalysis/doc/images/wrench.png +0 -0
  56. data/doc/ganalysis/doc/images/wrench_orange.png +0 -0
  57. data/doc/ganalysis/doc/images/zoom.png +0 -0
  58. data/doc/ganalysis/doc/index.html +383 -0
  59. data/doc/ganalysis/doc/js/darkfish.js +118 -0
  60. data/doc/ganalysis/doc/js/jquery.js +32 -0
  61. data/doc/ganalysis/doc/js/quicksearch.js +114 -0
  62. data/doc/ganalysis/doc/js/thickbox-compressed.js +10 -0
  63. data/doc/ganalysis/doc/rdoc.css +763 -0
  64. data/ext/numru/gphys/ext_init.c +1 -0
  65. data/ext/numru/gphys/quad_mesh_sample.c +478 -0
  66. data/gphys.gemspec +2 -2
  67. data/lib/numru/dclext.rb +394 -14
  68. data/lib/numru/derivative.rb +6 -0
  69. data/lib/numru/ganalysis/qg.rb +6 -4
  70. data/lib/numru/ggraph.rb +41 -8
  71. data/lib/numru/gphys/gphys.rb +62 -14
  72. data/lib/numru/gphys/gphys_io.rb +4 -4
  73. data/lib/numru/gphys/version.rb +2 -2
  74. metadata +84 -79
  75. data/.gitignore +0 -14
  76. data/TODO_ep_flux +0 -6
  77. data/gphys-bigmem.gemspec +0 -44
  78. data/install.rb +0 -130
  79. data/sample/cira86_to_nc.rb +0 -122
  80. data/sample/druby_cli1.rb +0 -23
  81. data/sample/druby_cli2.rb +0 -28
  82. data/sample/druby_serv1.rb +0 -30
  83. data/sample/druby_serv2.rb +0 -51
  84. data/sample/ep_flux/demo_NCEP_1.rb +0 -48
  85. data/sample/ep_flux/demo_NCEP_2.rb +0 -57
  86. data/sample/ep_flux/demo_NCEP_3.rb +0 -81
  87. data/sample/ggraph_latlon_labelling_dr002690.rb +0 -159
  88. data/sample/ggraph_mapfit-axes_dr002687.rb +0 -131
  89. data/sample/map_projection.rb +0 -121
  90. data/sample/ncep_theta_coord.rb +0 -79
  91. data/test_old/eof_slp.rb +0 -28
  92. data/test_old/mltbit.dat +0 -0
  93. data/test_old/test_ep_flux.rb +0 -533
  94. data/test_old/test_multibitIO.rb +0 -19
@@ -5,4 +5,5 @@ Init_gphys_ext()
5
5
  init_gphys_interpo();
6
6
  init_gphys_multibitIO();
7
7
  init_gphys_dim_op();
8
+ init_gphys_quad_mesh_sample();
8
9
  }
@@ -0,0 +1,478 @@
1
+ /**
2
+ * Sample an arbitrary quadrilateral mesh with an equally spaced regular grid.
3
+ */
4
+
5
+ #include<stdio.h>
6
+ #include <math.h>
7
+ #include "ruby.h"
8
+ #include "narray.h"
9
+
10
+ #ifndef NARRAY_BIGMEM
11
+ typedef int na_shape_t;
12
+ #endif
13
+
14
+ static double Eps = 1e-10;
15
+
16
+ // sort three pairs of x&y by x
17
+ void sort3pairs(double ax, double bx, double cx, // in
18
+ double ay, double by, double cy, // in
19
+ double *x3, double *y3) // out (len=3, alreadt allocated)
20
+ {
21
+ if ( ax <= bx && ax <= cx ) {
22
+ x3[0]=ax; y3[0]=ay;
23
+ if ( bx <= cx ) {
24
+ x3[1]=bx; y3[1]=by; x3[2]=cx; y3[2]=cy;
25
+ } else {
26
+ x3[1]=cx; y3[1]=cy; x3[2]=bx; y3[2]=by;
27
+ }
28
+ } else if ( bx <= cx ) {
29
+ x3[0]=bx; y3[0]=by;
30
+ if ( ax <= cx ) {
31
+ x3[1]=ax; y3[1]=ay; x3[2]=cx; y3[2]=cy;
32
+ } else {
33
+ x3[1]=cx; y3[1]=cy; x3[2]=ax; y3[2]=ay;
34
+ }
35
+ } else {
36
+ x3[0]=cx; y3[0]=cy;
37
+ if ( bx <= ax ) {
38
+ x3[1]=bx; y3[1]=by; x3[2]=ax; y3[2]=ay;
39
+ } else {
40
+ x3[1]=ax; y3[1]=ay; x3[2]=bx; y3[2]=by;
41
+ }
42
+ }
43
+ }
44
+
45
+ static int idxceil(double x, int limit)
46
+ {
47
+ int idx;
48
+ idx = ceil(x-Eps);
49
+ idx = ( idx >= limit ? idx : limit );
50
+ return idx;
51
+ }
52
+
53
+ static int idxfloor(double x, int limit)
54
+ {
55
+ int idx;
56
+ idx = floor(x+Eps);
57
+ idx = ( idx <= limit ? idx : limit );
58
+ return idx;
59
+ }
60
+
61
+ static double ycrossing(double x0, double x1, double y0, double y1, double x)
62
+ {
63
+ double yc = -999; // negative value considering the positive array indexing
64
+ if (x1!=x0) yc = y0 + (y1-y0)/(x1-x0)*(x-x0);
65
+ return yc;
66
+ }
67
+
68
+ // solve quadratic equation to return a solution which is likely between 0 and 1
69
+ // (if both solutions are between 0 and 1, arbitrary one of them is returned).
70
+ static double solv_quad_0to1(double a, double b, double c){
71
+ double x;
72
+ if ( a == 0 ) {
73
+ if (b == 0){
74
+ return 0.5; // no solution. return a moderate val
75
+ } else {
76
+ return -c/b;
77
+ }
78
+ }
79
+ if ( b*b - 4*a*c < 0) {
80
+ return 0.5; // no solution. return a moderate val
81
+ } else if ( b*b < Eps*fabs(4*a*c) ){ // b ~ 0
82
+ if ( c/a < 0) {
83
+ return 0.5; // likely due to a round-off error
84
+ } else {
85
+ return sqrt(c/a); // must be positive to be between 0 and 1
86
+ }
87
+ } else if ( fabs(4*a*c) < Eps*b*b ) {
88
+ // a ~ 0 or c ~ 0 : determinant is vulnerable to round-off error
89
+ // Taylor expansion -> solutions are -c/b or -b/a+c/b (usu big)
90
+ x = -b/a+c/b;
91
+ if ( x >= -Eps && x <= 1+Eps ) { // rare case
92
+ return x;
93
+ } else {
94
+ return -c/b;
95
+ }
96
+ } else {
97
+ x = ( -b + sqrt(b*b - 4*a*c) ) / (2*a) ;
98
+ if ( x >= -Eps && x <= 1+Eps ) {
99
+ return x;
100
+ } else {
101
+ x = ( -b - sqrt(b*b - 4*a*c) ) / (2*a) ;
102
+ return x;
103
+ }
104
+ }
105
+ }
106
+
107
+ /*
108
+ * Initialize a quadrilateral mesh sampling with an equally-spaced regular grid
109
+ *
110
+ * Prepare for the call of quad_mesh_sample.
111
+ * Using a transformed bilinear interpolation.
112
+ *
113
+ * (IN)
114
+ * * x, y: one-dimensionalized 2D array of ns(minor) * nr (major).
115
+ * Coordinate values of the field value to sample
116
+ * * nx, dx0, d_x: describes the regular grid of x: d0, d0+d_x,..,d0+(nx-1)*d_x.
117
+ * * ny, dy0, d_y: describes the regular grid of y: d0, d0+d_y,..,d0+(ny-1)*d_y.
118
+ * * handle_miss: if true (non zero), data missing in x and y are handled:
119
+ * not to sample if any one vertex of a surrounding quadrilateral is missing.
120
+ * (OUT)
121
+ * * si, ri: specifies the surrounding quadrilateral for the regular grid points
122
+ * * p, q: bilinear interpolation parameter, obtained from quadratic equations
123
+ * to support arbitrary quadrilaterals.
124
+ */
125
+
126
+ static void quad_mesh_sample_init(int ns, int nr, double *x, double *y, // (in)
127
+ int nx, double x0, double d_x, // (in)
128
+ int ny, double y0, double d_y, // (in)
129
+ int handle_miss, double misval, // (in)
130
+ int *si, int *ri, double *p, double *q) // (out)
131
+ {
132
+ int i, is, ir, ix, iy, j;
133
+ int iy0, iy1;
134
+ int imis=-1; // negative value as an invalid (missing) index
135
+ double ax, bx, cx, dx; // c d quadrilateral points
136
+ double ay, by, cy, dy; // a b normalized by x0, d_x, y0, d_y
137
+ double x3[3], y3[3]; // normalized triangle points sorted by x
138
+ double a0, a1, a2, a3, b0, b1 ,b2, b3, a, b, c, xi, yi;
139
+
140
+ //< array initialization >
141
+
142
+ for ( i=0 ; i<nx*ny ; i++ ){
143
+ si[i] = ri[i] = imis;
144
+ p[i] = q[i] = 0.0; // just to avoid non-initialization
145
+ }
146
+
147
+ //< find where each of x-y grid point is in the original mesh >
148
+
149
+ for ( ir=0 ; ir<nr-1 ; ir++ ){
150
+ for ( is=0 ; is<ns-1 ; is++ ){
151
+ if (handle_miss && ( x[is+ns*ir]==misval || x[is+1+ns*ir]==misval ||
152
+ x[is+ns*(ir+1)]==misval || x[is+1+ns*(ir+1)]==misval ||
153
+ y[is+ns*ir]==misval || y[is+1+ns*ir]==misval ||
154
+ y[is+ns*(ir+1)]==misval || y[is+1+ns*(ir+1)]==misval ) ) {
155
+ continue;
156
+ }
157
+
158
+ ax = (x[is + ns*ir] - x0)/d_x;
159
+ bx = (x[is+1 + ns*ir] - x0)/d_x;
160
+ cx = (x[is + ns*(ir+1)] - x0)/d_x;
161
+ dx = (x[is+1 + ns*(ir+1)] - x0)/d_x;
162
+ ay = (y[is + ns*ir] - y0)/d_y;
163
+ by = (y[is+1 + ns*ir] - y0)/d_y;
164
+ cy = (y[is + ns*(ir+1)] - y0)/d_y;
165
+ dy = (y[is+1 + ns*(ir+1)] - y0)/d_y;
166
+
167
+ for(j=0; j<2; j++) {
168
+ if (j==0) {
169
+ sort3pairs(ax, bx, cx, ay, by, cy, x3, y3); // first time
170
+ } else {
171
+ sort3pairs(dx, bx, cx, dy, by, cy, x3, y3); // second time
172
+ }
173
+ for(ix=idxceil(x3[0],0); ix<=idxfloor(x3[2],nx-1); ix++){
174
+ xi = (double) ix; // normalized x grid
175
+ if ( (x3[0]!=x3[1] && ix<=x3[1]) || x3[1]==x3[2] ){
176
+ // consider angle at x3[0],y3[0]
177
+ if ((x3[2]-x3[0])*(y3[1]-y3[0]) - (x3[1]-x3[0])*(y3[2]-y3[0]) < 0) {
178
+ iy0 = idxceil(ycrossing(x3[0],x3[1],y3[0],y3[1],xi), 0);
179
+ iy1 = idxfloor(ycrossing(x3[0],x3[2],y3[0],y3[2],xi), ny-1);
180
+ } else {
181
+ iy0 = idxceil(ycrossing(x3[0],x3[2],y3[0],y3[2],xi), 0);
182
+ iy1 = idxfloor(ycrossing(x3[0],x3[1],y3[0],y3[1],xi), ny-1);
183
+ }
184
+ } else {
185
+ // consider angle at x3[2],y3[2]
186
+ if ((x3[0]-x3[2])*(y3[1]-y3[2]) - (x3[1]-x3[2])*(y3[0]-y3[2]) > 0) {
187
+ iy0 = idxceil(ycrossing(x3[2],x3[1],y3[2],y3[1],xi), 0);
188
+ iy1 = idxfloor(ycrossing(x3[2],x3[0],y3[2],y3[0],xi), ny-1);
189
+ } else {
190
+ iy0 = idxceil(ycrossing(x3[2],x3[0],y3[2],y3[0],xi), 0);
191
+ iy1 = idxfloor(ycrossing(x3[2],x3[1],y3[2],y3[1],xi), ny-1);
192
+ }
193
+ }
194
+ for(iy=iy0; iy<=iy1; iy++){
195
+ si[ix + nx*iy] = is;
196
+ ri[ix + nx*iy] = ir;
197
+ }
198
+ }
199
+ }
200
+ }
201
+ }
202
+
203
+ //< interpolation point >
204
+
205
+ for (i=0; i<nx*ny; i++){
206
+ if (si[i] >= 0) { // then ri[i] >= 0
207
+ xi = (double) (i % nx); // normalized grid x val
208
+ yi = (double) (i / nx); // normalized grid y val
209
+
210
+ is = si[i];
211
+ ir = ri[i];
212
+ ax = (x[is + ns*ir] - x0)/d_x;
213
+ bx = (x[is+1 + ns*ir] - x0)/d_x;
214
+ cx = (x[is + ns*(ir+1)] - x0)/d_x;
215
+ dx = (x[is+1 + ns*(ir+1)] - x0)/d_x;
216
+ ay = (y[is + ns*ir] - y0)/d_y;
217
+ by = (y[is+1 + ns*ir] - y0)/d_y;
218
+ cy = (y[is + ns*(ir+1)] - y0)/d_y;
219
+ dy = (y[is+1 + ns*(ir+1)] - y0)/d_y;
220
+
221
+ // mapping xi = a0 + a1*p + a2*q + a3*p*q where p=0..1 & q=0..1
222
+ // yi = b0 + b1*p + b2*q + b3*p*q
223
+ a0 = ax; // x = ax when p=q=0
224
+ a1 = bx - ax; // x = bx when p=1 & q=0
225
+ a2 = cx - ax; // x = cx when p=0 & q=1
226
+ a3 = dx - bx -cx + ax; // x = dx when p=q=1
227
+ b0 = ay;
228
+ b1 = by - ay;
229
+ b2 = cy - ay;
230
+ b3 = dy - by -cy + ay;
231
+
232
+ // quadratic equation
233
+ a = a3*b2 - a2*b3;
234
+ b = -a3*yi + b3*xi +a3*b0 - a0*b3 + a1*b2 - a2*b1;
235
+ c = -a1*yi + b1*xi +a1*b0 - a0*b1;
236
+ q[i] = solv_quad_0to1(a, b, c);
237
+ if ( a1 + a3*q[i] != 0 ) {
238
+ p[i] = (xi - a2*q[i] - a0) / (a1 + a3*q[i]);
239
+ if (p[i] > 1.0) p[i]=1.0; // abnormal, likely due to round-off error
240
+ if (p[i] < 0.0) p[i]=0.0; // abnormal, likely due to round-off error
241
+ } else if ( b1 + b3*q[i] != 0 ) {
242
+ p[i] = (yi - b2*q[i] - b0) / (b1 + b3*q[i]);
243
+ if (p[i] > 1.0) p[i]=1.0; // abnormal, likely due to round-off error
244
+ if (p[i] < 0.0) p[i]=0.0; // abnormal, likely due to round-off error
245
+ } else {
246
+ p[i] = 0.5; //not uniq.
247
+ }
248
+ }
249
+ }
250
+
251
+ }
252
+
253
+ /*
254
+ * Conduct a quadrilateral mesh sampling with an equally-spaced regular grid
255
+ *
256
+ * Need to call quad_mesh_sample_init to set up.
257
+ *
258
+ * (IN)
259
+ * * z: The field value. One-dimensionalized 2D array of ns(minor) * nr (major).
260
+ * *si, ri, p, q: obtained from quad_mesh_sample_init
261
+ * (OUT)
262
+ * * zg: The interpolated field value.
263
+ * One-dimensionalized 2D array of nx (minor) * ny (major).
264
+ */
265
+
266
+ static void quad_mesh_sample(int ns, int nr, double *z, int nx, int ny, // (in)
267
+ int *si, int *ri, double *p, double *q, double misval, //(in)
268
+ double *zg) // (out)
269
+ {
270
+ int i, is, ir;
271
+ for (i=0; i<nx*ny; i++){
272
+ is = si[i];
273
+ ir = ri[i];
274
+ if (is >= 0 && ir >= 0) {
275
+ zg[i] = (1-p[i])*(1-q[i])*z[is+ns*ir]
276
+ + p[i]*(1-q[i])*z[is+1+ns*ir]
277
+ + (1-p[i])*q[i]*z[is+ns*(ir+1)]
278
+ + p[i]*q[i]*z[is+1+ns*(ir+1)];
279
+ } else {
280
+ zg[i] = misval;
281
+ }
282
+ }
283
+ }
284
+
285
+
286
+ ///////////////////////////////////////////////////////////////////////
287
+ // ruby interface
288
+ ///////////////////////////////////////////////////////////////////////
289
+ /*
290
+ * misval: nil or Numeric(Float)
291
+ */
292
+ VALUE rb_quad_mesh_sample_init(VALUE obj, VALUE x_na, VALUE y_na, // (in)
293
+ VALUE nx_i, VALUE x0_f, VALUE dx_f, // (in)
294
+ VALUE ny_i, VALUE y0_f, VALUE dy_f, // (in)
295
+ VALUE misval_f ) // (in)
296
+ {
297
+ VALUE si_na, ri_na, p_na, q_na; // (out)
298
+ int ns, nr, nx, ny, rank;
299
+ double *x, *y;
300
+ double x0, dx, y0, dy, misval;
301
+ int handle_miss;
302
+ int *si, *ri;
303
+ double *p, *q;
304
+ struct NARRAY *na;
305
+ na_shape_t sh[2];
306
+
307
+ if (!IsNArray(x_na)) rb_raise(rb_eTypeError, "1st arg (x) must be an NArray");
308
+ if (!IsNArray(y_na)) rb_raise(rb_eTypeError, "2nd arg (y) must be an NArray");
309
+
310
+ rank = NA_RANK(x_na);
311
+ if (rank != 2) rb_raise(rb_eArgError, "rank of x is not 2");
312
+ rank = NA_RANK(y_na);
313
+ if (rank != 2) rb_raise(rb_eArgError, "rank of x is not 2");
314
+
315
+ GetNArray( na_cast_object(x_na, NA_DFLOAT), na);
316
+ ns = na->shape[0];
317
+ nr = na->shape[1];
318
+ x = (double *) NA_PTR(na, 0);
319
+
320
+ GetNArray( na_cast_object(y_na, NA_DFLOAT), na);
321
+ if ( ns != na->shape[0] || nr != na->shape[1])
322
+ rb_raise(rb_eArgError, "shapes of x and y do not agree");
323
+ y = (double *) NA_PTR(na, 0);
324
+
325
+ nx = NUM2INT( nx_i );
326
+ ny = NUM2INT( ny_i );
327
+ x0 = NUM2DBL( x0_f );
328
+ dx = NUM2DBL( dx_f );
329
+ y0 = NUM2DBL( y0_f );
330
+ dy = NUM2DBL( dy_f );
331
+
332
+ handle_miss = misval_f != Qnil;
333
+ if (handle_miss) {
334
+ misval = NUM2DBL( misval_f );
335
+ } else {
336
+ misval_f = 0.0; // just to avoid non-nitialization
337
+ }
338
+
339
+ sh[0] = (na_shape_t) nx;
340
+ sh[1] = (na_shape_t) ny;
341
+ si_na = na_make_object(NA_LINT, 2, sh, cNArray);
342
+ si = NA_PTR_TYPE(si_na, int *);
343
+ ri_na = na_make_object(NA_LINT, 2, sh, cNArray);
344
+ ri = NA_PTR_TYPE(ri_na, int *);
345
+ p_na = na_make_object(NA_DFLOAT, 2, sh, cNArray);
346
+ p = NA_PTR_TYPE(p_na, double *);
347
+ q_na = na_make_object(NA_DFLOAT, 2, sh, cNArray);
348
+ q = NA_PTR_TYPE(q_na, double *);
349
+
350
+ quad_mesh_sample_init(ns, nr, x, y, nx, x0, dx, ny, y0, dy, // (in)
351
+ handle_miss, misval, // (in)
352
+ si, ri, p, q);
353
+
354
+ return rb_ary_new3(4, si_na, ri_na, p_na, q_na);
355
+ }
356
+
357
+ VALUE rb_quad_mesh_sample(VALUE obj, VALUE z_na, VALUE si_na, VALUE ri_na,
358
+ VALUE p_na, VALUE q_na, VALUE misval_f)
359
+ {
360
+ VALUE zg_na;
361
+ int ns, nr, nx, ny;
362
+ int *si, *ri;
363
+ double *p, *q, misval, *z, *zg;
364
+ struct NARRAY *na;
365
+ na_shape_t sh[2];
366
+
367
+ GetNArray( na_cast_object(z_na, NA_DFLOAT), na);
368
+ ns = na->shape[0];
369
+ nr = na->shape[1];
370
+ z = (double *) NA_PTR(na, 0);
371
+
372
+ GetNArray( na_cast_object(si_na, NA_DFLOAT), na);
373
+ nx = na->shape[0];
374
+ ny = na->shape[1];
375
+ si = NA_PTR_TYPE(si_na, int *);
376
+ ri = NA_PTR_TYPE(ri_na, int *);
377
+ p = NA_PTR_TYPE(p_na, double *);
378
+ q = NA_PTR_TYPE(q_na, double *);
379
+ misval = NUM2DBL( misval_f );
380
+
381
+ sh[0] = (na_shape_t) nx;
382
+ sh[1] = (na_shape_t) ny;
383
+ zg_na = na_make_object(NA_DFLOAT, 2, sh, cNArray);
384
+ zg = NA_PTR_TYPE(zg_na, double *);
385
+
386
+ quad_mesh_sample(ns, nr, z, nx, ny, si, ri, p, q, misval, zg);
387
+
388
+ return zg_na;
389
+ }
390
+
391
+ void
392
+ init_gphys_quad_mesh_sample()
393
+ {
394
+ static VALUE mNumRu;
395
+ static VALUE cGPhys;
396
+ mNumRu = rb_define_module("NumRu");
397
+ cGPhys = rb_define_class_under(mNumRu, "GPhys", rb_cObject);
398
+ rb_define_singleton_method(cGPhys, "quad_mesh_sample_init",
399
+ rb_quad_mesh_sample_init, 9);
400
+ rb_define_singleton_method(cGPhys, "quad_mesh_sample",
401
+ rb_quad_mesh_sample, 6);
402
+ }
403
+
404
+ /*
405
+ ///////////////////////////////////////////////////////////////////////
406
+ // gcc -Wall -DTESTMAIN -lm -g quad_mesh_sample.c
407
+ ///////////////////////////////////////////////////////////////////////
408
+ #ifdef TESTMAIN
409
+ #include <stdlib.h>
410
+
411
+ int main(int argc, char *argv[]) {
412
+ int ns=21, nr=6; // sizes of the original quadrilateral mesh
413
+ // (ns:minor, nr:major)
414
+ int nx=25, ny=25; // sizes of the regular grid to resample(nx:minor, ny:major)
415
+ double x[ns*nr], y[ns*nr]; // the mesh
416
+ double z[ns*nr], zg[nx*ny]; // orig & resampled values
417
+ double x0=-nr, dx=0.5, y0=-nr, dy=0.5;
418
+ int si[nx*ny], ri[nx*ny];
419
+ double p[nx*ny], q[nx*ny];
420
+ int is,ir,i;
421
+ double r, d, theta, misval=99.99;
422
+
423
+ // polar coordinate
424
+ d = 2.0 * M_PI / (ns - 1.0);
425
+ for ( ir=0 ; ir<nr ; ir++ ){
426
+ r = (double) ir;
427
+ for ( is=0 ; is<ns ; is++ ){
428
+ theta = d*is;
429
+ x[is + ns*ir] = r * cos(theta);
430
+ y[is + ns*ir] = r * sin(theta);
431
+ z[is + ns*ir] = 0.1 * sqrt(r) * sin(2*theta); // wavenum-2 field
432
+ }
433
+ }
434
+
435
+ // prep
436
+ quad_mesh_sample_init(ns, nr, x, y, nx, x0, dx, ny, y0, dy, // (in)
437
+ 0, 0.0, // (in)
438
+ si, ri, p, q);
439
+
440
+ printf("si\n");
441
+ printf(" "); for(i=0;i<nx;i++) printf(" %2d",i);
442
+ printf("\n %2d:",0);
443
+ for (i=0; i<nx*ny; i++){
444
+ printf("%3d",si[i]);
445
+ if ( (i+1) % nx == 0) printf("\n %2d:",(i+1)/nx);
446
+ }
447
+ printf("\nri\n %2d:",0);
448
+ for (i=0; i<nx*ny; i++){
449
+ printf("%3d",ri[i]);
450
+ if ( (i+1) % nx == 0) printf("\n %2d:",(i+1)/nx);
451
+ }
452
+ printf("\n");
453
+
454
+ printf("\nq\n %2d:",0);
455
+ for (i=0; i<nx*ny; i++){
456
+ printf("%5.2f",q[i]);
457
+ if ( (i+1) % nx == 0) printf("\n %2d:",(i+1)/nx);
458
+ }
459
+ printf("\n");
460
+ printf("\np\n %2d:",0);
461
+ for (i=0; i<nx*ny; i++){
462
+ printf("%5.2f",p[i]);
463
+ if ( (i+1) % nx == 0) printf("\n %2d:",(i+1)/nx);
464
+ }
465
+ printf("\n");
466
+
467
+ quad_mesh_sample(ns, nr, z, nx, ny, si, ri, p, q, misval, zg);
468
+
469
+ printf("\nzg\n %2d:",0);
470
+ for (i=0; i<nx*ny; i++){
471
+ printf("%5.2f",zg[i]);
472
+ if ( (i+1) % nx == 0) printf("\n %2d:",(i+1)/nx);
473
+ }
474
+
475
+ return 0;
476
+ }
477
+ #endif
478
+ */