r3.mapcalc(1grass)
โจ NAME โจ
okay bestie, meet r3.mapcalc(1grass) โ the Raster map calculator. ๐
๐ KEYWORDS ๐
raster, algebra
๐ธ SYNOPSIS ๐ธ
r3.mapcalc
r3.mapcalc --help
r3.mapcalc [-sl] [expression=string] [region=string] [file=name]
[seed=integer] [nprocs=integer] [--overwrite] [--help] [--verbose]
[--quiet] [--ui]
๐ฉ Flags: ๐ฉ
-sโ Generate random seed (result is non-deterministic) [deprecated]
This flag is deprecated and will be removed in a future release. Seeding is automatic or use parameter seed.
-lโ List input and output maps--overwriteโ Allow output files to overwrite existing files--helpโ Print usage summary--verboseโ Verbose module output--quietโ Quiet module output--uiโ Force launching GUI dialog
๐ Parameters: ๐
expression=stringโ Expression to evaluateregion=stringโ The computational region that should be used.- Options:
current,intersect,union - Default:
current current: current uses the current region of the mapsetintersect: intersect computes the intersection region between all input maps and uses the smallest resolutionunion: union computes the union extent of all map regions and uses the smallest resolution
- Options:
file=nameโ File containing expression(s) to evaluateseed=integerโ Seed value for the random number generator- Using the same seed ensures identical results, while a randomly generated seed produces different outcomes in each run.
nprocs=integerโ Number of threads for parallel computing0: use OpenMP default;>0: use nprocs;<0: use MAX-nprocs- Default:
0
๐ DESCRIPTION ๐
r3.mapcalc performs arithmetic on raster map layers. New raster map layers can be created which are arithmetic expressions involving existing raster map layers, integer or floating point constants, and functions. itโs giving calculator but make it cartography. โจ
๐งฎ Program use ๐งฎ
r3.mapcalc expression have the form:
result = expression
where result is the name of a raster map layer to contain the result of the calculation and expression is any legal arithmetic expression involving existing raster map layers (except result itself), integer or floating point constants, and functions known to the calculator. Parentheses are allowed in the expression and may be nested to any depth. result will be created in the userโs current mapset. ๐
As expression= is the first option, it is the default. This means that passing an expression on the command line is possible as long as the expression is quoted and a space is included before the first = sign. Example (โfooโ is the resulting map):
r3.mapcalc "foo = 1"
or:
r3.mapcalc โfoo = 1โ
An unquoted expression (i.e. split over multiple arguments) wonโt work, nor will omitting the space before the = sign:
r3.mapcalc โfoo=1โ
Sorry, <foo> is not a valid parameter
If no options are given, it manufactures "file=-" (which reads from stdin), so you can continue to use e.g.:
r3.mapcalc < file
or:
r3.mapcalc <<EOF
foo = 1
EOF
But unless you need compatibility with previous versions, use file= explicitly, e.g.:
r3.mapcalc file=file
or:
r3.mapcalc file=- <<EOF
foo = 1
EOF
The formula entered to r3.mapcalc by the user is recorded both in the result map title (which appears in the category file for result) and in the history file for result.
Some characters have special meaning to the command shell. If the user is entering input to r3.mapcalc on the command line, expressions should be enclosed within single quotes. See NOTES, below.
โก Operators and order of precedence โก
The following operators are supported:
-โ negation. Type: Arithmetic. Precedence: 12.~โ oneโs complement. Type: Bitwise. Precedence: 12.!โ not. Type: Logical. Precedence: 12.^โ exponentiation. Type: Arithmetic. Precedence: 11.%โ modulus. Type: Arithmetic. Precedence: 10./โ division. Type: Arithmetic. Precedence: 10.*โ multiplication. Type: Arithmetic. Precedence: 10.+โ addition. Type: Arithmetic. Precedence: 9.-โ subtraction. Type: Arithmetic. Precedence: 9.<<โ left shift. Type: Bitwise. Precedence: 8.>>โ right shift. Type: Bitwise. Precedence: 8.>>>โ right shift (unsigned). Type: Bitwise. Precedence: 8.>โ greater than. Type: Logical. Precedence: 7.>=โ greater than or equal. Type: Logical. Precedence: 7.<โ less than. Type: Logical. Precedence: 7.<=โ less than or equal. Type: Logical. Precedence: 7.==โ equal. Type: Logical. Precedence: 6.!=โ not equal. Type: Logical. Precedence: 6.&โ bitwise and. Type: Bitwise. Precedence: 5.|โ bitwise or. Type: Bitwise. Precedence: 4.&&โ logical and. Type: Logical. Precedence: 3.&&&โ logical and[1]. Type: Logical. Precedence: 3.||โ logical or. Type: Logical. Precedence: 2.|||โ logical or[1]. Type: Logical. Precedence: 2.?:โ conditional. Type: Logical. Precedence: 1.
(modulus is the remainder upon division)
[1] The &&& and ||| operators handle null values differently to other operators. See the section entitled NULL support below for more details.
The operators are applied from left to right, with those of higher precedence applied before those with lower precedence. Division by 0 and modulus by 0 are acceptable and give a NULL result. The logical operators give a 1 result if the comparison is true, 0 otherwise.
๐บ๏ธ 3D Grid names ๐บ๏ธ
Anything in the expression which is not a number, operator, or function name is taken to be a 3D grid name. Examples:
volume
x3
3d.his
Most GRASS raster map layers and 3D grids meet this naming convention. However, if a 3D grid has a name which conflicts with the above rule, it should be quoted. For example, the expression
x = a-b
would be interpreted as: x equals a minus b, whereas
x = "a-b"
would be interpreted as: x equals the 3D grid named a-b
Also
x = 3107
would create x filled with the number 3107, while
x = "3107"
would copy the 3D grid 3107 to the 3D grid x.
Quotes are not required unless the 3D grid names look like numbers or contain operators, OR unless the program is run non-interactively. Examples given here assume the program is run interactively. See NOTES, below.
r3.mapcalc will look for the 3D grids according to the userโs current mapset search path. It is possible to override the search path and specify the mapset from which to select the 3D grid. This is done by specifying the 3D grid name in the form:
name@mapset
For example, the following is a legal expression:
result = x@PERMANENT / y@SOILS
The mapset specified does not have to be in the mapset search path. (This method of overriding the mapset search path is common to all GRASS commands, not just r3.mapcalc.)
๐ง The neighborhood modifier ๐ง
3D grids are data base files stored in voxel format, i.e., three-dimensional matrices of float/double values. In r3.mapcalc, 3D grids may be followed by a neighborhood modifier that specifies a relative offset from the current cell being evaluated. The format is map[r,c,d], where r is the row offset, c is the column offset and d is the depth offset. For example, map[1,2,3] refers to the cell one row below, two columns to the right and 3 levels below of the current cell, map[-3,-2,-1] refers to the cell three rows above, two columns to the left and one level below of the current cell, and map[0,1,0] refers to the cell one column to the right of the current cell. This syntax permits the development of neighborhood-type filters within a single 3D grid or across multiple 3D grids.
๐ Functions ๐
The functions currently supported are listed in the table below. The type of the result is indicated in the last column. F means that the functions always results in a floating point value, I means that the function gives an integer result, and * indicates that the result is float if any of the arguments to the function are floating point values and integer if all arguments are integer.
okay so like, the function table is literally the whole vibe of this page, bestie. here's every single function, no cap, with its type if it has one. the type column uses *, F, I โ those are the vibes. don't skip any, they all matter. ๐
abs(x)โ return absolute value of x โ type:*acos(x)โ inverse cosine of x (result is in degrees) โ type:Fasin(x)โ inverse sine of x (result is in degrees) โ type:Fatan(x)โ inverse tangent of x (result is in degrees) โ type:Fatan(x,y)โ inverse tangent of y/x (result is in degrees) โ type:Fceil(x)โ the smallest integral value not less than x โ type:*cos(x)โ cosine of x (x is in degrees) โ type:Fdouble(x)โ convert x to double-precision floating point โ type:Feval([x,y,...,]z)โ evaluate values of listed expr, pass results to zexp(x)โ exponential function of x โ type:Fexp(x,y)โ x to the power y โ type:Ffloat(x)โ convert x to single-precision floating point โ type:Ffloor(x)โ the largest integral value not greater than x โ type:*graph(x,x1,y1[x2,y2..])โ convert the x to a y based on points in a graph โ type:Fgraph2(x,x1[,x2,..],y1[,y2..])โ alternative form ofgraph()โ type:Fifโ decision options: โ type:*if(x)โ 1 if x not zero, 0 otherwiseif(x,a)โ a if x not zero, 0 otherwiseif(x,a,b)โ a if x not zero, b otherwiseif(x,a,b,c)โ a if x > 0, b if x is zero, c if x < 0
int(x)โ convert x to integer [ truncates ] โ type:Iisnull(x)โ check if x = NULLlog(x)โ natural log of x โ type:Flog(x,b)โ log of x base b โ type:Fmax(x,y[,z...])โ largest value of those listed โ type:*median(x,y[,z...])โ median value of those listed โ type:*min(x,y[,z...])โ smallest value of those listed โ type:*mod(x,y)โ return the modulus (the remainder) of x/y โ type:*mode(x,y[,z...])โ mode value of those listed โ type:*nmax(x,y[,z...])โ largest value of those listed, excluding NULLs โ type:*nmedian(x,y[,z...])โ median value of those listed, excluding NULLs โ type:*nmin(x,y[,z...])โ smallest value of those listed, excluding NULLs โ type:*nmode(x,y[,z...])โ mode value of those listed, excluding NULLs โ type:*not(x)โ 1 if x is zero, 0 otherwisepow(x,y)โ x to the power y โ type:*rand(a,b)โ random value x : a <= x < b โ type:*round(x)โ round x to nearest integer โ type:Iround(x,y)โ round x to nearest multiple of yround(x,y,z)โ round x to nearest y*i+z for some integer isin(x)โ sine of x (x is in degrees) โ type:Fsqrt(x)โ square root of x โ type:Ftan(x)โ tangent of x (x is in degrees) โ type:Fxor(x,y)โ exclusive-or (XOR) of x and y โ type:I- Internal variables:
row()โ current row of moving window โ type:Icol()โ current col of moving window โ type:Idepth()โ return current depth โ type:Inrows()โ number of rows in computation region โ type:Incols()โ number of columns in computation region โ type:Indepths()โ number of depth levels in computation region โ type:Ix()โ current x-coordinate of moving window โ type:Fy()โ current y-coordinate of moving window โ type:Fz()โ return current z value โ type:Fewres()โ current east-west resolution โ type:Fnsres()โ current north-south resolution โ type:Ftbres()โ current top-bottom resolution โ type:Farea()โ area of current cell in square meters โ type:Fnull()โ NULL value
Note, that the row(), col() and depth() indexing starts with 1.
Floating point values in the expression โจ
Floating point numbers are totally allowed in the expression, bestie. A floating point number is a number which contains a decimal point:
2.3 12.0 12. .81
Floating point values in the expression are handled in a special way. With arithmetic and logical operators, if either operand is float, the other is converted to float and the result of the operation is float. This means, in particular that division of integers results in a (truncated) integer, while division of floats results in an accurate floating point value. With functions of type * (see table above), the result is float if any argument is float, integer otherwise.
Note: If you calculate with integer numbers, the resulting map will be integer. If you want to get a float result, add the decimal point to integer number(s).
If you want floating point division, at least one of the arguments has to be a floating point value. Multiplying one of them by 1.0 will produce a floating-point result, as will using float():
r3.mapcalc "ratio = float(soil.4 - soil.3) / soil.3)"
NULL support ๐
- Division by zero should result in NULL.
- Modulus by zero should result in NULL.
- NULL-values in any arithmetic or logical operation should result in NULL. (however,
&&&and|||are treated specially, as described below). - The
&&&and|||operators observe the following axioms even when x is NULL:
x &&& false == false
false &&& x == false
x ||| true == true
true ||| x == true
- NULL-values in function arguments should result in NULL (however,
if(),eval()andisnull()are treated specially, as described below). - The
eval()function always returns its last argument - The situation for
if()is:
if(x)
NULL if x is NULL; 0 if x is zero; 1 otherwise
if(x,a)
NULL if x is NULL; a if x is non-zero; 0 otherwise
if(x,a,b)
NULL if x is NULL; a if x is non-zero; b otherwise
if(x,n,z,p)
NULL if x is NULL; n if x is negative;
z if x is zero; p if x is positive
- The (new) function
isnull(x)returns: 1 if x is NULL; 0 otherwise. The (new) functionnull()(which has no arguments) returns an integer NULL. - Non-NULL, but invalid, arguments to functions should result in NULL. Examples:
log(-2)
sqrt(-2)
pow(a,b) where a is negative and b is not an integer
NULL support: Please note that any math performed with NULL cells always results in a NULL value for these cells. If you want to replace a NULL cell on-the-fly, use the isnull() test function in a if-statement.
Example: The users wants the NULL-valued cells to be treated like zeros. To add maps A and B (where B contains NULLs) to get a map C the user can use a construction like:
C = A + if(isnull(B),0,B)
NULL and conditions: ๐
For the one argument form:
if(x) = NULLif x is NULLif(x) = 0if x = 0if(x) = 1otherwise (i.e. x is neither NULL nor 0).
For the two argument form:
if(x,a) = NULLif x is NULLif(x,a) = 0if x = 0if(x,a) = aotherwise (i.e. x is neither NULL nor 0).
For the three argument form:
if(x,a,b) = NULLif x is NULLif(x,a,b) = bif x = 0if(x,a,b) = aotherwise (i.e. x is neither NULL nor 0).
For the four argument form:
if(x,a,b,c) = NULLif x is NULLif(x,a,b,c) = aif x > 0if(x,a,b,c) = bif x = 0if(x,a,b,c) = cif x < 0
More generally, all operators and most functions return NULL if any of their arguments are NULL. The functions if(), isnull() and eval() are exceptions. The function isnull() returns 1 if its argument is NULL and 0 otherwise. If the user wants the opposite, the ! operator, e.g. "!isnull(x)" must be used.
All forms of if() return NULL if the first argument is NULL. The 2, 3 and 4 argument forms of if() return NULL if the "selected" argument is NULL, e.g.:
if(0,a,b) = b regardless of whether a is NULL
if(1,a,b) = a regardless of whether b is NULL
eval() always returns its last argument, so it only returns NULL if the last argument is NULL.
Note: The user cannot test for NULL using the==operator, as that returns NULL if either or both arguments are NULL, i.e. if x and y are both NULL, then"x == y"and"x != y"are both NULL rather than 1 and 0 respectively. The behaviour makes sense if the user considers NULL as representing an unknown quantity. E.g. if x and y are both unknown, then the values of"x == y"and"x != y"are also unknown; if they both have unknown values, the user doesnโt know whether or not they both have the same value.
okay bestie we're back and it's notes time, this is where the real iykyk lore lives ๐
โจ NOTES โจ
๐ธ Usage from command line ๐ธ
okay so if you're typing the expression straight onto the command line, you gotta be so careful โ the UNIX shell is nosy and some characters mean stuff to it:
()>&|
(these are just some of them btw, not the whole list, don't come for me)
The move is to wrap the whole expression in single quotes, like:
'result = volume * 2'
Because bestie, without the quotes, that * โ which means something special to the UNIX shell โ gets altered, and then r3.mapcalc sees something that is not the * you meant. ๐ญ the vibe check fails. just quote it.
๐ Multiple computations ๐
Generally speaking, it's better to fit as much as you possibly can into a single r3.mapcalc command using multi-line input. stack that work, it's giving efficiency. โจ
๐ Backwards compatibility ๐
For backwards compatibility with GRASS 6: if you hand it no options at all, it manufactures file=- for you (which reads from stdin), so you can keep on doing this:
r3.mapcalc < file
or this:
r3.mapcalc <<EOF
foo = 1
EOF
But unless you actually need compatibility with previous GRASS versions, just use file= explicitly, like we said up above. periodt.
Now here's a fun one: when the map name has uppercase letter(s) or a dot โ things that aren't allowed in module option names โ the r3.mapcalc command will also be valid without quotes:
r3.mapcalc volume_A=1
r3.mapcalc volume.1=1
However, this syntax is not recommended, because quotes (like we said above) are more safe. Using quotes is both backwards compatible and valid in the future. ๐ซถ
๐ฆ Interactive input in command line ๐ฆ
For formulas the user types in from standard input (instead of from the command line), there's now a line continuation feature. If you slap a backslash at the end of an input line, r3.mapcalc assumes your formula keeps going on the next input line. And there is no limit โ not to the number of input lines, not to the length of a formula. ๐
go wild.
If the r3.mapcalc formula you entered is very long, the map title will only contain some of it โ but most (if not all) of the formula gets placed into the history file for the result map. so it's not lost fr.
โ ๏ธ heads up: when you enter input to r3.mapcalc non-interactively on the command line, the program will not warn you about overwriting existing map layers. so it is on YOU to take care and assign output raster map names that don't already exist in your current mapsets. no cap, it will just do it. ๐
๐ง 3D GRID mask handling ๐ง
r3.mapcalc follows the common GRASS behavior of raster mask handling, so the mask is only applied when reading an existing GRASS raster map. Which implies that, for example, this command:
r3.mapcalc "volume_amplified = volume * 3"
creates a map with NULL cells for the masked-out cells, if a raster mask is active.
But when you create a map that isn't based on any map at all โ like a map from a constant:
r3.mapcalc "volume_const = 200.0"
the created raster map is limited only by the computation region, and it is not affected by an active raster mask. And that's expected, because (as mentioned above) the mask is only applied when reading, not when writing a raster map.
If you do want the raster mask applied in that case, use an if() function that includes the mask raster, like this (assuming the mask is called MASK):
r3.mapcalc "volume_const = if(MASK, 200.0, null())"
psst โ when you're testing expressions related to mask handling, keep in mind that when the raster mask is active, you don't see data in masked areas even if they are not NULL. See r3.mask for the details. ๐
๐ Random number generator initialization ๐
The pseudo-random number generator that the rand() function uses can be initialised to a specific value with the seed option. This is how you replicate a previous calculation. ๐ฏ
Alternatively, it can be initialised from the system time and the PID using the -r flag. This should result in a different seed being used each time.
Either way, the seed gets written to the map's history, and you can see it with r.info. โจ
If you want other people to be able to verify your results, it's preferable to use the seed option and supply a seed that is either specified in the script or generated from a deterministic process โ like a pseudo-random number generator given an explicit seed. (iconic, reproducible, slay.)
โ ๏ธ note: therand()function will generate a fatal error if neither theseedoption nor the-sflag are given. ๐ญ no seed, no vibes.
๐ EXAMPLES ๐
To compute the average of two 3D grids a and b:
ave = (a + b)/2
To form a weighted average:
ave = (5*a + 3*b)/8.0
To produce a binary representation of the 3D grid a so that category 0 stays 0 and all other categories become 1:
mask = a != 0
This could also be accomplished by:
mask = if(a)
To mask 3D grid b by 3D grid a:
result = if(a,b)
To change all values below 5 to NULL, and keep the value otherwise:
newmap = if(map < 5, null(), map)
The graph() function lets users specify an x-y conversion using pairs of x,y coordinates. In some situations, a transformation from one value to another isn't easily established mathematically, but can be represented by a 2-D graph and then linearly interpolated. graph() is the function that lets you pull this off. ๐
An x-axis value is provided to the graph function along with the associated graph, represented by a series of x,y pairs. The x values must be monotonically increasing (each one larger than or equal to the previous). The graph function linearly interpolates between pairs. Any x value lower than the lowest x value (i.e. the first one) will have the associated y value returned. Any x value higher than the last will likewise have the associated y value returned.
Consider this request:
newmap = graph(map, 1,10, 2,25, 3,50)
X (map) values supplied and y (newmap) values returned:
0, 101, 101.5, 17.52.9, 47.54, 50100, 50
๐ KNOWN ISSUES ๐
okay bestie, listen up, this is the "do not do this" section:
The result variable on the left hand side of the equation should not appear in the expression on the right hand side.
mymap = if( mymap > 0, mymap, 0)
Any maps generated by an r3.mapcalc command only exist after the entire command has completed. All maps are generated concurrently, row-by-row (i.e. there's an implicit for row in rows {...} wrapped around the entire expression). Therefore the #, @, and [ ] operators cannot be used on a map that was generated within the same r3.mapcalc command run.
newmap = oldmap * 3.14
othermap = newmap[-1, 0] / newmap[1, 0]
Continuation lines must end with a \ and have no trailing white space (blanks or tabs). If you do leave white space at the end of continuation lines, the error messages r3.mapcalc produces will be meaningless and the equation will not work the way you intended. ๐ญ This is particularly important for the eval() function.
Currently, there is no comment mechanism in r3.mapcalc. Perhaps adding a capability that would cause the entire line to be ignored when the user inserted a # at the start of a line โ as if it were not present โ would do the trick. ๐
The function should require the user to type "end" or "exit" instead of simply a blank line. This would make separation of multiple scripts separable by white space.
r3.mapcalc does not print a warning in case of operations on NULL cells. It is left to the user to utilize the isnull() function. ๐ซถ
๐ REFERENCES ๐
r.mapcalc: An Algebra for GIS and Image Processing, by Michael Shapiro and Jim Westervelt, U.S. Army Construction Engineering Research Laboratory (March/1991).Performing Map Calculations on GRASS Data: r.mapcalc Program Tutorial, by Marji Larson, Michael Shapiro and Scott Tweddale, U.S. Army Construction Engineering Research Laboratory (December 1991)- Neteler, M. (2001): Volume modelling of soils using GRASS GIS 3D tools. - in: Brovelli, M. (ed.)(2001): The Geomatics Workbook N. 2. Politecnico di Milano, Italy (ISSN 1591-092X) (PDF)
๐ SEE ALSO ๐
g.region, r3.colors, r.mapcalc
๐ AUTHORS ๐
- Tomas Paudits & Jaro Hofierka, funded by GeoModel s.r.o., Slovakia
tpaudits@mailbox.sk,hofierka@geomodel.sk - Glynn Clements
๐ฅ SOURCE CODE ๐ฅ
Available at: r3.mapcalc source code (history)
Accessed: Tuesday Sep 08 11:54:19 2026
Main index | 3D raster index | Topics index | Keywords index | Graphical index | Full index
and that's the whole page, bestie, you made it ๐ this whole thing is from the GRASS Development Team, ยฉ 2003-2026, shipped with GRASS 8.5.0, and the man page itself is r3.mapcalc(1grass) โ go make some maps, you've got this, mwah ๐โจ๐
๐ฆ where this page comes from
- ubuntu stonking: grass-doc 8.5.0-1ubuntu1 ยท GPL-2.0-or-later
- ๐ girlified by deepseek-ai/DeepSeek-V4.1-Flash on : a language model's rewrite of the original, under its terms