main.c 5.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209
  1. /*
  2. * r3.stats
  3. *
  4. * Copyright (C) 2004-2007 by the GRASS Development Team
  5. * Author(s): Soeren Gebbert
  6. *
  7. * Purpose: Generates volume statistics for raster3d maps.
  8. *
  9. * This program is free software under the GNU General Public
  10. * License (>=v2). Read the file COPYING that comes with GRASS
  11. * for details.
  12. *
  13. */
  14. #include <stdio.h>
  15. #include <stdlib.h>
  16. #include <math.h>
  17. #include <grass/gis.h>
  18. #include <grass/raster3d.h>
  19. #include <grass/glocale.h>
  20. #include "local_proto.h"
  21. int main(int argc, char *argv[])
  22. {
  23. float val_f; /* for misc use */
  24. double val_d; /* for misc use */
  25. stat_table *stats = NULL;
  26. double min, max;
  27. equal_val_array *eqvals = NULL;
  28. unsigned int n = 0, nsteps;
  29. int map_type;
  30. char *infile = NULL;
  31. void *map = NULL;
  32. RASTER3D_Region region;
  33. unsigned int rows, cols, depths;
  34. unsigned int x, y, z;
  35. struct Option *inputfile, *steps;
  36. struct Flag *equal, *counts_only;
  37. struct GModule *module;
  38. G_gisinit(argv[0]);
  39. module = G_define_module();
  40. G_add_keyword(_("raster3d"));
  41. G_add_keyword(_("statistics"));
  42. G_add_keyword(_("voxel"));
  43. module->description = _("Generates volume statistics for 3D raster maps.");
  44. /* Define the different options */
  45. inputfile = G_define_standard_option(G_OPT_R3_INPUT);
  46. steps = G_define_option();
  47. steps->key = "nsteps";
  48. steps->type = TYPE_INTEGER;
  49. steps->required = NO;
  50. steps->answer = "20";
  51. steps->description = _("Number of subranges to collect stats from");
  52. equal = G_define_flag();
  53. equal->key = 'e';
  54. equal->description =
  55. _("Calculate statistics based on equal value groups");
  56. counts_only = G_define_flag();
  57. counts_only->key = 'c';
  58. counts_only->description = _("Only print cell counts");
  59. if (G_parser(argc, argv))
  60. exit(EXIT_FAILURE);
  61. /*Set the defaults */
  62. Rast3d_init_defaults();
  63. /*get the current region */
  64. Rast3d_get_window(&region);
  65. cols = region.cols;
  66. rows = region.rows;
  67. depths = region.depths;
  68. sscanf(steps->answer, "%i", &nsteps);
  69. /* break if the wrong number of subranges are given */
  70. if (nsteps <= 0)
  71. G_fatal_error(_("The number of subranges has to be equal or greater than 1"));
  72. infile = inputfile->answer;
  73. if (NULL == G_find_raster3d(infile, ""))
  74. Rast3d_fatal_error(_("3D raster map <%s> not found"), infile);
  75. map =
  76. Rast3d_open_cell_old(infile, G_find_raster3d(infile, ""), &region,
  77. RASTER3D_TILE_SAME_AS_FILE, RASTER3D_USE_CACHE_DEFAULT);
  78. if (map == NULL)
  79. Rast3d_fatal_error(_("Unable to open 3D raster map <%s>"), infile);
  80. map_type = Rast3d_tile_type_map(map);
  81. /* calculate statistics for groups of equal values */
  82. if ((equal->answer)) {
  83. /*search for equal values */
  84. eqvals = NULL;
  85. n = 0;
  86. for (z = 0; z < depths; z++) {
  87. G_percent(z, depths - 1, 2);
  88. for (y = 0; y < rows; y++) {
  89. for (x = 0; x < cols; x++) {
  90. if (map_type == FCELL_TYPE) {
  91. Rast3d_get_value(map, x, y, z, &val_f, map_type);
  92. if (!Rast3d_is_null_value_num(&val_f, map_type)) {
  93. /*the first entry */
  94. if (eqvals == NULL)
  95. eqvals =
  96. add_equal_val_to_array(eqvals,
  97. (double)val_f);
  98. else
  99. check_equal_value(eqvals, (double)val_f);
  100. n++; /*count non null cells */
  101. }
  102. }
  103. else if (map_type == DCELL_TYPE) {
  104. Rast3d_get_value(map, x, y, z, &val_d, map_type);
  105. if (!Rast3d_is_null_value_num(&val_d, map_type)) {
  106. /*the first entry */
  107. if (eqvals == NULL)
  108. eqvals =
  109. add_equal_val_to_array(eqvals, val_d);
  110. else
  111. check_equal_value(eqvals, val_d);
  112. n++; /*count non null cells */
  113. }
  114. }
  115. }
  116. }
  117. }
  118. if (eqvals) {
  119. /* sort the equal values array */
  120. G_message(_("Sort non-null values"));
  121. heapsort_eqvals(eqvals, eqvals->count);
  122. /* create the statistic table with equal values */
  123. stats = create_stat_table(eqvals->count, eqvals, 0, 0);
  124. /* compute the number of null values */
  125. stats->null->count = rows * cols * depths - n;
  126. free_equal_val_array(eqvals);
  127. }
  128. }
  129. else {
  130. /* create the statistic table based on value ranges */
  131. /* get the range of the map */
  132. Rast3d_range_load(map);
  133. Rast3d_range_min_max(map, &min, &max);
  134. stats = create_stat_table(nsteps, NULL, min, max);
  135. n = 0;
  136. for (z = 0; z < depths; z++) {
  137. G_percent(z, depths - 1, 2);
  138. for (y = 0; y < rows; y++) {
  139. for (x = 0; x < cols; x++) {
  140. if (map_type == FCELL_TYPE) {
  141. Rast3d_get_value(map, x, y, z, &val_f, map_type);
  142. if (!Rast3d_is_null_value_num(&val_f, map_type)) {
  143. check_range_value(stats, (double)val_f);
  144. n++;
  145. }
  146. }
  147. else if (map_type == DCELL_TYPE) {
  148. Rast3d_get_value(map, x, y, z, &val_d, map_type);
  149. if (!Rast3d_is_null_value_num(&val_d, map_type)) {
  150. check_range_value(stats, val_d);
  151. n++;
  152. }
  153. }
  154. }
  155. }
  156. }
  157. /* compute the number of null values */
  158. stats->null->count = rows * cols * depths - n;
  159. }
  160. if(stats) {
  161. /* Compute the volume and percentage */
  162. update_stat_table(stats, &region);
  163. /* Print the statistics to stdout */
  164. print_stat_table(stats, counts_only->answer);
  165. free_stat_table(stats);
  166. }
  167. exit(EXIT_SUCCESS);
  168. }