PostGIS  2.5.0beta2dev-r@@SVN_REVISION@@

◆ RASTER_mapAlgebraExpr()

Datum RASTER_mapAlgebraExpr ( PG_FUNCTION_ARGS  )

Create a new empty raster with having the same georeference as the provided raster

If this new raster is empty (width = 0 OR height = 0) then there is nothing to compute and we return it right now

Check if the raster has the required band. Otherwise, return a raster without band

We set the initial value of the future band to nodata value. If nodata value is null, then the raster will be initialized to rt_band_get_min_value but all the values should be recomputed anyway

Set the new pixeltype

Optimization: If a nodataval is provided, use it for newinitialvalue. Then, we can initialize the raster with this value and skip the computation of nodata values one by one in the main computing loop

Optimization: If the raster is only filled with nodata values return right now a raster filled with the newinitialvalue TODO: Call rt_band_check_isnodata instead?

Optimization: If expression resume to 'RAST' and hasnodataval is zero, we can just return the band from the original raster

Optimization: If expression resume to a constant (it does not contain [rast)

Compute the new value, set it and we will return after creating the new raster

Create the raster receiving all the computed values. Initialize it to the new initial value

Optimization: If expression is NULL, or all the pixels could be set in one step, return the initialized raster now

We compute a value only for the withdata value pixel since the nodata value has already been set by the first optimization

Definition at line 4410 of file rtpg_mapalgebra.c.

References ovdump::band, ES_NONE, FALSE, FLT_NEQ, rt_raster_serialized_t::height, pixval::nband, PG_FUNCTION_INFO_V1(), POSTGIS_RT_DEBUG, POSTGIS_RT_DEBUGF, PT_END, r, rtrowdump::raster, RASTER_DEBUG, RASTER_mapAlgebraFct(), rt_band_get_hasnodata_flag(), rt_band_get_isnodata_flag(), rt_band_get_min_value(), rt_band_get_nodata(), rt_band_get_pixel(), rt_band_get_pixtype(), rt_band_set_pixel(), rt_pixtype_index_from_name(), rt_pixtype_name(), rt_raster_copy_band(), rt_raster_deserialize(), rt_raster_destroy(), rt_raster_generate_new_band(), rt_raster_get_band(), rt_raster_get_height(), rt_raster_get_num_bands(), rt_raster_get_srid(), rt_raster_get_width(), rt_raster_get_x_offset(), rt_raster_get_x_scale(), rt_raster_get_x_skew(), rt_raster_get_y_offset(), rt_raster_get_y_scale(), rt_raster_get_y_skew(), rt_raster_has_band(), rt_raster_is_empty(), rt_raster_new(), rt_raster_serialize(), rt_raster_set_offsets(), rt_raster_set_scale(), rt_raster_set_skews(), rt_raster_set_srid(), rtpg_strreplace(), rt_raster_serialized_t::size, text_to_cstring(), TRUE, rt_raster_serialized_t::width, pixval::x, and pixval::y.

Referenced by RASTER_colorMap().

4411 {
4412  rt_pgraster *pgraster = NULL;
4413  rt_pgraster *pgrtn = NULL;
4414  rt_raster raster = NULL;
4415  rt_raster newrast = NULL;
4416  rt_band band = NULL;
4417  rt_band newband = NULL;
4418  int x, y, nband, width, height;
4419  double r;
4420  double newnodatavalue = 0.0;
4421  double newinitialvalue = 0.0;
4422  double newval = 0.0;
4423  char *newexpr = NULL;
4424  char *initexpr = NULL;
4425  char *expression = NULL;
4426  int hasnodataval = 0;
4427  double nodataval = 0.;
4428  rt_pixtype newpixeltype;
4429  int skipcomputation = 0;
4430  int len = 0;
4431  const int argkwcount = 3;
4432  enum KEYWORDS { kVAL=0, kX=1, kY=2 };
4433  char *argkw[] = {"[rast]", "[rast.x]", "[rast.y]"};
4434  Oid argkwtypes[] = { FLOAT8OID, INT4OID, INT4OID };
4435  int argcount = 0;
4436  Oid argtype[] = { FLOAT8OID, INT4OID, INT4OID };
4437  uint8_t argpos[3] = {0};
4438  char place[12];
4439  int idx = 0;
4440  int ret = -1;
4441  TupleDesc tupdesc;
4442  SPIPlanPtr spi_plan = NULL;
4443  SPITupleTable * tuptable = NULL;
4444  HeapTuple tuple;
4445  char * strFromText = NULL;
4446  Datum *values = NULL;
4447  Datum datum = (Datum)NULL;
4448  char *nulls = NULL;
4449  bool isnull = FALSE;
4450  int i = 0;
4451  int j = 0;
4452 
4453  POSTGIS_RT_DEBUG(2, "RASTER_mapAlgebraExpr: Starting...");
4454 
4455  /* Check raster */
4456  if (PG_ARGISNULL(0)) {
4457  elog(NOTICE, "Raster is NULL. Returning NULL");
4458  PG_RETURN_NULL();
4459  }
4460 
4461 
4462  /* Deserialize raster */
4463  pgraster = (rt_pgraster *)PG_DETOAST_DATUM(PG_GETARG_DATUM(0));
4464  raster = rt_raster_deserialize(pgraster, FALSE);
4465  if (NULL == raster) {
4466  PG_FREE_IF_COPY(pgraster, 0);
4467  elog(ERROR, "RASTER_mapAlgebraExpr: Could not deserialize raster");
4468  PG_RETURN_NULL();
4469  }
4470 
4471  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: Getting arguments...");
4472 
4473  if (PG_ARGISNULL(1))
4474  nband = 1;
4475  else
4476  nband = PG_GETARG_INT32(1);
4477 
4478  if (nband < 1)
4479  nband = 1;
4480 
4481 
4482  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: Creating new empty raster...");
4483 
4488  width = rt_raster_get_width(raster);
4489  height = rt_raster_get_height(raster);
4490 
4491  newrast = rt_raster_new(width, height);
4492 
4493  if ( NULL == newrast ) {
4494  PG_FREE_IF_COPY(pgraster, 0);
4495  elog(ERROR, "RASTER_mapAlgebraExpr: Could not create a new raster");
4496  PG_RETURN_NULL();
4497  }
4498 
4499  rt_raster_set_scale(newrast,
4500  rt_raster_get_x_scale(raster),
4501  rt_raster_get_y_scale(raster));
4502 
4503  rt_raster_set_offsets(newrast,
4504  rt_raster_get_x_offset(raster),
4505  rt_raster_get_y_offset(raster));
4506 
4507  rt_raster_set_skews(newrast,
4508  rt_raster_get_x_skew(raster),
4509  rt_raster_get_y_skew(raster));
4510 
4511  rt_raster_set_srid(newrast, rt_raster_get_srid(raster));
4512 
4513 
4518  if (rt_raster_is_empty(newrast))
4519  {
4520  elog(NOTICE, "Raster is empty. Returning an empty raster");
4521  rt_raster_destroy(raster);
4522  PG_FREE_IF_COPY(pgraster, 0);
4523 
4524  pgrtn = rt_raster_serialize(newrast);
4525  rt_raster_destroy(newrast);
4526  if (NULL == pgrtn) {
4527 
4528  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4529  PG_RETURN_NULL();
4530  }
4531 
4532  SET_VARSIZE(pgrtn, pgrtn->size);
4533  PG_RETURN_POINTER(pgrtn);
4534  }
4535 
4536 
4537  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: Getting raster band %d...", nband);
4538 
4543  if (!rt_raster_has_band(raster, nband - 1)) {
4544  elog(NOTICE, "Raster does not have the required band. Returning a raster "
4545  "without a band");
4546  rt_raster_destroy(raster);
4547  PG_FREE_IF_COPY(pgraster, 0);
4548 
4549  pgrtn = rt_raster_serialize(newrast);
4550  rt_raster_destroy(newrast);
4551  if (NULL == pgrtn) {
4552  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4553  PG_RETURN_NULL();
4554  }
4555 
4556  SET_VARSIZE(pgrtn, pgrtn->size);
4557  PG_RETURN_POINTER(pgrtn);
4558  }
4559 
4560  /* Get the raster band */
4561  band = rt_raster_get_band(raster, nband - 1);
4562  if ( NULL == band ) {
4563  elog(NOTICE, "Could not get the required band. Returning a raster "
4564  "without a band");
4565  rt_raster_destroy(raster);
4566  PG_FREE_IF_COPY(pgraster, 0);
4567 
4568  pgrtn = rt_raster_serialize(newrast);
4569  rt_raster_destroy(newrast);
4570  if (NULL == pgrtn) {
4571  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4572  PG_RETURN_NULL();
4573  }
4574 
4575  SET_VARSIZE(pgrtn, pgrtn->size);
4576  PG_RETURN_POINTER(pgrtn);
4577  }
4578 
4579  /*
4580  * Get NODATA value
4581  */
4582  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: Getting NODATA value for band...");
4583 
4584  if (rt_band_get_hasnodata_flag(band)) {
4585  rt_band_get_nodata(band, &newnodatavalue);
4586  }
4587 
4588  else {
4589  newnodatavalue = rt_band_get_min_value(band);
4590  }
4591 
4592  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: NODATA value for band: = %f",
4593  newnodatavalue);
4594 
4600  newinitialvalue = newnodatavalue;
4601 
4605  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: Setting pixeltype...");
4606 
4607  if (PG_ARGISNULL(2)) {
4608  newpixeltype = rt_band_get_pixtype(band);
4609  }
4610 
4611  else {
4612  strFromText = text_to_cstring(PG_GETARG_TEXT_P(2));
4613  newpixeltype = rt_pixtype_index_from_name(strFromText);
4614  pfree(strFromText);
4615  if (newpixeltype == PT_END)
4616  newpixeltype = rt_band_get_pixtype(band);
4617  }
4618 
4619  if (newpixeltype == PT_END) {
4620  PG_FREE_IF_COPY(pgraster, 0);
4621  elog(ERROR, "RASTER_mapAlgebraExpr: Invalid pixeltype");
4622  PG_RETURN_NULL();
4623  }
4624 
4625  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: Pixeltype set to %s",
4626  rt_pixtype_name(newpixeltype));
4627 
4628 
4629  /* Construct expression for raster values */
4630  if (!PG_ARGISNULL(3)) {
4631  expression = text_to_cstring(PG_GETARG_TEXT_P(3));
4632  len = strlen("SELECT (") + strlen(expression) + strlen(")::double precision");
4633  initexpr = (char *)palloc(len + 1);
4634 
4635  strncpy(initexpr, "SELECT (", strlen("SELECT ("));
4636  strncpy(initexpr + strlen("SELECT ("), expression, strlen(expression));
4637  strncpy(initexpr + strlen("SELECT (") + strlen(expression), ")::double precision", strlen(")::double precision"));
4638  initexpr[len] = '\0';
4639 
4640  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: Expression is %s", initexpr);
4641 
4642  /* We don't need this memory */
4643  /*
4644  pfree(expression);
4645  expression = NULL;
4646  */
4647  }
4648 
4649 
4650 
4656  if (!PG_ARGISNULL(4)) {
4657  hasnodataval = 1;
4658  nodataval = PG_GETARG_FLOAT8(4);
4659  newinitialvalue = nodataval;
4660 
4661  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: new initial value = %f",
4662  newinitialvalue);
4663  }
4664  else
4665  hasnodataval = 0;
4666 
4667 
4668 
4674  if (rt_band_get_isnodata_flag(band)) {
4675 
4676  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: Band is a nodata band, returning "
4677  "a raster filled with nodata");
4678 
4679  ret = rt_raster_generate_new_band(newrast, newpixeltype,
4680  newinitialvalue, TRUE, newnodatavalue, 0);
4681 
4682  /* Free memory */
4683  if (initexpr)
4684  pfree(initexpr);
4685  rt_raster_destroy(raster);
4686  PG_FREE_IF_COPY(pgraster, 0);
4687 
4688  /* Serialize created raster */
4689  pgrtn = rt_raster_serialize(newrast);
4690  rt_raster_destroy(newrast);
4691  if (NULL == pgrtn) {
4692  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4693  PG_RETURN_NULL();
4694  }
4695 
4696  SET_VARSIZE(pgrtn, pgrtn->size);
4697  PG_RETURN_POINTER(pgrtn);
4698  }
4699 
4700 
4705  if (initexpr != NULL && ( !strcmp(initexpr, "SELECT [rast]") || !strcmp(initexpr, "SELECT [rast.val]") ) && !hasnodataval) {
4706 
4707  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: Expression resumes to RAST. "
4708  "Returning raster with band %d from original raster", nband);
4709 
4710  POSTGIS_RT_DEBUGF(4, "RASTER_mapAlgebraExpr: New raster has %d bands",
4711  rt_raster_get_num_bands(newrast));
4712 
4713  rt_raster_copy_band(newrast, raster, nband - 1, 0);
4714 
4715  POSTGIS_RT_DEBUGF(4, "RASTER_mapAlgebraExpr: New raster now has %d bands",
4716  rt_raster_get_num_bands(newrast));
4717 
4718  pfree(initexpr);
4719  rt_raster_destroy(raster);
4720  PG_FREE_IF_COPY(pgraster, 0);
4721 
4722  /* Serialize created raster */
4723  pgrtn = rt_raster_serialize(newrast);
4724  rt_raster_destroy(newrast);
4725  if (NULL == pgrtn) {
4726  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4727  PG_RETURN_NULL();
4728  }
4729 
4730  SET_VARSIZE(pgrtn, pgrtn->size);
4731  PG_RETURN_POINTER(pgrtn);
4732  }
4733 
4738  if (initexpr != NULL && strstr(initexpr, "[rast") == NULL) {
4739  ret = SPI_connect();
4740  if (ret != SPI_OK_CONNECT) {
4741  PG_FREE_IF_COPY(pgraster, 0);
4742  elog(ERROR, "RASTER_mapAlgebraExpr: Could not connect to the SPI manager");
4743  PG_RETURN_NULL();
4744  };
4745 
4746  /* Execute the expresion into newval */
4747  ret = SPI_execute(initexpr, FALSE, 0);
4748 
4749  if (ret != SPI_OK_SELECT || SPI_tuptable == NULL || SPI_processed != 1) {
4750 
4751  /* Free memory allocated out of the current context */
4752  if (SPI_tuptable)
4753  SPI_freetuptable(tuptable);
4754  PG_FREE_IF_COPY(pgraster, 0);
4755 
4756  SPI_finish();
4757  elog(ERROR, "RASTER_mapAlgebraExpr: Invalid construction for expression");
4758  PG_RETURN_NULL();
4759  }
4760 
4761  tupdesc = SPI_tuptable->tupdesc;
4762  tuptable = SPI_tuptable;
4763 
4764  tuple = tuptable->vals[0];
4765  newexpr = SPI_getvalue(tuple, tupdesc, 1);
4766  if ( ! newexpr ) {
4767  POSTGIS_RT_DEBUG(3, "Constant expression evaluated to NULL, keeping initvalue");
4768  newval = newinitialvalue;
4769  } else {
4770  newval = atof(newexpr);
4771  }
4772 
4773  SPI_freetuptable(tuptable);
4774 
4775  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: New raster value = %f",
4776  newval);
4777 
4778  SPI_finish();
4779 
4780  skipcomputation = 1;
4781 
4786  if (!hasnodataval) {
4787  newinitialvalue = newval;
4788  skipcomputation = 2;
4789  }
4790 
4791  /* Return the new raster as it will be before computing pixel by pixel */
4792  else if (FLT_NEQ(newval, newinitialvalue)) {
4793  skipcomputation = 2;
4794  }
4795  }
4796 
4801  ret = rt_raster_generate_new_band(newrast, newpixeltype,
4802  newinitialvalue, TRUE, newnodatavalue, 0);
4803 
4808  /*if (initexpr == NULL || skipcomputation == 2) {*/
4809  if (expression == NULL || skipcomputation == 2) {
4810 
4811  /* Free memory */
4812  if (initexpr)
4813  pfree(initexpr);
4814  rt_raster_destroy(raster);
4815  PG_FREE_IF_COPY(pgraster, 0);
4816 
4817  /* Serialize created raster */
4818  pgrtn = rt_raster_serialize(newrast);
4819  rt_raster_destroy(newrast);
4820  if (NULL == pgrtn) {
4821  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4822  PG_RETURN_NULL();
4823  }
4824 
4825  SET_VARSIZE(pgrtn, pgrtn->size);
4826  PG_RETURN_POINTER(pgrtn);
4827  }
4828 
4829  RASTER_DEBUG(3, "RASTER_mapAlgebraExpr: Creating new raster band...");
4830 
4831  /* Get the new raster band */
4832  newband = rt_raster_get_band(newrast, 0);
4833  if ( NULL == newband ) {
4834  elog(NOTICE, "Could not modify band for new raster. Returning new "
4835  "raster with the original band");
4836 
4837  if (initexpr)
4838  pfree(initexpr);
4839  rt_raster_destroy(raster);
4840  PG_FREE_IF_COPY(pgraster, 0);
4841 
4842  /* Serialize created raster */
4843  pgrtn = rt_raster_serialize(newrast);
4844  rt_raster_destroy(newrast);
4845  if (NULL == pgrtn) {
4846  elog(ERROR, "RASTER_mapAlgebraExpr: Could not serialize raster");
4847  PG_RETURN_NULL();
4848  }
4849 
4850  SET_VARSIZE(pgrtn, pgrtn->size);
4851  PG_RETURN_POINTER(pgrtn);
4852  }
4853 
4854  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: Main computing loop (%d x %d)",
4855  width, height);
4856 
4857  if (initexpr != NULL) {
4858  /* Convert [rast.val] to [rast] */
4859  newexpr = rtpg_strreplace(initexpr, "[rast.val]", "[rast]", NULL);
4860  pfree(initexpr); initexpr=newexpr;
4861 
4862  sprintf(place,"$1");
4863  for (i = 0, j = 1; i < argkwcount; i++) {
4864  len = 0;
4865  newexpr = rtpg_strreplace(initexpr, argkw[i], place, &len);
4866  pfree(initexpr); initexpr=newexpr;
4867  if (len > 0) {
4868  argtype[argcount] = argkwtypes[i];
4869  argcount++;
4870  argpos[i] = j++;
4871 
4872  sprintf(place, "$%d", j);
4873  }
4874  else {
4875  argpos[i] = 0;
4876  }
4877  }
4878 
4879  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: initexpr = %s", initexpr);
4880 
4881  /* define values */
4882  values = (Datum *) palloc(sizeof(Datum) * argcount);
4883  if (values == NULL) {
4884 
4885  SPI_finish();
4886 
4887  rt_raster_destroy(raster);
4888  PG_FREE_IF_COPY(pgraster, 0);
4889  rt_raster_destroy(newrast);
4890 
4891  elog(ERROR, "RASTER_mapAlgebraExpr: Could not allocate memory for value parameters of prepared statement");
4892  PG_RETURN_NULL();
4893  }
4894 
4895  /* define nulls */
4896  nulls = (char *)palloc(argcount);
4897  if (nulls == NULL) {
4898 
4899  SPI_finish();
4900 
4901  rt_raster_destroy(raster);
4902  PG_FREE_IF_COPY(pgraster, 0);
4903  rt_raster_destroy(newrast);
4904 
4905  elog(ERROR, "RASTER_mapAlgebraExpr: Could not allocate memory for null parameters of prepared statement");
4906  PG_RETURN_NULL();
4907  }
4908 
4909  /* Connect to SPI and prepare the expression */
4910  ret = SPI_connect();
4911  if (ret != SPI_OK_CONNECT) {
4912 
4913  if (initexpr)
4914  pfree(initexpr);
4915  rt_raster_destroy(raster);
4916  PG_FREE_IF_COPY(pgraster, 0);
4917  rt_raster_destroy(newrast);
4918 
4919  elog(ERROR, "RASTER_mapAlgebraExpr: Could not connect to the SPI manager");
4920  PG_RETURN_NULL();
4921  };
4922 
4923  /* Type of all arguments is FLOAT8OID */
4924  spi_plan = SPI_prepare(initexpr, argcount, argtype);
4925 
4926  if (spi_plan == NULL) {
4927 
4928  rt_raster_destroy(raster);
4929  PG_FREE_IF_COPY(pgraster, 0);
4930  rt_raster_destroy(newrast);
4931 
4932  SPI_finish();
4933 
4934  pfree(initexpr);
4935 
4936  elog(ERROR, "RASTER_mapAlgebraExpr: Could not prepare expression");
4937  PG_RETURN_NULL();
4938  }
4939  }
4940 
4941  for (x = 0; x < width; x++) {
4942  for(y = 0; y < height; y++) {
4943  ret = rt_band_get_pixel(band, x, y, &r, NULL);
4944 
4949  if (ret == ES_NONE && FLT_NEQ(r, newnodatavalue)) {
4950  if (skipcomputation == 0) {
4951  if (initexpr != NULL) {
4952  /* Reset the null arg flags. */
4953  memset(nulls, 'n', argcount);
4954 
4955  for (i = 0; i < argkwcount; i++) {
4956  idx = argpos[i];
4957  if (idx < 1) continue;
4958  idx--;
4959 
4960  if (i == kX ) {
4961  /* x is 0 based index, but SQL expects 1 based index */
4962  values[idx] = Int32GetDatum(x+1);
4963  nulls[idx] = ' ';
4964  }
4965  else if (i == kY) {
4966  /* y is 0 based index, but SQL expects 1 based index */
4967  values[idx] = Int32GetDatum(y+1);
4968  nulls[idx] = ' ';
4969  }
4970  else if (i == kVAL ) {
4971  values[idx] = Float8GetDatum(r);
4972  nulls[idx] = ' ';
4973  }
4974 
4975  }
4976 
4977  ret = SPI_execute_plan(spi_plan, values, nulls, FALSE, 0);
4978  if (ret != SPI_OK_SELECT || SPI_tuptable == NULL ||
4979  SPI_processed != 1) {
4980  if (SPI_tuptable)
4981  SPI_freetuptable(tuptable);
4982 
4983  SPI_freeplan(spi_plan);
4984  SPI_finish();
4985 
4986  pfree(values);
4987  pfree(nulls);
4988  pfree(initexpr);
4989 
4990  rt_raster_destroy(raster);
4991  PG_FREE_IF_COPY(pgraster, 0);
4992  rt_raster_destroy(newrast);
4993 
4994  elog(ERROR, "RASTER_mapAlgebraExpr: Error executing prepared plan");
4995 
4996  PG_RETURN_NULL();
4997  }
4998 
4999  tupdesc = SPI_tuptable->tupdesc;
5000  tuptable = SPI_tuptable;
5001 
5002  tuple = tuptable->vals[0];
5003  datum = SPI_getbinval(tuple, tupdesc, 1, &isnull);
5004  if ( SPI_result == SPI_ERROR_NOATTRIBUTE ) {
5005  POSTGIS_RT_DEBUGF(3, "Expression for pixel %d,%d (value %g) errored, skip setting", x+1,y+1,r);
5006  newval = newinitialvalue;
5007  }
5008  else if ( isnull ) {
5009  POSTGIS_RT_DEBUGF(3, "Expression for pixel %d,%d (value %g) evaluated to NULL, skip setting", x+1,y+1,r);
5010  newval = newinitialvalue;
5011  } else {
5012  newval = DatumGetFloat8(datum);
5013  }
5014 
5015  SPI_freetuptable(tuptable);
5016  }
5017 
5018  else
5019  newval = newinitialvalue;
5020 
5021  POSTGIS_RT_DEBUGF(3, "RASTER_mapAlgebraExpr: new value = %f",
5022  newval);
5023  }
5024 
5025 
5026  rt_band_set_pixel(newband, x, y, newval, NULL);
5027  }
5028 
5029  }
5030  }
5031 
5032  if (initexpr != NULL) {
5033  SPI_freeplan(spi_plan);
5034  SPI_finish();
5035 
5036  pfree(values);
5037  pfree(nulls);
5038  pfree(initexpr);
5039  }
5040  else {
5041  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: no SPI cleanup");
5042  }
5043 
5044 
5045  /* The newrast band has been modified */
5046 
5047  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: raster modified, serializing it.");
5048  /* Serialize created raster */
5049 
5050  rt_raster_destroy(raster);
5051  PG_FREE_IF_COPY(pgraster, 0);
5052 
5053  pgrtn = rt_raster_serialize(newrast);
5054  rt_raster_destroy(newrast);
5055  if (NULL == pgrtn)
5056  PG_RETURN_NULL();
5057 
5058  SET_VARSIZE(pgrtn, pgrtn->size);
5059 
5060  POSTGIS_RT_DEBUG(3, "RASTER_mapAlgebraExpr: raster serialized");
5061 
5062 
5063  POSTGIS_RT_DEBUG(4, "RASTER_mapAlgebraExpr: returning raster");
5064 
5065 
5066  PG_RETURN_POINTER(pgrtn);
5067 }
char * text_to_cstring(const text *textptr)
void * rt_raster_serialize(rt_raster raster)
Return this raster in serialized form.
Definition: rt_serialize.c:521
double rt_raster_get_x_offset(rt_raster raster)
Get raster x offset, in projection units.
Definition: rt_raster.c:213
double rt_raster_get_y_skew(rt_raster raster)
Get skew about the Y axis.
Definition: rt_raster.c:190
uint16_t rt_raster_get_num_bands(rt_raster raster)
Definition: rt_raster.c:372
char * r
Definition: cu_in_wkt.c:24
raster
Be careful!! Zeros function&#39;s input parameter can be a (height x width) array, not (width x height): ...
Definition: rtrowdump.py:121
void rt_raster_set_skews(rt_raster raster, double skewX, double skewY)
Set skews about the X and Y axis.
Definition: rt_raster.c:168
char * rtpg_strreplace(const char *str, const char *oldstr, const char *newstr, int *count)
Definition: rtpg_internal.c:55
band
Definition: ovdump.py:57
rt_pixtype
Definition: librtcore.h:185
int rt_raster_is_empty(rt_raster raster)
Return TRUE if the raster is empty.
Definition: rt_raster.c:1334
#define POSTGIS_RT_DEBUGF(level, msg,...)
Definition: rtpostgis.h:65
rt_errorstate rt_band_get_nodata(rt_band band, double *nodata)
Get NODATA value.
Definition: rt_band.c:1730
nband
Definition: pixval.py:52
rt_errorstate rt_band_get_pixel(rt_band band, int x, int y, double *value, int *nodata)
Get pixel value.
Definition: rt_band.c:1221
void rt_raster_set_scale(rt_raster raster, double scaleX, double scaleY)
Set scale in projection units.
Definition: rt_raster.c:137
int rt_raster_generate_new_band(rt_raster raster, rt_pixtype pixtype, double initialvalue, uint32_t hasnodata, double nodatavalue, int index)
Generate a new inline band and add it to a raster.
Definition: rt_raster.c:485
rt_pixtype rt_pixtype_index_from_name(const char *pixname)
Definition: rt_pixel.c:80
void rt_raster_set_offsets(rt_raster raster, double x, double y)
Set insertion points in projection units.
Definition: rt_raster.c:199
rt_band rt_raster_get_band(rt_raster raster, int bandNum)
Return Nth band, or NULL if unavailable.
Definition: rt_raster.c:381
int rt_raster_copy_band(rt_raster torast, rt_raster fromrast, int fromindex, int toindex)
Copy one band from one raster to another.
Definition: rt_raster.c:1370
#define FLT_NEQ(x, y)
Definition: librtcore.h:2233
int rt_band_get_hasnodata_flag(rt_band band)
Get hasnodata flag value.
Definition: rt_band.c:674
double rt_raster_get_x_scale(rt_raster raster)
Get scale X in projection units.
Definition: rt_raster.c:150
int rt_raster_has_band(rt_raster raster, int nband)
Return TRUE if the raster has a band of this number.
Definition: rt_raster.c:1347
void rt_raster_set_srid(rt_raster raster, int32_t srid)
Set raster&#39;s SRID.
Definition: rt_raster.c:363
int32_t rt_raster_get_srid(rt_raster raster)
Get raster&#39;s SRID.
Definition: rt_raster.c:356
void rt_raster_destroy(rt_raster raster)
Release memory associated to a raster.
Definition: rt_raster.c:82
double rt_raster_get_y_scale(rt_raster raster)
Get scale Y in projection units.
Definition: rt_raster.c:159
rt_raster rt_raster_new(uint32_t width, uint32_t height)
Construct a raster with given dimensions.
Definition: rt_raster.c:48
double rt_raster_get_x_skew(rt_raster raster)
Get skew about the X axis.
Definition: rt_raster.c:181
uint16_t rt_raster_get_width(rt_raster raster)
Definition: rt_raster.c:121
#define FALSE
Definition: dbfopen.c:168
#define RASTER_DEBUG(level, msg)
Definition: librtcore.h:295
Struct definitions.
Definition: librtcore.h:2250
double rt_band_get_min_value(rt_band band)
Returns the minimal possible value for the band according to the pixel type.
Definition: rt_band.c:1745
const char * rt_pixtype_name(rt_pixtype pixtype)
Definition: rt_pixel.c:110
rt_pixtype rt_band_get_pixtype(rt_band band)
Return pixeltype of this band.
Definition: rt_band.c:631
int rt_band_get_isnodata_flag(rt_band band)
Get isnodata flag value.
Definition: rt_band.c:714
rt_errorstate rt_band_set_pixel(rt_band band, int x, int y, double val, int *converted)
Set single pixel&#39;s value.
Definition: rt_band.c:974
uint16_t rt_raster_get_height(rt_raster raster)
Definition: rt_raster.c:129
#define POSTGIS_RT_DEBUG(level, msg)
Definition: rtpostgis.h:61
unsigned char uint8_t
Definition: uthash.h:79
#define TRUE
Definition: dbfopen.c:169
rt_raster rt_raster_deserialize(void *serialized, int header_only)
Return a raster from a serialized form.
Definition: rt_serialize.c:717
double rt_raster_get_y_offset(rt_raster raster)
Get raster y offset, in projection units.
Definition: rt_raster.c:222
Here is the call graph for this function:
Here is the caller graph for this function: