units/0000755000176200001440000000000013547072622011424 5ustar liggesusersunits/NAMESPACE0000644000176200001440000000521513547030263012641 0ustar liggesusers# Generated by roxygen2: do not edit by hand S3method("[",mixed_units) S3method("[",units) S3method("[[",units) S3method("units<-",logical) S3method("units<-",mixed_units) S3method("units<-",numeric) S3method("units<-",units) S3method(Math,units) S3method(Ops,mixed_units) S3method(Ops,symbolic_units) S3method(Ops,units) S3method(Summary,units) S3method(all.equal,units) S3method(as.Date,units) S3method(as.POSIXct,units) S3method(as.character,mixed_symbolic_units) S3method(as.character,symbolic_units) S3method(as.data.frame,units) S3method(as.list,units) S3method(as_units,Date) S3method(as_units,POSIXt) S3method(as_units,call) S3method(as_units,character) S3method(as_units,default) S3method(as_units,difftime) S3method(as_units,expression) S3method(as_units,mixed_units) S3method(as_units,name) S3method(as_units,symbolic_units) S3method(as_units,units) S3method(boxplot,units) S3method(c,units) S3method(diff,units) S3method(drop_units,data.frame) S3method(drop_units,mixed_units) S3method(drop_units,units) S3method(format,mixed_units) S3method(format,units) S3method(hist,units) S3method(log10,units) S3method(log2,units) S3method(mean,units) S3method(median,units) S3method(mixed_units,numeric) S3method(mixed_units,units) S3method(plot,units) S3method(print,"units database") S3method(print,mixed_units) S3method(print,units) S3method(quantile,units) S3method(rep,units) S3method(seq,units) S3method(set_units,logical) S3method(set_units,mixed_units) S3method(set_units,numeric) S3method(set_units,units) S3method(str,mixed_units) S3method(str,units) S3method(summary,units) S3method(units,mixed_units) S3method(units,symbolic_units) S3method(units,units) S3method(weighted.mean,units) S3method(with,"units database") export(as.units) export(as_cf) export(as_difftime) export(as_units) export(deparse_unit) export(drop_units) export(install_conversion_constant) export(install_conversion_offset) export(install_symbolic_unit) export(make_unit) export(make_unit_label) export(make_units) export(mixed_units) export(parse_unit) export(remove_symbolic_unit) export(set_units) export(ud_units) export(unitless) export(units_options) export(valid_udunits) export(valid_udunits_prefixes) if(getRversion() >= "3.6.0") { S3method(pillar::type_sum, units) S3method(pillar::type_sum, mixed_units) S3method(pillar::pillar_shaft, units) S3method(pillar::pillar_shaft, mixed_units) S3method(pillar::format_type_sum, type_sum_units) } else { export(type_sum.units) export(type_sum.mixed_units) export(pillar_shaft.units) export(pillar_shaft.mixed_units) export(format_type_sum.type_sum_units) } import(graphics) import(stats) import(utils) importFrom(Rcpp,evalCpp) useDynLib(units) units/demo/0000755000176200001440000000000013203543612012337 5ustar liggesusersunits/demo/ggforce.R0000644000176200001440000000163513203543612014103 0ustar liggesusers# devtools::install_github("thomasp85/ggforce") library(ggforce) library(units) gallon = make_unit("gallon") mtcars$consumption = mtcars$mpg * with(ud_units, mi/gallon) mtcars$power = mtcars$hp * with(ud_units, hp) ggplot(mtcars) + geom_point(aes(power, consumption)) ggplot(mtcars) + geom_point(aes(1/power, 1/consumption)) # to generate figure 1 in vignette: #pdf("fig1.pdf", width = 4, height = 4) library(units) units_options(negative_power = TRUE) gallon = make_unit("gallon") mtcars$consumption = mtcars$mpg * with(ud_units, mi/gallon) mtcars$displacement = mtcars$disp * ud_units[["in"]]^3 units(mtcars$displacement) = with(ud_units, cm^3) units(mtcars$consumption) = with(ud_units, km/l) m = par("mar") m[3] = 0.1 par(mar = m + c(0, .3, 0, 0)) with(mtcars, plot(1/displacement, 1/consumption)) #pdf("fig2.pdf", width = 4, height = 4) library(ggforce) ggplot(mtcars) + geom_point(aes(1/displacement, 1/consumption)) units/demo/year.R0000644000176200001440000000157313203543612013430 0ustar liggesusers# demo illustrating the different year lengths, as available in # NISTunits: library(NISTunits) options(digits=7) NISTyearTOsec(1) / (24 * 3600) # number of mean solar days days in 1 common Gregorian year NISTyearTropicalTOsec(1) / (24 * 3600) # number of mean solar days days in 1 tropical year NISTyearSiderealTOsec(1) / (24 * 3600) # number of mean solar days days in 1 sidereal year NISTyearTropicalTOsec(1) / (24 * 3600) # number of mean solar days days in 1 tropical year NISTyearSiderealTOsec(1) / (24 * 3600) # number of mean solar days days in 1 sidereal year # ... and in udunits2: library(units) as.units(make_unit("common_year"), with(ud_units, d)) as.units(make_unit("leap_year"), with(ud_units, d)) as.units(make_unit("Gregorian_year"), with(ud_units, d)) as.units(make_unit("Julian_year"), with(ud_units, d)) as.units(with(ud_units, yr), with(ud_units, d)) # yr = tropical: units/demo/cf.R0000644000176200001440000000102613203543612013051 0ustar liggesuserslibrary(rvest) r = read_html( "http://cfconventions.org/Data/cf-standard-names/34/build/cf-standard-name-table.html") tb = html_table(r, fill = TRUE) library(units) cf_units = tb[[3]][2][[1]] u = lapply(cf_units, function(x) make_unit(x)) names(u) = substr(tb[[3]][1][[1]], 1, 50) library(udunits2) # does udunits2 understand them? all(sapply(u, udunits2::ud.is.parseable)) # can parse_unit parse them? remove "W m-2 sr-1 (m-1)-1" all(sapply(cf_units[cf_units != "W m-2 sr-1 (m-1)-1"], function(x) class(parse_unit(x))) == "units") units/demo/00Index0000644000176200001440000000031213203543612013465 0ustar liggesuserscf checks that the NetCDF-CF units are all udunits compatible ggforce demonstrates automatic units in default axis labels in ggplot2 year illustrate the year lenghts, for different definitions of year units/tools/0000755000176200001440000000000013306572371012563 5ustar liggesusersunits/tools/winlibs.R0000644000176200001440000000055413306477535014367 0ustar liggesusers# Build against mingw-w64 build of udunits if(!file.exists("../windows/udunits-2.2.20/include/udunits.h")){ if(getRversion() < "3.3.0") setInternet2() download.file("https://github.com/rwinlib/udunits/archive/v2.2.20.zip", "lib.zip", quiet = TRUE) dir.create("../windows", showWarnings = FALSE) unzip("lib.zip", exdir = "../windows") unlink("lib.zip") } units/man/0000755000176200001440000000000013463271333012174 5ustar liggesusersunits/man/Ops.units.Rd0000644000176200001440000000160013230500577014357 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/arith.R \name{Ops.units} \alias{Ops.units} \title{S3 Ops Group Generic Functions for units objects} \usage{ \method{Ops}{units}(e1, e2) } \arguments{ \item{e1}{object of class \code{units}, or something that can be coerced to it by \code{as_units(e1)}} \item{e2}{object of class \code{units}, or something that can be coerced to it by \code{as_units(e2)}, or in case of power a number (integer n or 1/n)} } \value{ object of class \code{units} } \description{ Ops functions for units objects, including comparison, product and divide, add, subtract } \examples{ a <- set_units(1:3, m/s) b <- set_units(1:3, m/s) a + b a * b a / b a <- as_units("kg m-3") b <- set_units(1, kg/m/m/m) a + b a = set_units(1:5, m) a \%/\% a a \%/\% set_units(2) set_units(1:5, m^2) \%/\% set_units(2, m) a \%\% a a \%\% set_units(2 ) } units/man/valid_udunits.Rd0000644000176200001440000000315013337004303015323 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/valid_udunits.R \name{valid_udunits} \alias{valid_udunits} \alias{valid_udunits_prefixes} \title{Get information about valid units} \usage{ valid_udunits(quiet = FALSE) valid_udunits_prefixes(quiet = FALSE) } \arguments{ \item{quiet}{logical, defaults \code{TRUE} to give a message about the location of the udunits database being read.} } \value{ a data frame with columns \code{symbol} , \code{symbol_aliases} , \code{name_singular} , \code{name_singular_aliases} , \code{name_plural} , or \code{name_plural_aliases} , \code{def} , \code{definition} , \code{comment} , \code{dimensionless} and \code{source_xml} } \description{ The returned dataframe is constructed at runtime by reading the xml database that powers unit conversion in [package:udunits2]. Inspect this dataframe to determine what inputs are accepted by \code{as_units} (and the other functions it powers: \code{as_units} , \code{set_units} , \code{units<-}). } \details{ Any entry listed under \code{symbol} , \code{symbol_aliases} , \code{ name_singular} , \code{name_singular_aliases} , \code{name_plural} , or \code{name_plural_aliases} is valid. Additionally, any entry under \code{symbol} or \code{symbol_aliases} may can also contain a valid prefix, as specified by \code{valid_udunits_prefixes()} . Note, this is primarily intended for interactive use, the exact format of the returned dataframe may change in the future. } \examples{ if (requireNamespace("xml2", quietly = TRUE)) { valid_udunits() valid_udunits_prefixes() if(interactive()) View(valid_udunits()) } } units/man/drop_units.Rd0000644000176200001440000000220413463271136014650 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/make_units.R, R/mixed.R \name{drop_units} \alias{drop_units} \alias{drop_units.units} \alias{drop_units.data.frame} \alias{drop_units.mixed_units} \title{Drop Units} \usage{ drop_units(x) \method{drop_units}{units}(x) \method{drop_units}{data.frame}(x) \method{drop_units}{mixed_units}(x) } \arguments{ \item{x}{an object with units metadata.} } \value{ the numeric without any units attributes, while preserving other attributes like dimensions or other classes. } \description{ Drop units attribute and class. } \details{ Equivalent to \code{units(x) <- NULL}, or the pipe-friendly version \code{set_units(x, NULL)}, but \code{drop_units} will fail if the object has no units metadata. Use the alternatives if you want this operation to succeed regardless of the object type. A \code{data.frame} method is also provided, which checks every column and drops units if any. } \examples{ x <- 1 y <- set_units(x, m/s) # this succeeds drop_units(y) set_units(y, NULL) set_units(x, NULL) \dontrun{ # this fails drop_units(x) } df <- data.frame(x=x, y=y) df drop_units(df) } units/man/ud_units.Rd0000644000176200001440000000052413315257050014312 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/valid_udunits.R \docType{data} \name{ud_units} \alias{ud_units} \title{List containing pre-defined units from the udunits2 package.} \format{An object of class \code{NULL} of length 0.} \usage{ ud_units } \description{ Lazy loaded when used } \keyword{datasets} units/man/install_conversion_constant.Rd0000644000176200001440000000317213337004027020304 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/user_conversion.R \name{install_conversion_constant} \alias{install_conversion_constant} \alias{install_conversion_offset} \title{Install a conversion constant or offset between user-defined units.} \usage{ install_conversion_constant(from, to, const) install_conversion_offset(from, to, const) } \arguments{ \item{from}{String for the symbol of the unit being converted from.} \item{to}{String for the symbol of the unit being converted to. One of \code{from} and \code{to} must be an existing unit name.} \item{const}{The constant \eqn{\alpha} in the conversion.} } \description{ Tells the \code{units} package how to convert between units that have a linear relationship, i.e. can be related on the form \eqn{y = \alpha x} (constant) or \eqn{y = \alpha + x} (offset). } \details{ This function handles the very common case where units are related through a linear function, that is, you can convert from one to the other as \eqn{y = \alpha x}. Using this function, you specify that you can go from values of type \code{from} to values of type \code{to} by multiplying by a constant, or adding a constant. } \examples{ # one orange is worth two apples install_symbolic_unit("orange") install_conversion_constant("orange", "apple", 2) # apple = 2 * orange apples <- 2 * as_units("apple") oranges <- 1 * as_units("orange") apples + oranges oranges + apples install_conversion_offset("meter", "newmeter", 1) m = set_units(1:3, meter) n = set_units(1:3, newmeter) m + n n + m } \seealso{ \code{\link{install_symbolic_unit}}, \code{\link{remove_symbolic_unit}} } units/man/tibble.Rd0000644000176200001440000000124513337004173013722 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/misc.R, R/mixed.R \name{tibble} \alias{tibble} \alias{type_sum.units} \alias{format_type_sum.type_sum_units} \alias{pillar_shaft.units} \alias{type_sum.mixed_units} \alias{pillar_shaft.mixed_units} \title{type_sum function for units} \usage{ type_sum.units(x, ...) format_type_sum.type_sum_units(x, width, ...) pillar_shaft.units(x, ...) type_sum.mixed_units(x, ...) pillar_shaft.mixed_units(x, ...) } \arguments{ \item{x}{see \link[pillar]{type_sum}} \item{...}{see \link[pillar]{type_sum}} \item{width}{ignored} } \description{ type_sum function for units pillar_shaft function for units } units/man/seq.units.Rd0000644000176200001440000000163113230477543014420 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/misc.R \name{seq.units} \alias{seq.units} \title{seq method for units objects} \usage{ \method{seq}{units}(from, to, by = ((to - from)/(length.out - 1)), length.out = NULL, along.with = NULL, ...) } \arguments{ \item{from}{see \link[base]{seq}} \item{to}{see \link[base]{seq}} \item{by}{see \link[base]{seq}} \item{length.out}{see \link[base]{seq}} \item{along.with}{see \link[base]{seq}} \item{...}{see \link[base]{seq}} } \description{ seq method for units objects } \details{ arguments with units are converted to have units of the first argument (which is either \code{from} or \code{to}) } \examples{ seq(to = set_units(10, m), by = set_units(1, m), length.out = 5) seq(set_units(10, m), by = set_units(1, m), length.out = 5) seq(set_units(10, m), set_units(19, m)) seq(set_units(10, m), set_units(.1, km), set_units(10000, mm)) } units/man/hist.units.Rd0000644000176200001440000000120513337004027014563 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/plot.R \name{hist.units} \alias{hist.units} \title{histogram for unit objects} \usage{ \method{hist}{units}(x, xlab = NULL, main = paste("Histogram of", xname), ...) } \arguments{ \item{x}{object of class units, for which we want to plot the histogram} \item{xlab}{character; x axis label} \item{main}{character; title of histogram} \item{...}{parameters passed on to \link{hist.default}} } \description{ histogram for unit objects } \examples{ units_options(parse = FALSE) # otherwise we break on the funny symbol! u = set_units(rnorm(100), degree_C) hist(u) } units/man/set_units.Rd0000644000176200001440000000170613463271333014504 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/set_units.R \name{set_units} \alias{set_units} \title{set_units} \usage{ set_units(x, value, ..., mode = units_options("set_units_mode")) } \arguments{ \item{x}{a numeric to be assigned units, or a units object to have units converted} \item{value}{a \code{units} object, or something coercible to one with \code{as_units}. Depending on \code{mode}, the unit is constructed from the supplied bare expression or from the supplied value via standard evaluation.} \item{...}{passed on to \code{as_units}} \item{mode}{if \code{"symbols"} (the default), then unit is constructed from the expression supplied. Otherwise, if\code{mode = "standard"}, standard evaluation is used for the supplied value This argument can be set via a global option \code{units_options(set_units_mode = "standard")}} } \description{ A pipe friendly version of \code{units<-} } \seealso{ \code{\link{as_units}} } units/man/deparse_unit.Rd0000644000176200001440000000106013337004027015134 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/misc.R \name{deparse_unit} \alias{deparse_unit} \alias{as_cf} \title{deparse unit to string in product power form (e.g. km m-2 s-1)} \usage{ deparse_unit(x) as_cf(x) } \arguments{ \item{x}{object of class units} } \value{ length one character vector } \description{ deparse unit to string in product power form (e.g. km m-2 s-1) } \details{ \code{as_cf} is deprecated; use \code{deparse_unit}. } \examples{ u = as_units("kg m-2 s-1", implicit_exponents = TRUE) u deparse_unit(u) } units/man/units.Rd0000644000176200001440000000251413337004027013621 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/conversion.R \name{units} \alias{units} \alias{units<-.numeric} \alias{units<-.units} \alias{units<-.logical} \alias{units.units} \title{Set measurement units on a numeric vector} \usage{ \method{units}{numeric}(x) <- value \method{units}{units}(x) <- value \method{units}{logical}(x) <- value \method{units}{units}(x) } \arguments{ \item{x}{numeric vector, or object of class \code{units}} \item{value}{object of class \code{units} or \code{symbolic_units}, or in the case of \code{set_units} expression with symbols that can be resolved in \link{ud_units} (see examples).} } \value{ object of class \code{units} the units method retrieves the units attribute, which is of class \code{symbolic_units} } \description{ Set measurement units on a numeric vector Convert units retrieve measurement units from \code{units} object } \details{ if \code{value} is of class \code{units} and has a value unequal to 1, this value is ignored unless \code{units_options("simplifiy")} is \code{TRUE}. If \code{simplify} is \code{TRUE}, \code{x} is multiplied by this value. } \examples{ x = 1:3 class(x) units(x) <- as_units("m/s") class(x) y = 2:5 a <- set_units(1:3, m/s) units(a) <- with(ud_units, km/h) a # convert to a mixed_units object: units(a) = c("m/s", "km/h", "km/h") a } units/man/install_symbolic_unit.Rd0000644000176200001440000000273313315257050017072 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/user_conversion.R \name{install_symbolic_unit} \alias{install_symbolic_unit} \alias{remove_symbolic_unit} \title{Define new symbolic units} \usage{ install_symbolic_unit(name, warn = TRUE, dimensionless = TRUE) remove_symbolic_unit(name) } \arguments{ \item{name}{a length 1 character vector that is the unit name or symbol.} \item{warn}{warns if the supplied unit symbol is already a valid unit symbol recognized by udunits.} \item{dimensionless}{logical; if \code{TRUE}, a new dimensionless unit is created, if \code{FALSE} a new base unit is created. Dimensionless units are convertible to other dimensionless units (such as \code{rad}), new base units are not convertible to other existing units.} } \description{ Adding a symbolic unit allows it to be used in \code{as_units}, \code{make_units} and \code{set_units}. No installation is performed if the unit is already known by udunits. } \details{ \code{install_symbolic_unit} installs a new dimensionless unit; these are directly compatible to any other dimensionless unit. To install a new unit that is a scaled or shifted version of an existing unit, use \code{install_conversion_constant} or \code{install_conversion_offset} directly. } \examples{ install_symbolic_unit("person") set_units(1, rad) + set_units(1, person) # that is how dimensionless units work! } \seealso{ \code{\link{install_conversion_constant}}, \code{\link{install_conversion_offset}} } units/man/unitless.Rd0000644000176200001440000000061013203543612014320 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/symbolic_units.R \docType{data} \name{unitless} \alias{unitless} \title{The "unit" type for vectors that are actually dimension-less.} \format{An object of class \code{symbolic_units} of length 2.} \usage{ unitless } \description{ The "unit" type for vectors that are actually dimension-less. } \keyword{datasets} units/man/Math.units.Rd0000644000176200001440000000373513401522640014515 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/math.R \name{Math.units} \alias{Math.units} \title{Mathematical operations for units objects} \usage{ \method{Math}{units}(x, ...) } \arguments{ \item{x}{object of class units} \item{...}{parameters passed on to the Math functions} } \description{ Mathematical operations for units objects } \details{ Logarithms receive a special treatment by the underlying \pkg{udunits2} library. If a natural logarithm is applied to some \code{unit}, the result is \code{ln(re 1 unit)}, which means \emph{natural logarithm referenced to \code{1 unit}}. For base 2 and base 10 logarithms, the output \code{lb(...)} and \code{lg(...)} respectively instead of \code{ln(...)}. This is particularly important for some units that are typically expressed in a logarithmic scale (i.e., \emph{bels}, or, more commonly, \emph{decibels}), such as Watts or Volts. For some of these units, the default \pkg{udunits2} database contains aliases: e.g., \code{BW} (bel-Watts) is an alias of \code{lg(re 1 W)}; \code{Bm} (bel-milliWatts) is an alias of \code{lg(re 0.001 W)}; \code{BV} is an alias of \code{lg(re 1 V)} (bel-Volts), and so on and so forth (see the output of \code{valid_udunits()} for further reference). Additionally, the \pkg{units} package defines \code{B}, the \emph{bel}, by default (because it is not defined by \pkg{udunits2}) as an alias of \code{lg(re 1)}, unless a user-provided XML database already contains a definition of \code{B}, or the \code{define_bel} option is set to \code{FALSE} (see \code{help(units_options)}). } \examples{ # roundings, cummulative functions x <- set_units(sqrt(1:10), m/s) signif(x, 2) cumsum(x) # trigonometry sin(x) # not meaningful x <- set_units(sqrt(1:10), rad) sin(x) cos(x) x <- set_units(seq(0, 1, 0.1), 1) asin(x) acos(x) # logarithms x <- set_units(sqrt(1:10), W) log(x) # base exp(1) log(x, base = 3) log2(x) log10(x) set_units(x, dBW) # decibel-watts set_units(x, dBm) # decibel-milliwatts } units/man/plot.units.Rd0000644000176200001440000000473713337004027014607 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/plot.R \name{plot.units} \alias{plot.units} \alias{make_unit_label} \title{create axis label with appropriate labels} \usage{ make_unit_label(lab, u, sep = units_options("sep"), group = units_options("group"), parse = units_options("parse")) \method{plot}{units}(x, y, xlab = NULL, ylab = NULL, ...) } \arguments{ \item{lab}{length one character; name of the variable to plot} \item{u}{vector of class \code{units}} \item{sep}{length two character vector, defaulting to \code{c("~","~")}, with the white space between unit name and unit symbols, and between subsequent symbols.} \item{group}{length two character vector with grouping symbols, e.g. \code{c("(",")")} for parenthesis, or \code{c("","")} for no group symbols} \item{parse}{logical; indicates whether a parseable expression should be returned (typically needed for super scripts), or a simple character string without special formatting.} \item{x}{object of class units, to plot along the x axis, or, if y is missing, along the y axis} \item{y}{object to plot along the y axis, or missing} \item{xlab}{character; x axis label} \item{ylab}{character; y axis label} \item{...}{other parameters, passed on to \link{plot.default}} } \description{ create axis label with appropriate labels plot unit objects } \details{ \link{units_options} can be used to set and change the defaults for \code{sep}, \code{group} and \code{doParse}. } \examples{ oldpar = par(mar = par("mar") + c(0, .3, 0, 0)) displacement = mtcars$disp * ud_units[["in"]]^3 # an example that would break if parse were (default) TRUE, since 'in' is a reserved word: units_options(parse=FALSE) make_unit_label("displacement", displacement) units_options(parse=TRUE) units(displacement) = with(ud_units, cm^3) weight = mtcars$wt * 1000 * with(ud_units, lb) units(weight) = with(ud_units, kg) plot(weight, displacement) units_options(group = c("(", ")") ) # parenthesis instead of square brackets plot(weight, displacement) units_options(sep = c("~~~", "~"), group = c("", "")) # no brackets; extra space plot(weight, displacement) units_options(sep = c("~", "~~"), group = c("[", "]")) gallon = as_units("gallon") consumption = mtcars$mpg * with(ud_units, mi/gallon) units(consumption) = with(ud_units, km/l) plot(displacement, consumption) # division in consumption units_options(negative_power = TRUE) # division becomes ^-1 plot(displacement, consumption) plot(1/displacement, 1/consumption) par(oldpar) } units/man/as_units.Rd0000644000176200001440000002325413337004303014305 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/conversion.R, R/make_units.R \name{as_units} \alias{as_units} \alias{as_units.default} \alias{as_units.difftime} \alias{make_units} \alias{as_units.character} \alias{as_units.call} \title{convert object to a units object} \usage{ as_units(x, ...) \method{as_units}{default}(x, value = unitless, ...) \method{as_units}{difftime}(x, value, ...) make_units(bare_expression, check_is_valid = TRUE) \method{as_units}{character}(x, check_is_valid = TRUE, implicit_exponents = NULL, force_single_symbol = FALSE, ...) \method{as_units}{call}(x, check_is_valid = TRUE, ...) } \arguments{ \item{x}{object of class units} \item{...}{passed on to other methods} \item{value}{an object of class units, or something coercible to one with \code{as_units}} \item{bare_expression}{a bare R expression describing units. Must be valid R syntax (reserved R syntax words like \code{in} must be backticked)} \item{check_is_valid}{throw an error if all the unit symbols are not either recognized by udunits2 via \code{ud_is_parseable()}, or a custom user defined via \code{install_symbolic_unit()}. If \code{FALSE}, no check for validity is performed.} \item{implicit_exponents}{If the unit string is in product power form (e.g. \code{"km m-2 s-1"}). Defaults to \code{NULL}, in which case a guess is made based on the supplied string. Set to \code{TRUE} or \code{FALSE} if the guess is incorrect.} \item{force_single_symbol}{Whether to perform no string parsing and force treatment of the string as a single symbol.} } \value{ A new unit object that can be used in arithmetic, unit conversion or unit assignment. } \description{ A number of functions are provided for creating unit objects. \itemize{ \item \code{as_units}, a generic with methods for a character string and for quoted language. Note, direct usage of this function by users is typically not necessary, as coercion via \code{as_units} is automatically done with \code{`units<-`} and \code{set_units()}. \item \code{make_units()}, constructs units from bare expressions. \code{make_units(m/s)} is equivalent to \code{as_units(quote(m/s))} \item \code{set_units()}, a pipe_friendly version of \code{`units<-`}. By default it operates with bare expressions like \code{make_unit}, but this behavior can be disabled by a specifying \code{mode = "standard"} or setting \code{units_options(set_units_mode = "standard")}. } } \note{ By default, unit names are automatically substituted with unit names (e.g., kilogram --> kg). To turn off this behavior, set \code{units_options(auto_convert_names_to_symbols = FALSE)} } \section{Character strings}{ Generally speaking, there are 3 types of unit strings are accepted in \code{as_units} (and by extension, \code{`units<-`}). The first, and likely most common, is a "standard" format unit specification where the relationship between unit symbols or names is specified explicitly with arithmetic symbols for division \code{/}, multiplication \code{*} and power exponents \code{^}, or other mathematical functions like \code{log()}. In this case, the string is parsed as an R expression via \code{parse(text = )} after backticking all unit symbols and names, and then passed on to \code{as_units.call()}. A heuristic is used to perform backticking, such that any continuous set of characters uninterrupted by one of \code{()\\*^-} are backticked (unless the character sequence consists solely of numbers \code{0-9}), with some care to not double up on pre-existing backticks. This heuristic appears to be quite robust, and works for units would otherwise not be valid R syntax. For example, percent (\code{"\%"}), feet (\code{"'"}), inches (\code{"in"}), and Tesla (\code{"T"}) are all backticked and parsed correctly. Nevertheless, for certain complex unit expressions, this backticking heuristic may give incorrect results. If the string supplied fails to parse as an R expression, then the string is treated as a single symbolic unit and \code{symbolic_unit(chr)} is used as a fallback with a warning. In that case, automatic unit simplification may not work properly when performing operations on unit objects, but unit conversion and other Math operations should still give correct results so long as the unit string supplied returns \code{TRUE} for \code{ud_is_parsable()}. The second type of unit string accepted is one with implicit exponents. In this format, \code{/}, \code{*}, and \code{^}, may not be present in the string, and unit symbol or names must be separated by a space. Each unit symbol may optionally be followed by a single number, specifying the power. For example \code{"m2 s-2"} is equivalent to \code{"(m^2)*(s^-2)"}. The third type of unit string format accepted is the special case of udunits time duration with a reference origin, for example \code{"hours since 1970-01-01 00:00:00"}. Note, that the handling of time and calendar operations via the udunits library is subtly different from the way R handles date and time operations. This functionality is mostly exported for users that work with udunits time data, e.g., with NetCDF files. Users are otherwise encouraged to use \code{R}'s date and time functionality provided by \code{Date} and \code{POSIXt} classes. } \section{Expressions}{ In \code{as_units()}, each of the symbols in the unit expression is treated individually, such that each symbol must be recognized by the udunits database (checked by \code{ud_is_parseable()}, \emph{or} be a custom, user-defined unit symbol that was defined either by \code{install_symbolic_unit()} or \code{install_conversion_constant()}. To see which symbols and names are currently recognized by the udunits database, see \code{udunits_symbols()}. } \examples{ s = Sys.time() d = s - (s+1) as_units(d) # The easiest way to assign units to a numeric vector is like this: x <- y <- 1:4 units(x) <- "m/s" # meters / second # Alternatively, the easiest pipe-friendly way to set units: if(requireNamespace("magrittr", quietly = TRUE)) { library(magrittr) y \%>\% set_units(m/s) } # these are different ways of creating the same unit: # meters per second squared, i.e, acceleration x1 <- make_units(m/s^2) x2 <- as_units(quote(m/s^2)) x2 <- as_units("m/s^2") x3 <- as_units("m s-2") # in product power form, i.e., implicit exponents = T x4 <- set_units(1, m/s^2) # by default, mode = "symbols" x5 <- set_units(1, "m/s^2", mode = "standard") x6 <- set_units(1, x1, mode = "standard") x7 <- set_units(1, units(x1), mode = "standard") x8 <- as_units("m") / as_units("s")^2 all_identical <- function(...) { l <- list(...) for(i in seq_along(l)[-1]) if(!identical(l[[1]], l[[i]])) return(FALSE) TRUE } all_identical(x1, x2, x3, x4, x5, x6, x7, x8) # Note, direct usage of these unit creation functions is typically not # necessary, since coercion is automatically done via as_units(). Again, # these are all equivalent ways to generate the same result. x1 <- x2 <- x3 <- x4 <- x5 <- x6 <- x7 <- x8 <- 1:4 units(x1) <- "m/s^2" units(x2) <- "m s-2" units(x3) <- quote(m/s^2) units(x4) <- make_units(m/s^2) units(x5) <- as_units(quote(m/s^2)) x6 <- set_units(x6, m/s^2) x7 <- set_units(x7, "m/s^2", mode = "standard") x8 <- set_units(x8, units(x1), mode = "standard") all_identical(x1, x2, x3, x4, x5, x6, x7, x8) # Both unit names or symbols can be used. By default, unit names are # automatically converted to unit symbols. make_units(degree_C) make_units(kilogram) make_units(ohm) # Note, if the printing of non-ascii characters is garbled, then you may # need to specify the encoding on your system manually like this: # ud_set_encoding("latin1") # not all unit names get converted to symbols under different encodings ## Arithmetic operations and units # conversion between unit objects that were defined as symbols and names will # work correctly, although unit simplification in printing may not always occur. x <- 500 * make_units(micrograms/liter) y <- set_units(200, ug/l) x + y x * y # numeric result is correct, but units not simplified completely # note, plural form of unit name accepted too ('liters' vs 'liter'), and # denominator simplification can be performed correctly x * set_units(5, liters) # unit conversion works too set_units(x, grams/gallon) ## Creating custom, user defined units # For example, a microbiologist might work with counts of bacterial cells # make_units(cells/ml) # by default, throws an ERROR # First define the unit, then the newly defined unit is accepted. install_symbolic_unit("cells") make_units(cells/ml) # Note, install_symbolic_unit() does not add any support for unit # conversion, or arithmetic operations that require unit conversion. See # ?install_conversion_constant for defining relationships between user # defined units. ## set_units() # set_units is a pipe friendly version of `units<-`. if(requireNamespace("magrittr", quietly = TRUE)) { library(magrittr) 1:5 \%>\% set_units(N/m^2) # first sets to m, then converts to km 1:5 \%>\% set_units(m) \%>\% set_units(km) } # set_units has two modes of operation. By default, it operates with # bare symbols to define the units. set_units(1:5, m/s) # use `mode = "standard"` to use the value of supplied argument, rather than # the bare symbols of the expression. In this mode, set_units() can be # thought of as a simple alias for `units<-` that is pipe friendly. set_units(1:5, "m/s", mode = "standard") set_units(1:5, make_units(m/s), mode = "standard") # the mode of set_units() can be controlled via a global option # units_options(set_units_mode = "standard") # To remove units use units(x) <- NULL # or set_units(x, NULL) # or drop_units(y) } \seealso{ \code{\link{valid_udunits}} } units/man/mixed_units.Rd0000644000176200001440000000166413337004027015014 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/mixed.R \name{mixed_units} \alias{mixed_units} \alias{units<-.mixed_units} \title{Create or convert to a mixed units list-column} \usage{ mixed_units(x, values, ...) \method{units}{mixed_units}(x) <- value } \arguments{ \item{x}{numeric, or vector of class \code{units}} \item{values}{character vector with units encodings, or list with symbolic units of class \code{mixed_symbolic_units}} \item{...}{ignored} \item{value}{see values} } \description{ Create or convert to a mixed units list-column } \details{ if \code{x} is of class \code{units}, \code{values} should be missing or of class \code{mixed_symbolic_units}; if \code{x} is numeric, \code{values} should be a character vector the length of \code{x}. } \examples{ a <- 1:4 u <- c("m/s", "km/h", "mg/L", "g") mixed_units(a, u) units(a) = as_units("m/s") mixed_units(a) # converts to mixed representation } units/man/deprecated.Rd0000644000176200001440000000077013230500577014564 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/deprecated.R \name{make_unit} \alias{make_unit} \alias{parse_unit} \alias{deprecated} \alias{as.units} \title{Deprecated functions} \usage{ make_unit(chr) parse_unit(chr) as.units(x, value = unitless) } \arguments{ \item{chr}{length 1 character string} \item{x}{a numeric} \item{value}{a units object, by default, unitless} } \description{ The following functions are deprecated and will be removed in a future release. } units/man/units_options.Rd0000644000176200001440000000525113420665743015410 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/options.R \name{units_options} \alias{units_options} \title{set one or more units global options} \usage{ units_options(..., sep, group, negative_power, parse, set_units_mode, auto_convert_names_to_symbols, simplify, allow_mixed, unitless_symbol, define_bel) } \arguments{ \item{...}{named options (character) for which the value is queried} \item{sep}{character length two; default \code{c("~", "~")}; space separator between variable and units, and space separator between two different units} \item{group}{character length two; start and end group, may be two empty strings, a parenthesis pair, or square brackets; default: square brackets.} \item{negative_power}{logical, default \code{FALSE}; should denominators have negative power, or follow a division symbol?} \item{parse}{logical, default \code{TRUE}; should the units be made into an expression (so we get subscripts)? Setting to \code{FALSE} may be useful if \link{parse} fails, e.g. if the unit contains symbols that assume a particular encoding} \item{set_units_mode}{character; either \code{"symbols"} or \code{"standard"}; see \link{set_units}; default is \code{"symbols"}} \item{auto_convert_names_to_symbols}{logical, default \code{TRUE}: should names, such as \code{degree_C} be converted to their usual symbol?} \item{simplify}{logical, default \code{NA}; simplify units in expressions?} \item{allow_mixed}{logical; if \code{TRUE}, combining mixed units creates a \code{mixed_units} object, if \code{FALSE} it generates an error} \item{unitless_symbol}{character; set the symbol to use for unitless (1) units} \item{define_bel}{logical; if \code{TRUE}, define the unit \code{B} (i.e., the \emph{bel}, widely used with the \emph{deci-} prefix as \code{dB}, \emph{decibel}) as an alias of \code{lg(re 1)}. \code{TRUE} by default, unless \code{B} is already defined in the existing XML database.} } \value{ in case options are set, invisibly a named list with the option values that are being set; if an option is queried, the current option value. } \description{ set units global options, mostly related how units are printed and plotted } \details{ This sets or gets units options. Set them by using named arguments, get them by passing the option name. The default \code{NA} value for \code{simplify} means units are not simplified in \link{set_units} or \link{as_units}, but are simplified in arithmetical expressions. } \examples{ old = units_options(sep = c("~~~", "~"), group = c("", "")) # more space, parenthesis old ## set back to defaults: units_options(sep = c("~", "~"), group = c("[", "]"), negative_power = FALSE, parse = TRUE) units_options("group") } units/man/as_difftime.Rd0000644000176200001440000000065313203543612014733 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/conversion.R \name{as_difftime} \alias{as_difftime} \title{convert units object into difftime object} \usage{ as_difftime(x) } \arguments{ \item{x}{object of class \code{units}} } \description{ convert units object into difftime object } \examples{ t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 du <- as_units(d) dt = as_difftime(du) class(dt) dt } units/man/boxplot.units.Rd0000644000176200001440000000121613315260530015304 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/plot.R \name{boxplot.units} \alias{boxplot.units} \title{boxplot for unit objects} \usage{ \method{boxplot}{units}(x, ..., horizontal = FALSE) } \arguments{ \item{x}{object of class units, for which we want to plot the boxplot} \item{...}{parameters passed on to \link{boxplot.default}} \item{horizontal}{logical indicating if the boxplots should be horizontal; default FALSE means vertical boxes.} } \description{ boxplot for unit objects } \examples{ units_options(parse = FALSE) # otherwise we break on the funny symbol! u = set_units(rnorm(100), degree_C) boxplot(u) } units/TODO0000644000176200001440000000227713231415524012114 0ustar liggesusers> install_conversion_offset("tempK", "my_temp_C", 273.15) ut_offset(): NULL unit argumentError in R_ut_offset(as.character(to), as.character(from), as.double(const)) : Error in function R_ut_offset: An argument violates the function's contract make errors friendlier, so it becomes clear what is wrong. 1. first arg does not exist 2. second does already exist help of ?set_units: ... ; mention NSE # This should not occur: > units(b) = "10 m" > b Units: ^10*m [1] 1 2 3 DONE ======================= search path for udunits2.xml: /usr/local/share/udunits/udunits2.xml /usr/share/udunits/udunits2.xml /usr/share/xml/udunits/udunits2.xml /usr/share/udunits/udunits2.xml fallback: system.file("share/udunits2.xml", package="units") set_units(1, g/kg) -> errors -> retain g/g ratio as special case of unitless? # This should be an error: > b = 1:3 > units(b) = "10*m" Warning message: In ‘10 * m’ the numeric multiplier ‘10’ was discarded. The returned unit object was coerced to a value of 1. Use `install_conversion_constant()` to define a new unit that is a multiple of another unit. === resolved # This should not occur: > set_units(1:3, as_units("m")) Units: 1 [1] 1 2 3 ==== resolved units/DESCRIPTION0000644000176200001440000000351413547072622013135 0ustar liggesusersPackage: units Version: 0.6-5 Title: Measurement Units for R Vectors Authors@R: c(person("Edzer", "Pebesma", role = c("aut", "cre"), email = "edzer.pebesma@uni-muenster.de", comment = c(ORCID = "0000-0001-8049-7069")), person("Thomas", "Mailund", role = "aut", email = "mailund@birc.au.dk"), person("Tomasz", "Kalinowski", role = "aut"), person("James", "Hiebert", role = "ctb"), person("Iñaki", "Ucar", role = "ctb", email = "iucar@fedoraproject.org", comment = c(ORCID = "0000-0001-6403-5550")) ) Depends: R (>= 3.0.2) Imports: Rcpp LinkingTo: Rcpp (>= 0.12.10) Suggests: udunits2, NISTunits, measurements, xml2, tibble, pillar (>= 1.3.0), knitr, testthat, ggforce, rmarkdown, magrittr VignetteBuilder: knitr Description: Support for measurement units in R vectors, matrices and arrays: automatic propagation, conversion, derivation and simplification of units; raising errors in case of unit incompatibility. Compatible with the POSIXct, Date and difftime classes. Uses the UNIDATA udunits library and unit database for unit compatibility checking and conversion. Documentation about 'units' is provided in the paper by Pebesma, Mailund & Hiebert (2016, ), included in this package as a vignette; see 'citation("units")' for details. SystemRequirements: udunits-2 License: GPL-2 URL: https://github.com/r-quantities/units/ BugReports: https://github.com/r-quantities/units/issues/ RoxygenNote: 6.1.1 Encoding: UTF-8 NeedsCompilation: yes Packaged: 2019-10-08 06:46:26 UTC; edzer Author: Edzer Pebesma [aut, cre] (), Thomas Mailund [aut], Tomasz Kalinowski [aut], James Hiebert [ctb], Iñaki Ucar [ctb] () Maintainer: Edzer Pebesma Repository: CRAN Date/Publication: 2019-10-08 11:40:02 UTC units/build/0000755000176200001440000000000013547030302012510 5ustar liggesusersunits/build/vignette.rds0000644000176200001440000000041213547030302015044 0ustar liggesusersuAK0m  "z/śeAD)$)7lvnzh2{Ϝ1`qEx7',a{ U=Jg+UY!EhS뿕K>~[~*k%@O\ FgtNj<[0˩$!\ Sh~I2vvrd" )d-;m2:Y7`cz6.ʌ}_ ð;OTwŽF7‰5units/tests/0000755000176200001440000000000013463271333012563 5ustar liggesusersunits/tests/set_units.R0000644000176200001440000000201213463271333014716 0ustar liggesuserslibrary(units) library(testthat) ref = set_units(1, m) # character input expect_equal(set_units(1, "m", mode = "standard"), ref) # units input expect_equal(set_units(1, as_units("m"), mode = "standard"), ref) # symbolic_units input expect_equal(set_units(1, units(ref), mode = "standard"), ref) set_units(1, m/s) # use object from parent frame, non-ambiguous: foo = ref expect_equal(set_units(1, foo, mode = "standard"), ref) foo = "m" expect_equal(set_units(1, foo, mode = "standard"), ref) foo = as_units("m") expect_equal(set_units(1, foo, mode = "standard"), ref) # ambiguous, should warn: m = "u" set_units(1, m) # m by NSE m = as_units("u") set_units(1, m, mode = "standard") # u by units set_units(1, m) # m by NSE degree_C = "m" set_units(1, degree_C) degree_C = as_units("m") set_units(1, degree_C) # OK: set_units(1, "bar", mode = "standard") (tenbar <- set_units(10, bar)) (set_units(1, units(tenbar), mode = "standard")) (set_units(1, tenbar, mode = "standard")) set_units(10, uu <- degree_C, mode = "standard") units/tests/testthat/0000755000176200001440000000000013547072622014426 5ustar liggesusersunits/tests/testthat/test_symbolic_units.R0000644000176200001440000000655013315421215020646 0ustar liggesuserscontext("Symbolic unit manipulation") test_that("we can make symbolic units", { m <- units:::.symbolic_units("m") expect_true(inherits(m, "symbolic_units")) expect_equal(as.character(m), "m") }) test_that("we can multiply and divide symbolic units", { m <- units:::.symbolic_units("m") s <- units:::.symbolic_units("s") expect_equal(as.character(units(units:::.multiply_symbolic_units(1, m, m))), "m^2") expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, s))), "m/s") expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.divide_symbolic_units(1, m, s)), s))), "m/s^2") }) test_that("we can simplify basic units", { m <- units:::.symbolic_units("m") s <- units:::.symbolic_units("s") expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, m))), units_options("unitless_symbol")) opt = units_options(unitless_symbol = "-") expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, m))), "-") units_options(unitless_symbol = opt$unitless_symbol) expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, m))), units_options("unitless_symbol")) expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.divide_symbolic_units(1, m, s)), m))), "1/s") expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.multiply_symbolic_units(1, m, m)), m))), "m") expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.divide_symbolic_units(1, s, m)), s))), "1/m") }) test_that("we can simplify basic units", { m <- units:::.symbolic_units("m") s <- units:::.symbolic_units("s") expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, m))), units_options("unitless_symbol")) expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.divide_symbolic_units(1, m, s)), m))), "1/s") expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.multiply_symbolic_units(1, m, m)), m))), "m") expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.divide_symbolic_units(1, s, m)), s))), "1/m") }) test_that("we can simplify basic units with conversion", { m <- units:::.symbolic_units("m") s <- units:::.symbolic_units("s") km <- units:::.symbolic_units("km") expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, m))), units_options("unitless_symbol")) expect_equal(as.character(units(units:::.divide_symbolic_units(1, m, km))), units_options("unitless_symbol")) expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.divide_symbolic_units(1, m, s)), km))), "1/s") expect_equal(as.character(units(units:::.divide_symbolic_units(1, units(units:::.multiply_symbolic_units(1, m, m)), km))), "m") }) test_that("we can compare units", { g <- as_units("g") m <- as_units("m") s <- as_units("s") d <- as_units("day") e1 <- 1:10 * g * m / s / d e2 <- 1:10 * m / s expect_equal(units:::.same_units(units(e1),units(e1)), TRUE) expect_equal(units:::.same_units(units(e1),units(e2)), FALSE) expect_equal(units(e1) == units(e1), TRUE) expect_equal(units(e1) != units(e1), FALSE) expect_equal(units(e1) == units(e2), FALSE) expect_equal(units(e1) != units(e2), TRUE) }) test_that("symbolic_unit works", { expect_error(units:::symbolic_unit("qqq")) expect_silent(units:::symbolic_unit("m")) }) units/tests/testthat/test_arith.R0000644000176200001440000001231513345735005016716 0ustar liggesuserscontext("Arithmetic") test_that("we can compare vectors with equal units", { x <- 1:4 * as_units("m") y <- 1:4 * as_units("m") z <- 2 * y expect_true(all(x == y)) expect_true(all(x <= y)) expect_true(all(x >= y)) expect_true(all(x < z)) expect_true(all(x <= z)) expect_true(all(z > x)) expect_true(all(z >= x)) expect_false(any(x > y)) expect_false(any(x != y)) expect_true(all(x != z)) }) test_that("we can scale units with scalars", { x <- 1:4 ux <- x * as_units("m") expect_equal(as.numeric(10 * ux), 10 * x) expect_equal(as.numeric(ux / 10), x / 10) }) test_that("we can multiply and divide units", { x <- 1:4 ; y <- 5:8 m <- x * as_units("m") s <- y * as_units("s") expect_equal(as.numeric(m * s), x * y) expect_equal(as.numeric(m / s), x / y) # FIXME: There ought to be a test that the expressions get the right units # but I am not entirely sure how that should be wrapped. Just checking string # equality would give problems if units are equivalent but needs to be converted # first... }) test_that("we can take powers of units", { x <- 1:4 ux <- x * as_units("m") expect_equal(as.numeric(ux ** 2), x ** 2) expect_equal(as.numeric(ux ^ 2), x ^ 2) expect_equal(as.character(units(ux ** 2)), "m^2") expect_equal(as.character(units(ux ^ 2)), "m^2") expect_error(ux ^ 1.3) expect_error(ux ^ 0.3) expect_error(ux ^ ux) # expect_error(ux ^ x) --> see below: gives mixed_units expect_silent(ux ^ x) expect_equal(as.numeric(ux ** -2), x ** -2) expect_equal(as.numeric(ux ^ -2), x ^ -2) expect_equal(as.character(units(ux ** -2)), "1/m^2") expect_equal(as.character(units(ux ^ -2)), "1/m^2") expect_equal(as.numeric(ux ** 0), x ** 0) expect_equal(as.numeric(ux ^ 0), x ^ 0) expect_identical(units(ux ** 0), set_units(1)) expect_identical(units(ux ^ 0), set_units(1)) }) test_that("we support unary +/-", { expect_equal(-set_units(10, m), set_units(-10, m)) expect_equal(+set_units(10, m), set_units(10, m)) }) test_that("we can convert units and simplify after multiplication", { x <- 1:4 y <- 1:4 z <- 1:4 m <- as_units("m") s <- as_units("s") km <- as_units("km") ux <- x * m uy <- y * s uz <- z * km expect_equal(as.numeric(ux/ux), x/x) expect_equal(as.character(units(ux/ux)), units_options("unitless_symbol")) expect_equal(as.numeric(ux*uy), x*y) expect_equal(as.character(units(ux*uy)), "m*s") expect_equal(as.numeric(ux*uz), x*z) expect_equal(as.character(units(ux*uz)), "km*m") expect_equal(as.numeric(set_units(ux*uz, km * km)), (x/1000)*z) expect_equal(as.character(units(set_units(ux*uz, km * km))), "km^2") expect_equal(as.numeric(ux/ux), x/x) expect_equal(as.character(units(ux/ux)), units_options("unitless_symbol")) expect_equal(as.numeric(ux/uy), x/y) expect_equal(as.character(units(ux/uy)), "m/s") expect_equal(as.numeric(ux/uz), x/(1000*z)) expect_equal(as.character(units(ux/uz)), units_options("unitless_symbol")) expect_equal(as.numeric(ux/uy/uz), x/y/z/1000) expect_equal(as.character(units(ux/uy/uz)), "1/s") }) test_that("unit one is handled correctly", { one <- set_units(1) onem <- set_units(1, m) expect_equal(one * one, one) expect_equal(onem * one, onem) expect_equal(one * one * one, one) expect_equal(onem * one * one, onem) expect_equal(one / one, one) expect_equal(onem / one, onem) expect_equal(one ^ 3, one) # expect_equal(one ^ pi, one) # expect_equal(one ^ -pi, one) }) test_that("we can compute powers +/- 1/n for integer n", { expect_equal(as.numeric(set_units(1:10, m^2) ^ 0.5), (1:10) ^ .5) expect_error(as.numeric(set_units(1:10, m^3) ^ 0.5), "units not divisible") expect_error(as.numeric(set_units(1:10, m^3) ^ 1.5)) expect_equal(as.numeric(set_units(1:10, m^-3) ^ (-1/3)), (1:10) ^ (-1/3)) expect_equal(as.numeric(set_units(1:10, m^-2) ^ (-1/2)), (1:10) ^ (-1/2)) expect_equal(as.numeric(set_units(1:10, m^-2) ^ (1/2)), (1:10) ^ (1/2)) expect_error(set_units(1:10, m^2) ^ (1/pi), "not a integer divisor") expect_error(set_units(1:10, m^3) ^ -1.5, "currently you can only take integer powers of units below -1") }) test_that("%*%, %/% and %% work", { a = set_units(1:5, m) expect_equal(a %/% set_units(2, m), set_units(c(0,1,1,2,2))) expect_equal(a %% set_units(2, m), set_units(c(1,0,1,0,1), m)) mat = set_units(matrix(1:5, 1), m) # expect_equal(mat %*% t(mat), set_units(matrix(55), m^2)) # expect_equal(t(mat) %*% mat, set_units(t(unclass(mat)) %*% unclass(mat), m^2)) }) test_that("The order of multiplication for basic units is commutative", { a <- set_units(1:4, m^-3) b <- set_units(1:4, mm) expect_equal(a * b, b * a) expect_true(units(a * b) == units(b * a)) a <- set_units(1:4, m) b <- set_units(1:4, mm) expect_equal(a * b, b * a) expect_true(units(a * b) == units(b * a)) }) test_that("Division gets the right scaling and units", { a <- set_units(1:4, m^-3) b <- set_units(1:4, mm) expect_true(units(a / b) != units(b / a)) expect_equal(a / b, 1/(b / a)) }) test_that("we obtain mixed units when taking powers of multiple integers", { a = set_units(1:4, m) p = 4:1 expect_equal(a ^ p, c(set_units(1, m^4), set_units(8, m^3), set_units(9, m^2), set_units(4, m), allow_mixed=TRUE)) }) units/tests/testthat/test_udunits.R0000644000176200001440000000401713527327534017310 0ustar liggesuserscontext("udunits2") test_that("udunits error messages", { expect_error(set_units(1:3, "qqq"), "qqq") }) test_that("udunits low-level functions work", { expect_silent(units:::R_ut_get_dimensionless_unit_one(character(0))) a <- units:::R_ut_parse("m") b <- units:::R_ut_parse("g") expect_error(units:::R_convert_doubles(a, b, 1:10), "not convertible") u = units:::R_ut_offset("foo", "kg", -10) expect_equal(set_units(set_units(1, kg), foo), set_units(11, foo)) remove_symbolic_unit("foo") expect_silent(units:::R_ut_divide(a, b)) expect_silent(units:::R_ut_multiply(a, b)) expect_silent(units:::R_ut_invert(a)) expect_silent(sq <- units:::R_ut_raise(a, 2L)) expect_error(units:::R_ut_raise(a, 2L:3L), "length 1") expect_silent(units:::R_ut_root(sq, 2L)) expect_error(units:::R_ut_root(a, 2L:3L), "length 1") expect_silent(units:::R_ut_log(a, 10.0)) expect_error(units:::R_ut_log(a, c(2, 10.0)), "length 1") expect_error(units:::R_ut_log(a, -10.0), "positive") expect_silent(units:::R_ut_format(a)) expect_silent(units:::R_ut_format(a, ascii = TRUE)) expect_silent(units:::R_ut_format(sq, names = TRUE)) expect_silent(units:::R_ut_format(sq, definition = TRUE)) expect_silent(units:::R_ut_set_encoding("ascii")) expect_silent(units:::R_ut_set_encoding("iso-8859-1")) expect_silent(units:::R_ut_set_encoding("latin1")) expect_silent(units:::R_ut_set_encoding("utf8")) expect_silent(ud_set_encoding("utf8")) expect_error(units:::R_ut_set_encoding("foo")) expect_error(units:::R_ut_get_symbol("foo"), "string unit representation contains unknown word") expect_error(units:::R_ut_get_name("foo"), "R_ut_get_name") }) test_that("udunits database can be read", { skip_if_not_installed("xml2") expect_message(units:::.message_where_udunits_db(), "udunits") expect_message(valid_udunits(), "udunits") expect_message(valid_udunits_prefixes(), "udunits") # expect_identical(units:::.construct_ud_units(), ud_units) # NOT TRUE -- *ppv not in ud_units? expect_silent(units:::.construct_ud_units()) }) units/tests/testthat/test_mixed.R0000644000176200001440000000337713463271136016726 0ustar liggesuserscontext("Mixed Unit tests") test_that("mixed units work", { (m = c(set_units(1:3, km), set_units(4:6, g), allow_mixed = TRUE)) # select a subset expect_s3_class(m[3:4], "mixed_units") expect_s3_class(m[3], "mixed_units") # select a single units object: expect_s3_class(m[[3]], "units") m <- set_units(m, c(rep(c("m", "kg"), each = 3))) expect_s3_class(m, "mixed_units") units(m) = rep(c("mm", "mg"), each = 3) expect_s3_class(m, "mixed_units") # does the value get recycled? expect_s3_class(set_units(m[1:3], "m"), "mixed_units") # convert to units: expect_s3_class(as_units( m[1:3] ), "units") # round-trip via units: m0 <- mixed_units(as_units(m[1:3])) expect_identical(m[1:3], m0) # Ops using by single unit: needs to be explicitly coerced to mixed_units: expect_s3_class(m[1:3] * mixed_units(set_units(1, mm)), "mixed_units") expect_s3_class(m[1:3] / mixed_units(set_units(1, mm)), "mixed_units") expect_s3_class(m[1:3] + mixed_units(set_units(1, mm)), "mixed_units") expect_s3_class(m[1:3] - mixed_units(set_units(1, mm)), "mixed_units") expect_is(m[1:3] == mixed_units(set_units(1, mm)), "logical") expect_is(m[1:3] != mixed_units(set_units(1, mm)), "logical") expect_error(m[1:3] ^ mixed_units(set_units(1, mm))) # this breaks -- seems to be an s3 limitation: expect_error(m[1:3] * set_units(1, mm)) expect_s3_class(units(m), "mixed_symbolic_units") expect_is(format(m), "character") expect_is(as.character(units(m)), "character") print(m) expect_equal(drop_units(m), sapply(m, as.numeric)) skip_if_not_installed("tibble") print(tibble::tibble(m)) str(m) units_options(allow_mixed = TRUE) m = c(set_units(1:3, km), set_units(4:6, g)) units_options(allow_mixed = FALSE) }) units/tests/testthat/test_summaries.R0000644000176200001440000000306013472516125017612 0ustar liggesuserscontext("Unit summaries") test_that("we can compute summary functions on units", { x <- 1:4 ux <- x * as_units("m") expect_equal(as.numeric(sum(ux)), sum(x)) expect_equal(as.numeric(min(ux)), min(x)) expect_equal(as.numeric(max(ux)), max(x)) expect_equal(as.numeric(range(ux)), range(x)) expect_equal(units(sum(ux)), units(ux)) expect_equal(units(min(ux)), units(ux)) expect_equal(units(max(ux)), units(ux)) expect_equal(units(range(ux)), units(ux)) expect_error(all(ux)) expect_error(sum(ux, x)) y <- 1:4 uy <- y * as_units("km") expect_equal(as.numeric(sum(ux, uy)), sum(c(x, 1000*y))) expect_equal(as.numeric(min(ux, uy)), min(c(x, 1000*y))) expect_equal(as.numeric(max(ux, uy)), max(c(x, 1000*y))) expect_equal(as.numeric(range(ux, uy)), range(c(x, 1000*y))) z <- 1:4 * ud_units$s expect_error(sum(ux, z)) }) test_that("we can compute means and medians and quantiles", { x <- 1:4 ux <- x * as_units("m") w <- x / 5:8 uw <- w * as_units("g") expect_equal(as.numeric(mean(ux)), mean(x)) expect_equal(as.numeric(median(ux)), median(x)) expect_equivalent(as.numeric(quantile(ux)), quantile(x)) expect_equal(as.numeric(weighted.mean(ux, w)), weighted.mean(x, w)) expect_equal(as.numeric(weighted.mean(ux, uw)), weighted.mean(x, w)) }) test_that("we can format units", { x <- 1:4 ux <- x * as_units("m") expect_equal(format(ux), c("1 [m]", "2 [m]", "3 [m]", "4 [m]")) }) test_that("summary works with NA values", { x <- c(1, NA) * as_units("g") expect_equal(summary(x), summary(as.numeric(x))) }) units/tests/testthat/test_math.R0000644000176200001440000000566413401522640016541 0ustar liggesuserscontext("Math functions") test_that("we can call math functions on units", { x <- 1:4 - 2.1 ux <- x * as_units("m") expect_equal(as.numeric(abs(ux)), abs(x)) expect_equal(units(abs(ux)), units(ux)) expect_equal(as.numeric(sign(ux)), sign(x)) expect_true(!inherits(sign(ux), "units")) expect_equal(as.numeric(sqrt(ux^2)), sqrt(x^2)) expect_error(sqrt(ux), "units not divisible") expect_equal(as.numeric(floor(ux)), floor(x)) expect_equal(units(floor(ux)), units(ux)) expect_equal(as.numeric(ceiling(ux)), ceiling(x)) expect_equal(units(ceiling(ux)), units(ux)) expect_equal(as.numeric(trunc(ux)), trunc(x)) expect_equal(units(trunc(ux)), units(ux)) expect_equal(as.numeric(round(ux)), round(x)) expect_equal(units(round(ux)), units(ux)) expect_equal(as.numeric(signif(ux)), signif(x)) expect_equal(units(signif(ux)), units(ux)) expect_equal(as.numeric(cumsum(ux)), cumsum(x)) expect_equal(units(cumsum(ux)), units(ux)) expect_equal(as.numeric(cummax(ux)), cummax(x)) expect_equal(units(cummax(ux)), units(ux)) expect_equal(as.numeric(cummin(ux)), cummin(x)) expect_equal(units(cummin(ux)), units(ux)) expect_warning(y <- cos(ux)) expect_equal(y, cos(x)) expect_equal(class(y), "numeric") expect_equal(sin(set_units(1, rad)), set_units(sin(1))) expect_equal(sin(set_units(90, degree)), sin(set_units(pi/2, rad))) expect_equal(units(acos(set_units(-1))), units(make_units(rad))) expect_equal(set_units(acos(set_units(-1)), degree), set_units(180, degree)) }) test_that("we can take logarithms units", { x <- 1:4 ux <- x * as_units("m") expect_equal(as.numeric(log2(ux)), log2(x)) expect_equal(units(log2(ux)), units(as_units("lb(re 1 m)", force_single_symbol=TRUE))) expect_equal(as.numeric(log(ux, 2)), log(x, 2)) expect_equal(units(log(ux, 2)), units(as_units("lb(re 1 m)", force_single_symbol=TRUE))) expect_equal(as.numeric(log10(ux)), log10(x)) expect_equal(units(log10(ux)), units(as_units("lg(re 1 m)", force_single_symbol=TRUE))) expect_equal(as.numeric(log(ux, 10)), log(x, 10)) expect_equal(units(log(ux, 10)), units(as_units("lg(re 1 m)", force_single_symbol=TRUE))) expect_equal(as.numeric(log1p(ux)), log1p(x)) expect_equal(units(log1p(ux)), units(as_units("ln(re 1 m)", force_single_symbol=TRUE))) expect_equal(as.numeric(log(ux)), log(x)) expect_equal(units(log(ux)), units(as_units("ln(re 1 m)", force_single_symbol=TRUE))) expect_equal(as.numeric(log(ux, exp(2))), log(x, exp(2))) expect_equal(units(log(ux, exp(2))), units(as_units("0.5 ln(re 1 m)", force_single_symbol=TRUE))) }) test_that("decibel is available", { expect_true(units:::ud_is_parseable("B")) units_options(define_bel=FALSE) expect_false(units:::ud_is_parseable("B")) units_options(define_bel=TRUE) expect_true(units:::ud_is_parseable("B")) x <- set_units(set_units(100, 1), dB) expect_equal(as.numeric(x), 20) expect_equal(as.character(units(x)), "dB") }) units/tests/testthat/test_user_conversion.R0000644000176200001440000000603013472516125021030 0ustar liggesuserscontext("User-defined unit conversion") test_that("we can convert between units with a user-defined function", { expect_error(as_units("apple")) expect_error(as_units("orange")) #install_symbolic_unit("apple") -> needs to be defined by install_conversion_constant install_symbolic_unit("orange") oranges <- 3 * as_units("orange") expect_error(apples + oranges) # obviously install_conversion_constant("orange", "apple", 2) # one orange is worth two apples apples <- 2 * as_units("apple") expect_equal(apples + oranges, (2 + 2*3) * as_units("apple")) expect_equal(oranges + apples, (3 + 2/2) * as_units("orange")) # FIXME: expect_equal(oranges + apples, set_units(apples + oranges, oranges, mode = "standard")) # FIXME: expect_equal(apples + oranges, set_units(apples + oranges, apples, mode = "standard")) #install_conversion_constant("orange", "apple", 2, 1) # but you always have to add one #expect_equal(apples + oranges, (2 + 2*3 + 1) * make_unit("apple")) #expect_equal(oranges + apples, (3 + (2 - 1)/2) * make_unit("orange")) #expect_equal(oranges + apples, set_units(apples + oranges, oranges)) # now just checking that we get different results with a different fruit expect_error(as_units("banana")) #install_symbolic_unit("banana") -> need to be done by install_user_conversion expect_error(apples + bananas) # obviously expect_error(bananas + apples) # obviously install_conversion_constant("apple", "banana", 1/3) # one apple only gives you a third banana bananas <- 6 * as_units("banana") expect_equal(bananas + 3 * apples, (6 + 3 * 2 / 3) * as_units("banana")) install_symbolic_unit("aaa") install_conversion_offset("aaa", "bbb", 2) # bbb is aaa + 2 expect_warning(install_symbolic_unit("aaa"), "is already a valid unit") # restore remove_symbolic_unit("orange") remove_symbolic_unit("apple") remove_symbolic_unit("banana") remove_symbolic_unit("aaa") remove_symbolic_unit("bbb") }) test_that("we can simplify via user-defined units", { install_symbolic_unit("orange") install_conversion_constant("orange", "apple", 2) # one orange is worth two apples apples <- 4 * as_units("apple") oranges <- 2 * as_units("orange") expect_equal(apples / oranges, set_units(1)) expect_equal(oranges / apples, set_units(1)) # restore remove_symbolic_unit("orange") remove_symbolic_unit("apple") }) test_that("removing units works", { expect_error(remove_symbolic_unit("foo")) expect_silent(install_symbolic_unit("foo")) expect_silent(remove_symbolic_unit("foo")) expect_error(remove_symbolic_unit("foo")) }) test_that("new units' format is checked for possible issues", { wrong_formats <- c( " 2asdf", "asdf2 ", "as+df", "as-df", "as*df", "as/df", "as^df", "as df") for (i in wrong_formats) { expect_error(install_symbolic_unit(i)) expect_error(install_conversion_constant(i, "m", 2)) expect_error(install_conversion_constant("m", i, 2)) expect_error(install_conversion_offset(i, "m", 2)) expect_error(install_conversion_offset("m", i, 2)) } }) units/tests/testthat/test_misc.R0000644000176200001440000000773513547030247016554 0ustar liggesuserscontext("Misc. utility functions") test_that("We can concatenate units if they have the same unit", { x <- 1:4 * as_units("m") y <- 5:8 * as_units("m") z <- c(x, y) expect_equal(length(z), length(x) + length(y)) expect_equal(x, z[1:4]) expect_equal(y, z[1:4 + 4]) }) test_that("We can't concatenate units if they have different units", { x <- 1:4 * as_units("m") y <- 5:8 * as_units("s") expect_error(c(x, y)) }) test_that("We can concatenate units if their units can be converted", { x <- 1:4 * as_units("m") y <- 5:8 * as_units("km") z <- c(x, y) expect_equal(length(z), length(x) + length(y)) expect_equal(as.character(units(z)), "m") expect_equal(x, z[1:4]) expect_equal(set_units(y, units(as_units("m")), mode = "standard"), z[1:4 + 4]) }) test_that("We can use diff on a units object", { x = 1:10 * as_units("m") y = rep(1,9) * as_units("m") expect_equal(diff(x), y) }) test_that("type_sum is available for units objects", { skip_if_not_installed("pillar") expect_s3_class(pillar::type_sum(as_units("m")), "type_sum_units") }) test_that("parse_unit works", { kg = as_units("kg") m = as_units("m") s = as_units("s") u0 = kg/m/m/s u = as_units("kg m-2 s-1", implicit_exponents = TRUE) expect_equal(u, u0) J = as_units("J") u0 = with(ud_units, kg*kg*kg*m*m*J/s/s/s/s/s) u = as_units("kg3 m2 s-5 J", implicit_exponents = TRUE) expect_equal(u, u0) }) test_that("deparse_unit works", { str = "kg m-2 s-1" u = as_units(str, implicit_exponents = TRUE) str0 = deparse_unit(u) expect_equal(str, str0) }) test_that("we can provide a symbol to as_units and make it look in ud_units", { skip("skipping as_units() tests") five_ha <- as_units(5, ha) # ha pulled from ud_units expect_equal(as.numeric(five_ha), 5) expect_equal(units(five_ha), units(ud_units$ha)) ha <- as_units("m") # make sure that user-defined units overrule five_ha <- as_units(5, ha) # ha pulled from ud_units expect_equal(as.numeric(five_ha), 5) expect_equal(units(five_ha), units(ud_units$m)) }) test_that("set_units(x, u) is a short form for x * with(ud_units, u)", { skip("ud_units not necessary") expect_equal(set_units(1:10, m/s), 1:10 * with(ud_units, m/s)) # not identical - why? x = set_units(1:5, m/s) y = x units(y) = set_units(1, km/h) expect_identical(y, set_units(x, km/h)) }) test_that("rep.units works", { expect_equal(rep(set_units(1:2, m/s), 2), set_units(c(1,2,1,2), m/s)) }) test_that("set_units works with symbols in character data, and resolves names", { skip_on_cran() deg = paste0(enc2native(intToUtf8(176)), "C") expect_equal(set_units(1:2, deg, mode = "standard"), set_units(1:2, "degree_C", mode = "standard")) expect_equal(set_units(1:2, deg, mode = "standard"), set_units(1:2, "degree_Celsius", mode = "standard")) expect_equal(set_units(1:2, "degree_C", mode = "standard"), set_units(1:2, "degree_Celsius", mode = "standard")) expect_equal(set_units(1:2, degree_C), set_units(1:2, degree_Celsius)) expect_equal(set_units(1:2, deg, mode = "standard"), set_units(1:2, degree_Celsius)) x = set_units(1:3, km) y <- set_units(x, "meter", mode = "standard") expect_equal(y, set_units(c(1000,2000,3000), m)) }) test_that("all.equal works", { expect_true(all.equal(set_units(1, m/s), set_units(3.6, km/h))) expect_true(set_units(1, m/s) == set_units(3.6, km/h)) expect_true(all.equal(set_units(3.6, km/h), set_units(1, m/s))) expect_false(set_units(3.6, km/h) == set_units(1, m/s)) }) test_that("seq works", { seq(to = set_units(10, m), by = set_units(1, m), length.out = 5) seq(set_units(10, m), by = set_units(1, m), length.out = 5) seq(set_units(10, m), set_units(19, m)) seq(set_units(10, m), set_units(.02, km)) }) test_that("tibble printing works", { skip_if_not_installed("tibble") print(tibble::tibble(a = set_units(1/1:3, m/s))) }) test_that("str works", { str(set_units(1/1:3, m/s)) }) test_that("deprecations work", { expect_warning(parse_unit("m")) }) units/tests/testthat/test_conversion.R0000644000176200001440000001272313463271136020000 0ustar liggesuserscontext("Unit conversion") test_that("we can convert numbers to unit-less units", { x <- as_units(1:4) expect_equal(length(x), 4) expect_equal(class(x), "units") expect_equal(as.numeric(x), 1:4) y <- 1:4 units(y) <- unitless expect_equal(x, y) }) test_that("we can convert numbers to physical units", { m <- as_units("m") x <- 1:4 * m expect_equal(length(x), 4) expect_equal(class(x), "units") expect_equal(as.character(units(x)), "m") expect_equal(as.numeric(x), 1:4) y <- 1:4 units(y) <- m expect_equal(x, y) z <- 1:4 / m expect_equal(length(z), 4) expect_equal(class(z), "units") expect_equal(as.character(units(z)), "1/m") expect_equal(as.numeric(z), 1:4) }) test_that("we can convert NA values to physical units", { m <- as_units("m") x <- NA * m expect_equal(class(x), "units") expect_equal(as.character(units(x)), "m") expect_equal(as.numeric(x), as.numeric(NA)) x <- set_units(NA,m/s) expect_equal(as.character(units(x)), "m/s") expect_equal(x + set_units(5,m/s), set_units(NA,m/s)) expect_error(x + set_units(5,m)) x <- NA units(x) <- m expect_equal(as.character(units(x)), 'm') x <- rep(NA,5) s <- as_units("s") units(x) <- make_units(m/s) expect_equal(length(x),5) expect_equal(units(x),units(m/s)) expect_equal(x,5 * x) expect_error(x + 1) }) test_that("we can convert between two units that can be converted", { m <- as_units("m") km <- as_units("km") x <- y <- 1:4 * m units(x) <- km expect_equal(as.numeric(y), 1000 * as.numeric(x)) skip_if_not_installed("magrittr") library(magrittr) y %>% set_units(km) -> z expect_equal(x, z) }) test_that("we can't convert between two units that can't be converted", { m <- as_units("m") s <- as_units("s") expect_error(units(m) <- s) }) test_that("we can convert difftime objects to units", { s <- Sys.time() d <- s - (s + 1) x <- as_units(d) expect_equal(as.numeric(x), as.numeric(d)) week <- as.difftime(1, units = "weeks") units_week <- as_units(week) expect_equal(as.character(units(units_week)), "d") expect_equal(as.numeric(units_week), 7) }) test_that("we can convert units objects to difftime objects", { s <- Sys.time() d <- s - (s + 1) x <- as_units(d) y <- as_difftime(x) expect_equal(d, y) }) #test_that("we can convert units objects to and from hms objects", { # s <- Sys.time() # library(hms) # d <- as.hms(s - (s + 1)) # x <- as_units(d) # y <- as.hms(x) # # expect_equal(d, y) #}) test_that("we can subscript units", { x <- 1:4 y <- x * as_units("m") expect_equal(as.numeric(y[1]), x[1]) expect_equal(class(y[1]), class(y)) expect_equal(as.numeric(y[[1]]), x[[1]]) expect_equal(class(y[[1]]), class(y)) }) test_that("m + m*s is an error", { m <- as_units("m") s <- as_units("s") expect_error(m + m * s) }) test_that("we can convert between units that are not simply a scalar from each other", { m <- 0 * as_units("degC") units(m) <- as_units("degK") expect_equal(as.numeric(m), units:::ud_convert(0, "degC", "degK")) expect_equal(as.character(units(m)), "K") temp <- 75 * as_units('degF') units(temp) <- as_units('degK') result <- temp / as_units('degF') expect_equal(as.numeric(result), 75) expect_equal(units(result), unitless) }) test_that("dim propagates", { y = x = set_units(matrix(1:4,2), m) units(y) = make_unit("mm") expect_equal(dim(x), dim(y)) }) test_that("conversion of g/kg to dimensionless is not the default", { a_orig <- a <- 1:10 units(a) = as_units("mg/kg") expect_equal(as.numeric(a), a_orig) }) test_that("conversion to dimensionless with prefix works (g/kg) if simplify=TRUE", { a_orig <- a <- 1:10 units_options(simplify = TRUE) units(a) = as_units("mg/kg") expect_equal(as.numeric(a), a_orig/1e6) units(a) = as_units("kg/mg") expect_equal(a, a_orig) units(a) = as_units("g/g") expect_equal(a, a_orig) units(a) = as_units("kg/g") expect_equal(a, a_orig * 1000) units_options(simplify = NA) }) test_that("a NULL value returns NULL", { expect_null(as_units(NULL)) }) #test_that("as.data.frame.units works", { # expect_silent(as.data.frame(set_units(matrix(1:9,3), m))) #}) test_that("units.symbolic_units works", { m = set_units(1, m) expect_equal(units(m), units(units(m))) }) test_that("new base units work", { install_symbolic_unit("person", dimensionless = FALSE) expect_equal(set_units(1, person) + set_units(1, kperson), set_units(1001, person)) expect_error(set_units(1, person) + set_units(1, rad), "cannot convert") # restore remove_symbolic_unit("person") }) test_that("errors are correctly coerced to a data frame", { a <- 1:10 b <- a * as_units("m") expect_equal(as.data.frame(b)$b, b) x <- data.frame(a, b) expect_equal(x$a, a) expect_equal(x$b, b) x <- cbind(x, a, data.frame(b)) expect_equal(x[[3]], a) expect_equal(x[[4]], b) x <- rbind(x, a[1:4], x[1,]) expect_equal(x[[1]], c(a, 1, 1)) expect_equal(x[[2]], c(b, c(2, 1) * as_units("m"))) expect_equal(x[[3]], c(a, 3, 1)) expect_equal(x[[4]], c(b, c(4, 1) * as_units("m"))) }) test_that("units are correctly coerced to a list", { x <- 1:10 * as_units("m") y <- as.list(x) expect_is(y, "list") expect_true(all(sapply(seq_along(y), function(i) all.equal(y[[i]], x[i])))) }) test_that("NA as units generate warnings", { expect_error(set_units(NA_real_, NA_character_, mode="standard"), "a missing value for units is not allowed") expect_error(set_units(NA_real_, NA, mode="standard"), "a missing value for units is not allowed") }) units/tests/testthat/test_time.R0000644000176200001440000000211713230500577016541 0ustar liggesuserscontext("Date/time") test_that("we can convert from udunits time/date to R", { #skip("set_units doesn't accept strings") # rewrite this to expect_equal(as.Date("1999-10-31"), as.Date(as_units("days since 1999-10-30"))) expect_equal(as.POSIXct("1999-10-31 01:00:00", tz = "UTC"), as.POSIXct(set_units(25, as_units("hours since 1999-10-30"), mode = "standard"))) }) test_that("we can convert from R's time/date to udunits", { #skip("set_units doesn't accept strings") expect_equal( as_units(as.Date("1970-01-10")), set_units(9, as_units("days since 1970-01-01"), mode = "standard")) expect_equal( as_units(as.Date("1999-10-31"), "days since 1999-10-30"), set_units(1, as_units("days since 1999-10-30"), mode = "standard")) expect_equal( as_units(as.POSIXct("1970-01-01 01:00:00", tz = "UTC")), set_units(3600, as_units("seconds since 1970-01-01 00:00:00 +00:00"), mode = "standard")) expect_equal( as_units(as.POSIXct("1999-10-31 01:00:00", tz = "UTC"), "hours since 1999-10-30"), set_units(25, as_units("hours since 1999-10-30"), mode = "standard")) }) units/tests/testthat/test_unit_creation.R0000644000176200001440000001061413463271136020453 0ustar liggesuserscontext("unit(s) creation") test_that("parse_units() backticks strings correctly", { x <- matrix(ncol = 2, byrow = TRUE, c( "in", "`in`", "`in`", "`in`", "kelvin", "`kelvin`", "%", "`%`", "T", "`T`", "'/s", "`'`/`s`", "'", "`'`" , '"', '`"`' , '"/s' , '`"`/`s`', "s/'" , "`s`/`'`" , "C" , "`C`" , "F" , "`F`", "\u00B0C", "`\u00B0C`", "\u2103" , "`\u2103`", "\u00B0F", "`\u00B0F`", "\u2109", "`\u2109`", "log(ug)", "`log`(`ug`)", "log(ug/l)", "`log`(`ug`/`l`)", "kg*m/s^2", "`kg`*`m`/`s`^2" )) colnames(x) <- c("input", "expected_output") expect_identical(units:::backtick(x[,"input"]), x[,"expected_output"]) }) test_that("explicit exponents identified correctly", { expect_true( are_exponents_implicit("m s") ) expect_true( are_exponents_implicit("m2") ) expect_true( are_exponents_implicit("m-2") ) expect_true( are_exponents_implicit("2 m") ) expect_true( are_exponents_implicit("m s-2") ) expect_true( are_exponents_implicit("m s-2 kg") ) expect_true( are_exponents_implicit("2 m s") ) expect_false( are_exponents_implicit("m") ) expect_false( are_exponents_implicit("m/s") ) expect_false( are_exponents_implicit("m^2") ) expect_false( are_exponents_implicit("m*s") ) }) test_that("global options are respected", { # rt: round trip rt <- function(x) as.character(units(as_units(x))) expect_equal("g", rt("grams")) #op <- units_options(auto_convert_names_to_symbols = FALSE) units_options(auto_convert_names_to_symbols = FALSE) expect_equal("grams", rt("grams")) units_options(auto_convert_names_to_symbols = TRUE) expect_equal("g", rt("grams")) #units_options(op) expect_equal("g", rt("grams")) o = units_options("set_units_mode") g = set_units(1, g) units_options(set_units_mode = "standard") expect_equal(set_units(1, "g"), g) units_options(set_units_mode = o) }) test_that("various forms of unit creation and destruction work", { #ox <- x <- 1L:4L # why should ints be preserved? ox <- x <- as.numeric(1:4) units(x) <- "m/s" expect_s3_class(x,"units") units(x) <- NULL expect_identical(x, ox) ox <- x <- matrix(ox, ncol = 2) units(x) <- "m/s" expect_s3_class(x,"units") units(x) <- NULL expect_identical(x, ox) ox <- y <- x <- as.numeric(1:4) units(x) <- "m/s" expect_identical(x, set_units(y, m/s)) expect_identical(x, set_units(y, "m/s", mode = "standard")) expect_identical(ox, set_units(x, NULL)) expect_identical(ox, set_units(x, NULL, mode = "standard")) ox <- x <- as.numeric(1:4) units(x) <- "m/s" expect_s3_class(x, "units") x <- drop_units(x) expect_identical(x, ox) expect_error(drop_units(x)) ox <- x <- data.frame(x=1:4, y=1:4) units(x[[1]]) <- "m/s" expect_s3_class(x[[1]], "units") x <- drop_units(x) expect_identical(x, ox) meter <- units:::symbolic_unit("m") expect_identical(meter, make_units(m)) expect_identical(meter, as_units("m")) expect_identical(meter, as_units(quote(m))) expect_identical(meter, as_units(expression(m))) meter_per_sec <- meter/units:::symbolic_unit("s") expect_identical(meter_per_sec, make_units(m/s)) expect_identical(meter_per_sec, as_units("m/s")) expect_identical(meter_per_sec, as_units(" m / s ")) expect_identical(meter_per_sec, as_units(quote(m/s))) expect_identical(meter_per_sec, as_units(expression(m/s))) expect_identical(meter_per_sec, as_units("m s-1")) }) test_that("unitless objects can be created", { unit <- 1.0 units(unit) <- units:::unitless xul <- x <- as.numeric(2:5) units(xul) <- units:::unitless expect_identical(unit, make_units()) expect_identical(unit, make_units(1)) expect_identical(unit, as_units(1)) expect_identical(unit, as_units("1")) expect_identical(xul, set_units(x, 1)) expect_identical(xul, set_units(x)) expect_identical(xul, set_units(x, "1")) expect_identical(xul, set_units(x, "1", mode = "standard")) expect_identical(xul, set_units(x, mode = "standard")) }) test_that("set_units default enforces NSE", { expect_error(set_units(1:3, as_units("m"))) expect_error(set_units(1:3, as_units("m/s"))) expect_error(set_units(1:3, make_units(m))) expect_error(set_units(1:3, make_units(m/s))) # is it bad if this works? # expect_error(set_units(1:3, "m/s")) }) units/tests/plot.R0000644000176200001440000000204413463271136013665 0ustar liggesuserslibrary(units) oldpar = par(mar = par("mar") + c(0, .3, 0, 0)) displacement = mtcars$disp * ud_units[["in"]]^3 units(displacement) = with(ud_units, cm^3) weight = mtcars$wt * 1000 * with(ud_units, lb) units(weight) = with(ud_units, kg) plot(weight, displacement) units_options(group = c("(", ")") ) # parenthesis instead of square brackets plot(weight, displacement) units_options(sep = c("~~~", "~"), group = c("", "")) # no brackets; extra space plot(weight, displacement) units_options(sep = c("~", "~~"), group = c("[", "]")) gallon = as_units("gallon") consumption = mtcars$mpg * with(ud_units, mi/gallon) units(consumption) = with(ud_units, km/l) plot(displacement, consumption) # division in consumption units_options(negative_power = TRUE) # division becomes ^-1 plot(displacement, consumption) plot(1/displacement, 1/consumption) par(oldpar) units_options(parse = FALSE) n = 100 u = rnorm(1:n) * as_units("degree_C") v = rnorm(1:n) * as_units("s") plot(u, v) plot(u, type = 'l') hist(u) boxplot(u) do.call(units_options, units:::.default_options) units/tests/testthat.R0000644000176200001440000000014713463271136014551 0ustar liggesuserslibrary(testthat) library(units) test_check("units") do.call(units_options, units:::.default_options) units/configure.ac0000644000176200001440000000527513463271135013720 0ustar liggesusersdefine([pkgversion], esyscmd([sh -c "grep Version: DESCRIPTION | cut -d' ' -f2 | tr -d '\n'"])) AC_INIT(units, [pkgversion], edzer.pebesma@uni-muenster.de) AC_MSG_NOTICE([${PACKAGE_NAME}: ${PACKAGE_VERSION}]) : ${R_HOME=`R RHOME`} if test -z "${R_HOME}"; then echo "could not determine R_HOME" exit 1 fi CC=`"${R_HOME}/bin/R" CMD config CC` CFLAGS=`"${R_HOME}/bin/R" CMD config CFLAGS` CPPFLAGS=`"${R_HOME}/bin/R" CMD config CPPFLAGS` LDFLAGS=`"${R_HOME}/bin/R" CMD config LDFLAGS` CXX=`"${R_HOME}/bin/R" CMD config CXX` CXXFLAGS=`"${R_HOME}/bin/R" CMD config CXXFLAGS` AC_LANG(C++) AC_CHECK_HEADER_STDBOOL AC_FUNC_ERROR_AT_LINE AC_PREREQ AC_PROG_CC AC_ARG_WITH([udunits2-include], AS_HELP_STRING([--with-udunits2-include=DIR], [location of the udunits2 header files]), [udunits2_include_path=$withval]) if test [ -n "$udunits2_include_path" ] ; then UD_CPPFLAGS="-I${udunits2_include_path}" else if test [ -n "${UDUNITS2_INCLUDE}" ] ; then UD_CPPFLAGS="-I${UDUNITS2_INCLUDE}" fi fi AC_ARG_WITH([udunits2-lib], AS_HELP_STRING([--with-udunits2-lib=DIR], [location of the udunits2 libraries]), [udunits2_lib_path=$withval]) if test [ -n "$udunits2_lib_path" ] ; then LIBS="-L${udunits2_lib_path} ${LIBS}" else if test [ -n "${UDUNITS2_LIBS}" ] ; then LIBS="-L${UDUNITS2_LIBS} ${LIBS}" fi fi AC_CHECK_LIB(expat, XML_ParserCreate, [],[], ${LIBS}) if test "${ac_cv_lib_expat_XML_ParserCreate}" == yes; then LIBS="${LIBS} -lexpat" fi CPPFLAGS="${UD_CPPFLAGS} ${CPPFLAGS}" AC_CHECK_HEADER(udunits2.h, UDUNITS2_DIR=0, [ AC_CHECK_HEADER(udunits2/udunits2.h, UDUNITS2_DIR=1, UD_ERROR="udunits2.h was not found") ]) AC_CHECK_LIB(udunits2, ut_read_xml, LIBS="${LIBS} -ludunits2", UD_ERROR="libudunits2.so was not found") if test "${UD_ERROR}" != "" ; then AC_MSG_FAILURE([ -------------------------------------------------------------------------------- Configuration failed because ${UD_ERROR}. Try installing: * deb: libudunits2-dev (Debian, Ubuntu, ...) * rpm: udunits2-devel (Fedora, EPEL, ...) * brew: udunits (OSX) If udunits2 is already installed in a non-standard location, use: --configure-args='--with-udunits2-lib=/usr/local/lib' if the library was not found, and/or: --configure-args='--with-udunits2-include=/usr/include/udunits2' if the header was not found, replacing paths with appropriate values. You can alternatively set UDUNITS2_INCLUDE and UDUNITS2_LIBS manually. -------------------------------------------------------------------------------- ]) fi UD_CPPFLAGS="${UD_CPPFLAGS} ${CPPFLAGS}" AC_SUBST([LIBS]) AC_SUBST([UD_CPPFLAGS]) AC_SUBST([UDUNITS2_DIR]) AC_CONFIG_FILES([src/Makevars]) AC_OUTPUT units/src/0000755000176200001440000000000013547030302012200 5ustar liggesusersunits/src/udunits.cpp0000644000176200001440000001660613463271136014421 0ustar liggesusers/* part of this was modified from: https://github.com/pacificclimate/Rudunits2 (c) James Hiebert Pacific Climate Impacts Consortium August, 16, 2010 Functions to support the R interface to the udunits (API version 2) library */ #include #if UDUNITS2_DIR != 0 # include #else # include #endif extern "C" { #include "io.h" } using namespace Rcpp; typedef XPtr XPtrUT; static ut_system *sys = NULL; static ut_encoding enc = UT_UTF8; // [[Rcpp::export]] void udunits_init(CharacterVector path) { ut_set_error_message_handler(ut_ignore); ut_free_system(sys); for (int i = 0; i < path.size(); i++) { if ((sys = ut_read_xml(path[i])) != NULL) break; } if (sys == NULL) sys = ut_read_xml(NULL); // #nocov ut_set_error_message_handler((ut_error_message_handler) r_error_fn); if (sys == NULL) handle_error("udunits_init"); // #nocov } // [[Rcpp::export]] void udunits_exit() { // #nocov start ut_free_system(sys); sys = NULL; } // #nocov end // wrap a ut_unit pointer in an XPtr SEXP ut_wrap(ut_unit *u) { XPtrUT p(u); return p; } // fetch the ut_unit pointer from an XPtr wrapper ut_unit *ut_unwrap(SEXP u) { XPtrUT ptr(u); return ((ut_unit *) ptr); } // [[Rcpp::export]] SEXP R_ut_parse(CharacterVector name) { ut_unit *u = ut_parse(sys, ut_trim(name[0], enc), enc); if (u == NULL) { switch (ut_get_status()) { case UT_BAD_ARG: case UT_SYNTAX: case UT_UNKNOWN: case UT_OS: default: handle_error("R_ut_parse"); } } // error checking ... return ut_wrap(u); } // [[Rcpp::export]] SEXP R_ut_get_dimensionless_unit_one(CharacterVector name) { return ut_wrap(ut_get_dimensionless_unit_one(sys)); } // [[Rcpp::export]] LogicalVector R_ut_are_convertible(SEXP a, SEXP b) { ut_unit *u1 = ut_unwrap(a); ut_unit *u2 = ut_unwrap(b); if (u1 == NULL || u2 == NULL) return false; // #nocov return ut_are_convertible(u1, u2) != 0; } // [[Rcpp::export]] NumericVector R_convert_doubles(SEXP from, SEXP to, NumericVector val) { if (! ut_are_convertible(ut_unwrap(from), ut_unwrap(to))) stop("units are not convertible"); cv_converter *cv = ut_get_converter(ut_unwrap(from), ut_unwrap(to)); NumericVector out(val.size()); cv_convert_doubles(cv, &(val[0]), val.size(), &(out[0])); cv_free(cv); return out; } // [[Rcpp::export]] void R_ut_new_dimensionless_unit(CharacterVector name) { ut_unit *u = ut_new_dimensionless_unit(sys); if (ut_map_name_to_unit(name[0], enc, u) != UT_SUCCESS) handle_error("R_ut_new_dimensionless_unit"); // #nocov ut_free(u); } // [[Rcpp::export]] void R_ut_new_base_unit(CharacterVector name) { ut_unit *u = ut_new_base_unit(sys); if (ut_map_name_to_unit(name[0], enc, u) != UT_SUCCESS) handle_error("R_ut_new_base_unit"); // #nocov ut_free(u); } // [[Rcpp::export]] void R_ut_remove_unit(CharacterVector name) { ut_unit *u = NULL; if ((u = ut_get_unit_by_name(sys, name[0])) != NULL) { ut_free(u); if (ut_unmap_name_to_unit(sys, name[0], enc) != UT_SUCCESS) handle_error("R_ut_remove_unit"); // #nocov } else if ((u = ut_get_unit_by_symbol(sys, name[0])) != NULL) { ut_free(u); if (ut_unmap_symbol_to_unit(sys, name[0], enc) != UT_SUCCESS) handle_error("R_ut_remove_unit"); // #nocov } else stop("unknown unit name or symbol"); return ; } // [[Rcpp::export]] void R_ut_scale(CharacterVector nw, CharacterVector old, NumericVector d) { if (d.size() != 1) stop("d should have size 1"); // #nocov ut_unit *u_old = ut_parse(sys, ut_trim(old[0], enc), enc); ut_unit *u_new = ut_scale(d[0], u_old); if (ut_map_name_to_unit(nw[0], enc, u_new) != UT_SUCCESS) handle_error("R_ut_scale"); // #nocov ut_free(u_new); ut_free(u_old); } // [[Rcpp::export]] void R_ut_offset(CharacterVector nw, CharacterVector old, NumericVector d) { if (d.size() != 1) stop("d should have size 1"); // #nocov ut_unit *u_old = ut_parse(sys, ut_trim(old[0], enc), enc); ut_unit *u_new = ut_offset(u_old, d[0]); if (ut_map_name_to_unit(nw[0], enc, u_new) != UT_SUCCESS) handle_error("R_ut_offset"); // #nocov ut_free(u_new); ut_free(u_old); } // [[Rcpp::export]] SEXP R_ut_divide(SEXP numer, SEXP denom) { return ut_wrap(ut_divide(ut_unwrap(numer), ut_unwrap(denom))); } // [[Rcpp::export]] SEXP R_ut_multiply(SEXP a, SEXP b) { return ut_wrap(ut_multiply(ut_unwrap(a), ut_unwrap(b))); } // [[Rcpp::export]] SEXP R_ut_invert(SEXP a) { return ut_wrap(ut_invert(ut_unwrap(a))); } // [[Rcpp::export]] SEXP R_ut_raise(SEXP a, IntegerVector i) { if (i.length() != 1) stop("i should have length 1"); return ut_wrap(ut_raise(ut_unwrap(a), i[0])); } // [[Rcpp::export]] SEXP R_ut_root(SEXP a, IntegerVector i) { if (i.length() != 1) stop("i should have length 1"); return ut_wrap(ut_root(ut_unwrap(a), i[0])); } // [[Rcpp::export]] SEXP R_ut_log(SEXP a, NumericVector base) { if (base.length() != 1) stop("base should have length 1"); if (base[0] <= 0) stop("base should be positive"); return ut_wrap(ut_log(base[0], ut_unwrap(a))); } // [[Rcpp::export]] CharacterVector R_ut_format(SEXP p, bool names = false, bool definition = false, bool ascii = false) { int opt; if (! ascii) opt = enc; else opt = UT_ASCII; if (names) opt = opt | UT_NAMES; if (definition) opt = opt | UT_DEFINITION; char buf[256]; ut_set_error_message_handler(ut_ignore); int len = ut_format(ut_unwrap(p), buf, 256, opt); ut_set_error_message_handler((ut_error_message_handler) r_error_fn); if (len == -1) { // #nocov start switch (ut_get_status()) { case UT_BAD_ARG: case UT_CANT_FORMAT: handle_error("R_ut_format"); break; default:; } buf[0] = '\0'; // "": dont' return rubbish } else if (len == 256) handle_error("buffer of 256 bytes too small!"); // #nocov end return CharacterVector::create(buf); } // [[Rcpp::export]] void R_ut_set_encoding(std::string enc_str) { if (enc_str.compare("utf8") == 0) enc = UT_UTF8; else if (enc_str.compare("ascii") == 0) enc = UT_ASCII; else if (enc_str.compare("iso-8859-1") == 0 || enc_str.compare("latin1") == 0) enc = UT_LATIN1; else stop("Valid encoding string parameters are ('utf8'|'ascii'|'iso-8859-1','latin1')"); } // [[Rcpp::export]] CharacterVector R_ut_get_symbol(CharacterVector ustr) { ut_unit *u = ut_parse(sys, ut_trim(ustr[0], enc), enc); if (u == NULL) handle_error("R_ut_get_symbol"); // #nocov -- never reached const char *s = ut_get_symbol(u, enc); ut_free(u); if (s == NULL) return CharacterVector::create(""); else return CharacterVector::create(s); } // [[Rcpp::export]] CharacterVector R_ut_get_name(CharacterVector ustr) { ut_unit *u = ut_parse(sys, ut_trim(ustr[0], enc), enc); if (u == NULL) handle_error("R_ut_get_name"); // #nocov -- never reached const char *s = ut_get_name(u, enc); ut_free(u); if (s == NULL) return CharacterVector::create(""); else return CharacterVector::create(s); // #nocov } // https://github.com/r-quantities/units/issues/89#issuecomment-359251623 // [[Rcpp::export]] SEXP R_ut_map_name_to_unit( CharacterVector name, SEXP inunit) { // #nocov start ut_unit *unit = ut_unwrap(inunit); if (ut_map_name_to_unit(name[0], enc, unit) != UT_SUCCESS) handle_error("R_ut_map_name_to_unit"); return ut_wrap(unit); } // #nocov end units/src/io.c0000644000176200001440000000230213463271136012761 0ustar liggesusers#include #if UDUNITS2_DIR != 0 # include #else # include #endif #include "io.h" /* From the enum comments in udunits2.h */ const char * ut_status_strings[] = { "Success", "An argument violates the function's contract", "Unit, prefix, or identifier already exists", "No such unit exists", "Operating-system error. See \"errno\".", "The units belong to different unit-systems", "The operation on the unit(s) is meaningless", "The unit-system doesn't have a unit named \"second\"", "An error occurred while visiting a unit", "A unit can't be formatted in the desired manner", "string unit representation contains syntax error", "string unit representation contains unknown word", "Can't open argument-specified unit database", "Can't open environment-specified unit database", "Can't open installed, default, unit database", "Error parsing unit specification" }; void handle_error(const char *calling_function) { ut_status stat; stat = ut_get_status(); error("Error in function %s: %s", calling_function, ut_status_strings[stat]); } void r_error_fn(const char* fmt, va_list args) { // #nocov start Rvprintf(fmt, args); } // #nocov end units/src/Makevars.win0000644000176200001440000000060213463271136014477 0ustar liggesusersPKG_CPPFLAGS = -DUDUNITS2_DIR=0 -I../windows/udunits-2.2.20/include PKG_LIBS = -L../windows/udunits-2.2.20/lib${R_ARCH} \ -ludunits2 -lexpat all: clean winlibs winlibs: "${R_HOME}/bin${R_ARCH_BIN}/Rscript.exe" "../tools/winlibs.R" mkdir -p ../inst rm -Rf ../inst/share cp -r ../windows/udunits-2.2.20/share ../inst/ clean: rm -Rf $(SHLIB) $(OBJECTS) .PHONY: all winlibs clean units/src/Makevars.in0000644000176200001440000000011513463271136014307 0ustar liggesusersPKG_CPPFLAGS = -DUDUNITS2_DIR=@UDUNITS2_DIR@ @UD_CPPFLAGS@ PKG_LIBS = @LIBS@ units/src/io.h0000644000176200001440000000014113306477535012774 0ustar liggesusersvoid r_error_fn(const char* fmt, va_list args); void handle_error(const char *calling_function); units/src/RcppExports.cpp0000644000176200001440000002507113463271136015213 0ustar liggesusers// Generated by using Rcpp::compileAttributes() -> do not edit by hand // Generator token: 10BE3573-1514-4C36-9D1C-5A225CD40393 #include using namespace Rcpp; // udunits_init void udunits_init(CharacterVector path); RcppExport SEXP _units_udunits_init(SEXP pathSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type path(pathSEXP); udunits_init(path); return R_NilValue; END_RCPP } // udunits_exit void udunits_exit(); RcppExport SEXP _units_udunits_exit() { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; udunits_exit(); return R_NilValue; END_RCPP } // R_ut_parse SEXP R_ut_parse(CharacterVector name); RcppExport SEXP _units_R_ut_parse(SEXP nameSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type name(nameSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_parse(name)); return rcpp_result_gen; END_RCPP } // R_ut_get_dimensionless_unit_one SEXP R_ut_get_dimensionless_unit_one(CharacterVector name); RcppExport SEXP _units_R_ut_get_dimensionless_unit_one(SEXP nameSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type name(nameSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_get_dimensionless_unit_one(name)); return rcpp_result_gen; END_RCPP } // R_ut_are_convertible LogicalVector R_ut_are_convertible(SEXP a, SEXP b); RcppExport SEXP _units_R_ut_are_convertible(SEXP aSEXP, SEXP bSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type a(aSEXP); Rcpp::traits::input_parameter< SEXP >::type b(bSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_are_convertible(a, b)); return rcpp_result_gen; END_RCPP } // R_convert_doubles NumericVector R_convert_doubles(SEXP from, SEXP to, NumericVector val); RcppExport SEXP _units_R_convert_doubles(SEXP fromSEXP, SEXP toSEXP, SEXP valSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type from(fromSEXP); Rcpp::traits::input_parameter< SEXP >::type to(toSEXP); Rcpp::traits::input_parameter< NumericVector >::type val(valSEXP); rcpp_result_gen = Rcpp::wrap(R_convert_doubles(from, to, val)); return rcpp_result_gen; END_RCPP } // R_ut_new_dimensionless_unit void R_ut_new_dimensionless_unit(CharacterVector name); RcppExport SEXP _units_R_ut_new_dimensionless_unit(SEXP nameSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type name(nameSEXP); R_ut_new_dimensionless_unit(name); return R_NilValue; END_RCPP } // R_ut_new_base_unit void R_ut_new_base_unit(CharacterVector name); RcppExport SEXP _units_R_ut_new_base_unit(SEXP nameSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type name(nameSEXP); R_ut_new_base_unit(name); return R_NilValue; END_RCPP } // R_ut_remove_unit void R_ut_remove_unit(CharacterVector name); RcppExport SEXP _units_R_ut_remove_unit(SEXP nameSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type name(nameSEXP); R_ut_remove_unit(name); return R_NilValue; END_RCPP } // R_ut_scale void R_ut_scale(CharacterVector nw, CharacterVector old, NumericVector d); RcppExport SEXP _units_R_ut_scale(SEXP nwSEXP, SEXP oldSEXP, SEXP dSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type nw(nwSEXP); Rcpp::traits::input_parameter< CharacterVector >::type old(oldSEXP); Rcpp::traits::input_parameter< NumericVector >::type d(dSEXP); R_ut_scale(nw, old, d); return R_NilValue; END_RCPP } // R_ut_offset void R_ut_offset(CharacterVector nw, CharacterVector old, NumericVector d); RcppExport SEXP _units_R_ut_offset(SEXP nwSEXP, SEXP oldSEXP, SEXP dSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type nw(nwSEXP); Rcpp::traits::input_parameter< CharacterVector >::type old(oldSEXP); Rcpp::traits::input_parameter< NumericVector >::type d(dSEXP); R_ut_offset(nw, old, d); return R_NilValue; END_RCPP } // R_ut_divide SEXP R_ut_divide(SEXP numer, SEXP denom); RcppExport SEXP _units_R_ut_divide(SEXP numerSEXP, SEXP denomSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type numer(numerSEXP); Rcpp::traits::input_parameter< SEXP >::type denom(denomSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_divide(numer, denom)); return rcpp_result_gen; END_RCPP } // R_ut_multiply SEXP R_ut_multiply(SEXP a, SEXP b); RcppExport SEXP _units_R_ut_multiply(SEXP aSEXP, SEXP bSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type a(aSEXP); Rcpp::traits::input_parameter< SEXP >::type b(bSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_multiply(a, b)); return rcpp_result_gen; END_RCPP } // R_ut_invert SEXP R_ut_invert(SEXP a); RcppExport SEXP _units_R_ut_invert(SEXP aSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type a(aSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_invert(a)); return rcpp_result_gen; END_RCPP } // R_ut_raise SEXP R_ut_raise(SEXP a, IntegerVector i); RcppExport SEXP _units_R_ut_raise(SEXP aSEXP, SEXP iSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type a(aSEXP); Rcpp::traits::input_parameter< IntegerVector >::type i(iSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_raise(a, i)); return rcpp_result_gen; END_RCPP } // R_ut_root SEXP R_ut_root(SEXP a, IntegerVector i); RcppExport SEXP _units_R_ut_root(SEXP aSEXP, SEXP iSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type a(aSEXP); Rcpp::traits::input_parameter< IntegerVector >::type i(iSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_root(a, i)); return rcpp_result_gen; END_RCPP } // R_ut_log SEXP R_ut_log(SEXP a, NumericVector base); RcppExport SEXP _units_R_ut_log(SEXP aSEXP, SEXP baseSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type a(aSEXP); Rcpp::traits::input_parameter< NumericVector >::type base(baseSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_log(a, base)); return rcpp_result_gen; END_RCPP } // R_ut_format CharacterVector R_ut_format(SEXP p, bool names, bool definition, bool ascii); RcppExport SEXP _units_R_ut_format(SEXP pSEXP, SEXP namesSEXP, SEXP definitionSEXP, SEXP asciiSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< SEXP >::type p(pSEXP); Rcpp::traits::input_parameter< bool >::type names(namesSEXP); Rcpp::traits::input_parameter< bool >::type definition(definitionSEXP); Rcpp::traits::input_parameter< bool >::type ascii(asciiSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_format(p, names, definition, ascii)); return rcpp_result_gen; END_RCPP } // R_ut_set_encoding void R_ut_set_encoding(std::string enc_str); RcppExport SEXP _units_R_ut_set_encoding(SEXP enc_strSEXP) { BEGIN_RCPP Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< std::string >::type enc_str(enc_strSEXP); R_ut_set_encoding(enc_str); return R_NilValue; END_RCPP } // R_ut_get_symbol CharacterVector R_ut_get_symbol(CharacterVector ustr); RcppExport SEXP _units_R_ut_get_symbol(SEXP ustrSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type ustr(ustrSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_get_symbol(ustr)); return rcpp_result_gen; END_RCPP } // R_ut_get_name CharacterVector R_ut_get_name(CharacterVector ustr); RcppExport SEXP _units_R_ut_get_name(SEXP ustrSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type ustr(ustrSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_get_name(ustr)); return rcpp_result_gen; END_RCPP } // R_ut_map_name_to_unit SEXP R_ut_map_name_to_unit(CharacterVector name, SEXP inunit); RcppExport SEXP _units_R_ut_map_name_to_unit(SEXP nameSEXP, SEXP inunitSEXP) { BEGIN_RCPP Rcpp::RObject rcpp_result_gen; Rcpp::RNGScope rcpp_rngScope_gen; Rcpp::traits::input_parameter< CharacterVector >::type name(nameSEXP); Rcpp::traits::input_parameter< SEXP >::type inunit(inunitSEXP); rcpp_result_gen = Rcpp::wrap(R_ut_map_name_to_unit(name, inunit)); return rcpp_result_gen; END_RCPP } static const R_CallMethodDef CallEntries[] = { {"_units_udunits_init", (DL_FUNC) &_units_udunits_init, 1}, {"_units_udunits_exit", (DL_FUNC) &_units_udunits_exit, 0}, {"_units_R_ut_parse", (DL_FUNC) &_units_R_ut_parse, 1}, {"_units_R_ut_get_dimensionless_unit_one", (DL_FUNC) &_units_R_ut_get_dimensionless_unit_one, 1}, {"_units_R_ut_are_convertible", (DL_FUNC) &_units_R_ut_are_convertible, 2}, {"_units_R_convert_doubles", (DL_FUNC) &_units_R_convert_doubles, 3}, {"_units_R_ut_new_dimensionless_unit", (DL_FUNC) &_units_R_ut_new_dimensionless_unit, 1}, {"_units_R_ut_new_base_unit", (DL_FUNC) &_units_R_ut_new_base_unit, 1}, {"_units_R_ut_remove_unit", (DL_FUNC) &_units_R_ut_remove_unit, 1}, {"_units_R_ut_scale", (DL_FUNC) &_units_R_ut_scale, 3}, {"_units_R_ut_offset", (DL_FUNC) &_units_R_ut_offset, 3}, {"_units_R_ut_divide", (DL_FUNC) &_units_R_ut_divide, 2}, {"_units_R_ut_multiply", (DL_FUNC) &_units_R_ut_multiply, 2}, {"_units_R_ut_invert", (DL_FUNC) &_units_R_ut_invert, 1}, {"_units_R_ut_raise", (DL_FUNC) &_units_R_ut_raise, 2}, {"_units_R_ut_root", (DL_FUNC) &_units_R_ut_root, 2}, {"_units_R_ut_log", (DL_FUNC) &_units_R_ut_log, 2}, {"_units_R_ut_format", (DL_FUNC) &_units_R_ut_format, 4}, {"_units_R_ut_set_encoding", (DL_FUNC) &_units_R_ut_set_encoding, 1}, {"_units_R_ut_get_symbol", (DL_FUNC) &_units_R_ut_get_symbol, 1}, {"_units_R_ut_get_name", (DL_FUNC) &_units_R_ut_get_name, 1}, {"_units_R_ut_map_name_to_unit", (DL_FUNC) &_units_R_ut_map_name_to_unit, 2}, {NULL, NULL, 0} }; RcppExport void R_init_units(DllInfo *dll) { R_registerRoutines(dll, NULL, CallEntries, NULL, NULL); R_useDynamicSymbols(dll, FALSE); } units/vignettes/0000755000176200001440000000000013547030302013421 5ustar liggesusersunits/vignettes/measurement_units_in_R.bib0000644000176200001440000001567713463271136020646 0ustar liggesusers@Manual{R, title = {R: A Language and Environment for Statistical Computing}, author = {{R Core Team}}, organization = {R Foundation for Statistical Computing}, address = {Vienna, Austria}, year = {2012}, note = {{ISBN} 3-900051-07-0}, url = {http://www.R-project.org/}, } @article{ihaka:1996, Author = {Ihaka, Ross and Gentleman, Robert}, Journal = {Journal of Computational and Graphical Statistics}, Number = 3, Pages = {299--314}, Title = {R: A Language for Data Analysis and Graphics}, Volume = 5, Year = {1996} } @article{cobb, author = { Cobb, George W. and Moore, David S. }, title = { Mathematics, statistics, and teaching }, journal = { American Mathematical Monthly }, year = {1997}, pages = { 801--823} } @article{scheider, author = {Simon Scheider and Benedikt Gräler and Edzer Pebesma and Christoph Stasch}, title = {Modeling spatiotemporal information generation}, journal = {International Journal of Geographical Information Science}, volume = {30}, number = {10}, pages = {1980-2008}, year = {2016}, URL = { http://dx.doi.org/10.1080/13658816.2016.1151520 }, } @book{iliffe, pages = { 208 }, title = { Datums and Map Projections: For Remote Sensing, GIS and Surveying }, year = { 2008 }, author = { Jonathan Iliffe and Roger Lott }, publisher = {CRC Inc} } @article{sp, author = {Pebesma, Edzer and Bivand, Roger}, year = 2005, title = { Classes and methods for spatial data in {R}}, url = { https://cran.r-project.org/doc/Rnews/}, journal = {R News}, volume = 5, issue = 2, pages = {9--13} } @article{si, title={The international system of units ({SI})}, author={{International Bureau of Weights and Measures} and Taylor, Barry N and Thompson, Ambler}, year={2001}, publisher={US Department of Commerce, Technology Administration, National Institute of Standards and Technology} } @Manual{birkdeprecated, title = {birk: {MA} {Birk}'s Functions}, author = {Matthew A. Birk}, year = {2016}, note = {R package version 2.1.0}, url = {https://CRAN.R-project.org/package=birk} } @Manual{birk, title = {measurements: Tools for Units of Measurement}, author = {Matthew A. Birk}, year = {2016}, note = {R package version 1.0.0}, url = {https://CRAN.R-project.org/package=measurements} } @Manual{NISTunits, title = {NISTunits: Fundamental Physical Constants and Unit Conversions from NIST}, author = {Jose Gama}, year = {2014}, note = {R package version 1.0.0}, url = {https://CRAN.R-project.org/package=NISTunits} } @Manual{udunits2, title = {udunits2: Udunits-2 Bindings for R}, author = {James Hiebert}, year = {2015}, note = {R package version 0.9} } @article{lubridate, author = {Garrett Grolemund and Hadley Wickham}, title = {Dates and Times Made Easy with lubridate}, journal = {Journal of Statistical Software}, volume = {40}, number = {1}, year = {2011}, issn = {1548-7660}, pages = {1--25}, doi = {10.18637/jss.v040.i03}, url = {https://www.jstatsoft.org/index.php/jss/article/view/v040i03} } @Article{zoo, title = {zoo: S3 Infrastructure for Regular and Irregular Time Series}, author = {Achim Zeileis and Gabor Grothendieck}, journal = {Journal of Statistical Software}, year = {2005}, volume = {14}, number = {6}, pages = {1--27}, doi = {10.18637/jss.v014.i06}, } @Manual{xts, title = {xts: eXtensible Time Series}, author = {Jeffrey A. Ryan and Joshua M. Ulrich}, year = {2014}, note = {R package version 0.9-7}, url = {https://CRAN.R-project.org/package=xts} } @article{spacetime, author = {Edzer Pebesma}, title = {spacetime: Spatio-Temporal Data in {R}}, journal = {Journal of Statistical Software}, volume = {51}, number = {1}, year = {2012}, issn = {1548-7660}, pages = {1--30}, doi = {10.18637/jss.v051.i07}, url = {https://www.jstatsoft.org/index.php/jss/article/view/v051i07} } @article{ucum, title={The Unified Code for Units of Measure}, author={Schadow, Gunther and McDonald, Clement J}, journal={Regenstrief Institute and UCUM Organization: Indianapolis, IN, USA}, year={2009} } @Manual{h5, title = {h5: Interface to the 'HDF5' Library}, author = {Mario Annau}, year = {2016}, note = {R package version 0.9.7}, url = {https://CRAN.R-project.org/package=h5} } @Manual{RNetCDF, title = {RNetCDF: Interface to NetCDF Datasets}, author = {Pavel Michna and Milton Woods}, year = {2016}, note = {R package version 1.8-2}, url = {https://CRAN.R-project.org/package=RNetCDF} } @inproceedings{sos4R, author = { Nüst, D. and Stasch, C. and Pebesma, E. J. }, title = { Connecting {R} to the Sensor Web }, editor = {Geertman, S. and Reinhardt, W. and Toppen, F.}, title = { Advancing Geoinformation Science for a Changing World }, series = { Lecture Notes in Geoinformation and Cartography}, publisher = { Springer }, year = {2011}, pages = {227--246} } @Manual{tibble, title = {tibble: Simple Data Frames}, author = {Hadley Wickham and Romain Francois and Kirill Müller}, year = {2016}, note = {R package version 1.2}, url = {https://CRAN.R-project.org/package=tibble} } @Manual{hms, title = {hms: Pretty Time of Day}, author = {Kirill Müller}, year = {2016}, note = {R package version 0.2}, url = {https://CRAN.R-project.org/package=hms} } @article{netcdf, title={NetCDF: an interface for scientific data access}, author={Rew, Russ and Davis, Glenn}, journal={IEEE computer graphics and applications}, volume={10}, number={4}, pages={76--82}, year={1990}, publisher={IEEE} } @Manual{measurements, title = {measurements: Tools for Units of Measurement}, author = {Matthew A. Birk}, year = {2016}, note = {R package version 1.0.0}, url = {https://CRAN.R-project.org/package=measurements} } @Book{lattice, title = {Lattice: Multivariate Data Visualization with R}, author = {Deepayan Sarkar}, publisher = {Springer}, address = {New York}, year = {2008}, note = {ISBN 978-0-387-75968-5}, url = {http://lmdvr.r-forge.r-project.org} } @Book{ggplot2, author = {Hadley Wickham}, title = {ggplot2: Elegant Graphics for Data Analysis}, publisher = {Springer-Verlag New York}, year = {2009}, isbn = {978-0-387-98140-6} } @Manual{ggforce, title = {ggforce: Accelerating 'ggplot2'}, author = {Thomas Lin Pedersen}, year = {2016}, note = {R package version 0.1.0}, url = {https://CRAN.R-project.org/package=ggforce} } @book{lang, author = {Lang, K.R}, title = { Astrophysical Formulae Volume II: Space, Time, Matter and Cosmology, 3rd Edition 1999. 2nd printing }, publisher = { Springer }, year = 2006 } @article{rj, author = {Edzer Pebesma and Thomas Mailund and James Hiebert}, title = {{Measurement Units in R}}, journal = {{The R Journal}}, year = 2016, volume = 8, number = 2, pages = {486--494}, doi = {10.32614/RJ-2016-061} } units/vignettes/measurement_units_in_R.Rmd0000644000176200001440000004713713430273643020627 0ustar liggesusers--- title: "Measurement units in R" author: "Edzer Pebesma, Thomas Mailund, and James Hiebert" output: html_document: toc: true toc_float: collapsed: false smooth_scroll: false toc_depth: 2 bibliography: measurement_units_in_R.bib link-citations: yes vignette: > %\VignetteIndexEntry{Measurement units in R} %\VignetteEngine{knitr::rmarkdown} %\VignetteEncoding{UTF-8} --- ```{r echo=FALSE} knitr::opts_chunk$set(collapse = TRUE) ``` This vignette is identical to @rj, except for two changes: * it has been synchronized with updates to the [units](https://cran.r-project.org/package=units) package * it has been converted to R-markdown ## Abstract We briefly review SI units, and discuss R packages that deal with measurement units, their compatibility and conversion. Built upon [udunits2](https://cran.r-project.org/package=udunits2) and the UNIDATA udunits library, we introduce the package [units](https://cran.r-project.org/package=units) that provides a class for maintaining unit metadata. When used in expression, it automatically converts units, and simplifies units of results when possible; in case of incompatible units, errors are raised. The class flexibly allows expansion beyond predefined units. Using [units](https://cran.r-project.org/package=units) may eliminate a whole class of potential scientific programming mistakes. We discuss the potential and limitations of computing with explicit units. ## Introduction Two quotes from @cobb -- _Data are not just numbers, they are numbers with a context_ and _in data analysis, context provides meaning_ -- illustrate that for a data analysis to be meaningful, knowledge of the data's context is needed. Pragmatic aspects of this context include who collected or generated the data, how this was done, and for which purpose [@scheider]; semantic aspects concern what the data represents: which aspect of the world do the data refer to, when and where were they measured, and what a value of `1` means. R does allow for keeping some context with data, for instance * `data.frame` columns must have and `list` elements may have names that can be used to describe context, using freetext * `matrix` or `array` objects may have `dimnames` * for variables of class `factor` or `ordered`, `levels` may indicate, using freetext, the categories of nominal or ordinal variables * `POSIXt` and `Date` objects specify how numbers should be interpreted as time or date, with fixed units (second and day, respectively) and origin (Jan 1, 1970, 00:00 UTC) * `difftime` objects specify how time duration can be represented by numbers, with flexible units (secs, mins, hours, days, weeks); [lubridate](https://cran.r-project.org/package=lubridate) [@lubridate] extends some of this functionality. Furthermore, if spatial objects as defined in package [sp](https://cran.r-project.org/package=sp) [@sp] have a proper coordinate reference system set, they can be transformed to other datums, or converted to various flat (projected) representations of the Earth [@iliffe]. In many cases however, R drops contextual information. As an example, we look at annual global land-ocean temperature index (from `http://climate.nasa.gov/vital-signs/global-temperature/`) since 1960: ```{r} temp_data = subset(read.table("647_Global_Temperature_Data_File.txt", header=TRUE)[1:2], Year >= 1960) temp_data$date = as.Date(paste0(temp_data$Year, "-01-01")) temp_data$time = as.POSIXct(temp_data$date) Sys.setenv(TZ="UTC") head(temp_data, 3) year_duration = diff(temp_data$date) mean(year_duration) ``` Here, the time difference units are reported for the `difftime` object `year_duration`, but if we would use it in a linear algebra operation ```{r} year_duration %*% rep(1, length(year_duration)) / length(year_duration) ``` the unit is dropped. Similarly, for linear regression coefficients we see ```{r} coef(lm(Annual_Mean ~ date, temp_data)) coef(lm(Annual_Mean ~ time, temp_data)) ``` where the unit of change is in degrees Celsius but either _per day_ (`date`) or _per second_ (`time`). For purely mathematical manipulations, R often strips context from numbers when it is carried in attributes, the linear algebra routines being a prime example. Most variables are somehow attributed with information about their _units_, which specify what the value `1` of this variable represents. This may be counts of something, e.g. `1 apple`, but it may also refer to some _physical unit_, such as distance in meter. This article discusses how strong unit support can be introduced in R. ## SI The [BIPM](http://www.bipm.org/) (Bureau International des Poids et Mesures) is "_the intergovernmental organization through which Member States act together on matters related to measurement science and measurement standards. Its recommended practical system of units of measurement is the International System of Units (Syst\`{e}me International d'Unit\'{e}s, with the international abbreviation SI)_ (http://www.bipm.org/en/measurement-units/)". @si describe the SI units, where, briefly, _SI units_ * consist of seven base units (length, mass, time \& duration, electric current, thermodynamic temperature, amount of substance, and luminous intensity), each with a name and abbreviation (see table below) * consist of _derived units_ that are formed by products of powers of base units, such as m/s$^2$, many of which have special names and symbols (e.g. angle: 1 rad = 1 m/m; force: 1 N = 1 m kg s$^{-2}$) * consist of _coherent derived units_ when derived units include no numerical factors other than one (with the exception of `kg`; as a base unit, kg can be part of coherent derived units); an example of a coherent derived unit is 1 watt = 1 joule per 1 second, * may contain SI prefixes (k = kilo for $10^3$, m = milli for $10^{-3}$, etc.) * contain special quantities where units disappear (e.g., m/m) or have the nature of a count, in which cases the unit is 1. base quantities, SI units and their symbols (from @si, p. 23): | Base quantity | | SI base unit | | | -----------|--------|----------|------| | Name |Symbol|Name | Symbol | length | $l,x,r,$ etc.| meter | m | | mass | $m$ | kilogram | kg | | time, duration | $t$ | second | s | | electric current| $I, i$ | ampere | A | | thermodynamic temperature | $T$ | kelvin | K | | amount of substance | $n$ | mole | mol | | luminous intensity | $I_v$ | candela | cd | ## Related work in R Several R packages provide unit conversions. For instance, [measurements](https://cran.r-project.org/package=measurements) [@measurements] provides a collection of tools to make working with physical measurements easier. It converts between metric and imperial units, or calculates a dimension's unknown value from other dimensions' measurements. It does this by the `conv_unit` function: ```{r, eval=requireNamespace("measurements", quietly=TRUE)} library(measurements) conv_unit(2.54, "cm", "inch") conv_unit(c("101 44.32","3 19.453"), "deg_dec_min", "deg_min_sec") conv_unit(10, "cm_per_sec", "km_per_day") ``` but uses for instance `kph` instead of `km_per_hour`, and then `m3_per_hr` for flow -- unit names seem to come from convention rather than systematic composition. Object `conv_unit_options` contains all 173 supported units, categorized by the physical dimension they describe: ```{r, eval=requireNamespace("measurements", quietly=TRUE)} names(conv_unit_options) conv_unit_options$volume ``` Function `conv_dim` allows for the conversion of units in products or ratios, e.g. ```{r, eval=requireNamespace("measurements", quietly=TRUE)} conv_dim(x = 100, x_unit = "m", trans = 3, trans_unit = "ft_per_sec", y_unit = "min") ``` computes how many minutes it takes to travel 100 meters at 3 feet per second. Package [NISTunits](https://cran.r-project.org/package=NISTunits) [@NISTunits] provides fundamental physical constants (Quantity, Value, Uncertainty, Unit) for SI and non-SI units, plus unit conversions, based on the data from NIST (National Institute of Standards and Technology). The package provides a single function for every unit conversion; all but 5 from its 896 functions are of the form `NISTxxxTOyyy` where `xxx` and `yyy` refer to two different units. For instance, converting from W m$^{-2}$ to W inch$^{-2}$ is done by ```{r, eval=requireNamespace("NISTunits", quietly=TRUE)} library(NISTunits) NISTwattPerSqrMeterTOwattPerSqrInch(1:5) ``` Both [measurements](https://cran.r-project.org/package=measurements) and [NISTunits](https://cran.r-project.org/package=NISTunits) are written entirely in R. ## UNIDATA's udunits library and the `udunits2` R package Udunits, developed by UCAR/UNIDATA, advertises itself on [its web page](https://www.unidata.ucar.edu/software/udunits/) as: "_The udunits package supports units of physical quantities. Its C library provides for arithmetic manipulation of units and for conversion of numeric values between compatible units. The package contains an extensive unit database, which is in XML format and user-extendable._" The R package [udunits2](https://cran.r-project.org/package=udunits2) [@udunits2] provides a low-level R interface to the most important functions in the udunits2 C library. The functions provided by [udunits2](https://cran.r-project.org/package=udunits2) are ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} library(udunits2) ls(2) ``` Dropping the `ud` prefix, `is.parseable` verifies whether a unit is parseable ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.is.parseable("m/s") ud.is.parseable("q") ``` `are.convertible` specifies whether two units are convertible ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.are.convertible("m/s", "km/h") ud.are.convertible("m/s", "s") ``` `convert` converts units that are convertible, and throws an error otherwise ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.convert(1:3, "m/s", "km/h") ``` and `get.name`, `get.symbol` and `set.encoding` get name, get symbol or modify encoding of the character unit arguments. ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.get.name("kg") ud.get.symbol("kilogram") ud.set.encoding("utf8") ``` Unlike the [measurements](https://cran.r-project.org/package=measurements) and [NISTunits](https://cran.r-project.org/package=NISTunits), [udunits2](https://cran.r-project.org/package=udunits2) parses units as expressions, and bases its logic upon the convertibility of expressions, rather than the comparison of fixed strings: ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} m100_a = paste(rep("m", 100), collapse = "*") dm100_b = "dm^100" ud.is.parseable(m100_a) ud.is.parseable(dm100_b) ud.are.convertible(m100_a, dm100_b) ``` This has the advantage that through complex computations, intermediate objects can have units that are arbitrarily complex, and that can potentially be simplified later on. It also means that the package practically supports an unlimited amount of derived units. ## Udunits versus the Unified Code for Units of Measure (UCUM) Another set of encodings for measurement units is the Unified Code for Units of Measure (UCUM, @ucum). A dedicated web site\footnote{\url{http://coastwatch.pfeg.noaa.gov/erddap/convert/units.html}} describes the details of the differences between udunits and UCUM, and provides a conversion service between the two encoding sets. The UCUM website refers to some Java implementations, but some of the links seem to be dead. UCUM is the preferred encoding for standards from the Open Geospatial Consortium. udunits on the other hand is the units standard of choice by the climate science community, and is adopted by the CF (Climate and Forecast) conventions, which mostly uses NetCDF. NetCDF [@netcdf] is a binary data format that is widely used for atmospheric and climate model predictions. The udunits library is a C library that has strong support from UNIDATA, and we decided to build our developments on this, rather than on Java implementations of UCUM with a less clear provenance. ## Handling data with units in R: the units package The [units](https://cran.r-project.org/package=units) package builds `units` objects from scratch, e.g. where ```{r} library(units) x = set_units(1:5, m/s) str(x) ``` represents speed values in `m/s`. The units `m` and `s` are retrieved from the `ud_units` database, which is part of [units](https://cran.r-project.org/package=units), and was derived from the xml units database that is part of udunits2 C library. Units can be used in arbitrary R expressions like ```{r} set_units(1:3, m/s^2) ``` Several manipulations with `units` objects will now be illustrated. Manipulations that do not involve unit conversion are for instance addition: ```{r} x = set_units(1:3, m/s) x + 2 * x ``` Explicit unit conversion is done by assigning new units: ```{r} (x = set_units(x, cm/s)) as.numeric(x) ``` similar to the behaviour of `difftime` objects, this modifies the numeric values without modifying their meaning (what the numbers refer to). When mixing units in sums, comparisons or concatenation, units are automatically converted to those of the first argument: ```{r} y = set_units(1:3, km/h) x + y y + x x == y c(y, x) ``` where `c(y, x)` concatenates `y` and `x` after converting `x` to the units of `y`. Derived units are created where appropriate: ```{r} x * y x^3 ``` and meaningful error messages appear when units are not compatible: ```{r} e = try(z <- x + x * y) attr(e, "condition")[[1]] ``` The full set of methods and method groups for `units` objects is shown by ```{r} methods(class = "units") ``` where the method groups * `Ops` include operations that require compatible units, converting when necessary (`+`, `-`, `==`, `!=`, `<`, `>`, `<=`, `>=`), and operations that create new units (`*`, `/`, `^` and `**`), * `Math` include `abs`, `sign`, `floor`, `ceiling`, `trunc`, `round`, `signif`, `log`, `cumsum`, `cummax`, `cummin`, and * `Summary` include `sum`, `min`, `max` and `range`, and all convert to the unit of the first argument. When possible, new units are simplified: ```{r} a = set_units(1:10, m/s) b = set_units(1:10, h) a * b ustr1 = paste(rep("m", 101), collapse = "*") ustr2 = "dm^100" as_units(ustr1) / as_units(ustr2) ``` Units are printed as simple R expressions, e.g. ```{r} set_units(1, m^5/s^4) ``` Another way to print units commonly seen in Climate and Forecast Conventions\footnote{CF, \url{http://cfconventions.org/Data/cf-standard-names/34/build/cf-standard-name-table.html}} is `m2 s-1` for m$^2$/s. These are not R expressions, but they can be parsed by `as_units`, and created by `deparse_unit`: ```{r} as_units("m2 s-1") deparse_unit(set_units(1, m^2*s^-1)) ``` The `plot` and `hist` methods add units to default axis labels, an example is shown in the following figures. For [ggplot2](https://cran.r-project.org/package=ggplot2) plots [@ggplot2], automatic unit placement in default axis label is provided by package [ggforce](https://cran.r-project.org/package=ggforce) [@ggforce]; `demo(ggforce)` gives an example. ```{r fig=TRUE, height=3.8, width=7} library(units) units_options(negative_power = TRUE) # initialize variables with units: mtcars$consumption = set_units(mtcars$mpg, mi/gallon) # "in" is also a reserved R keyword, and so needs back-quotes: mtcars$displacement = set_units(mtcars$disp, `in`^3) # convert to SI: mtcars$consumption = set_units(mtcars$consumption, km/l) mtcars$displacement = set_units(mtcars$displacement, cm^3) par(mar = par("mar") + c(0, .3, 0, 0)) with(mtcars, plot(1/displacement, 1/consumption)) ``` ```{r fig=TRUE, height=3.8, width=7, eval=requireNamespace("ggforce", quietly=TRUE)} library(ggforce) if (utils::packageVersion("ggplot2") > "2.2.1") ggplot(mtcars) + geom_point(aes(x = 1/displacement, y = 1/consumption)) ``` Automatic conversion between `units` and `difftime` is provided: ```{r} (dt = diff(Sys.time() + c(0, 1, 1+60, 1+60+3600))) # class difftime (dt.u = as_units(dt)) identical(as_difftime(dt.u), dt) ``` as well as to and from `POSIXct` or `Date`: ```{r} (t1 <- as_units(as.POSIXct("2017-08-20 17:03:00"))) (t2 <- as_units(as.POSIXct("2017-08-20 17:03:00"), "hours since 2017-08-20")) (d1 <- as_units(as.Date("2017-08-20"))) as.POSIXct(t1) as.Date(d1) ``` Objects of class `units` can be used as columns in `data.frame` objects, as well as in `tbl_df` [@tibble]. They can also be `matrix` or `array`, with the constraint that a single unit holds for all elements. ## Discussion and conclusions The [units](https://cran.r-project.org/package=units) R package provides a new class, `units`, for numeric data with associated measurement units. Operations on objects of this class retain the unit metadata and provide automated dimensional analysis: dimensions are taken into consideration in computations and comparisons. Combining different units that are compatible triggers automatic unit conversion, derived units are automatically generated and simplified where possible, and meaningful error messages are given when a user tries to add objects with incompatible units. This verifies that computations are not only syntactically and numerically allowed, but also semantically, and in the case of physical units, physically allowed, which may support code verification and provenance tracking. Using this package may eliminate a whole class of potential scientific programming mistakes. Where the R packages [measurements](https://cran.r-project.org/package=measurements) and [NISTunits](https://cran.r-project.org/package=NISTunits) provide conversion between a fixed number of units, with the help of the udunits2 C library and unit database, R package [units](https://cran.r-project.org/package=units) handles arbitrarily complex derived units. By treating units as expressions it can derive, convert and simplify units. In addition, beyond the SI units packaged, [units](https://cran.r-project.org/package=units) handles user-defined units. Data in `units` vectors can be stored as columns in `data.frame` or `tbl_df` objects, and can be converted to and from `difftime`. When `units` objects have associated time and location information, they could be stored in spatial or spatio-temporal objects provided by [sp](https://cran.r-project.org/package=sp) or [spacetime](https://cran.r-project.org/package=spacetime) [@spacetime] as these store attribute data in `data.frame` slots, but for instance not in `zoo` [@zoo] or `xts` [@xts] objects, as these latter two set the class attribute of a vector or matrix. Despite all standardization efforts, units may still be ambiguous, or subject to interpretation. For instance for the duration of one year [NISTunits](https://cran.r-project.org/package=NISTunits) or [udunits2](https://cran.r-project.org/package=udunits2) give us an answer that depends on whether we want a common, leap, Gregorian, Julian, tropical or siderial year (@lang, see also `demo(year)`). This illustrates that those who apply unit conversion should be aware of possible pitfalls. Support for calendars in udunits seems not as well developed as in R. Future work includes extending packages that read external data from formats, databases or interfaces with support for measurement unit information into R, preserving the measurement unit information. Examples would be interfaces to HDF5 (e.g., [h5](https://cran.r-project.org/package=h5), @h5), [RNetCDF](https://cran.r-project.org/package=RNetCDF) [@RNetCDF] or [sos4R](https://cran.r-project.org/package=sos4R) [@sos4R]. It would be nice to see units of measurements propagate into units of regression coefficient estimates. # Acknowledgements We acknowledge three anonymous reviewers and the handling editor for their constructive comments, and Thomas Lin Pedersen for implementing the ggplot extensions in package `ggforce` that automatically add units to default ggplot axis labels. # References units/vignettes/units.Rmd0000644000176200001440000001555513230500577015247 0ustar liggesusers--- title: "Units of Measurement for R Vectors: an Introduction" output: html_document: toc: true theme: united vignette: > %\VignetteIndexEntry{Units of Measurement for R Vectors: an Introduction} %\VignetteEngine{knitr::rmarkdown} %\VignetteEncoding{UTF-8} --- ```{r echo=FALSE} knitr::opts_chunk$set(collapse = TRUE) ``` ```{r echo=FALSE} units:::units_options(negative_power = FALSE) ``` R has little support for physical measurement units. The exception is formed by time differences: time differences objects of class `difftime` have a `units` attribute that can be modified: ```{r} t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 class(d) units(d) d units(d) = "secs" d ``` We see here that the `units` method is used to retrieve and modify the unit of time differences. The `units` package generalizes this idea to other physical units, building upon the [udunits2](https://cran.r-project.org/package=udunits2) R package, which in turn is build upon the [udunits2](https://www.unidata.ucar.edu/software/udunits/) C library. The `udunits2` library provides the following operations: * validating whether an expression, such as `m/s` is a valid physical unit * verifying whether two units such as `m/s` and `km/h` are convertible * converting values between two convertible units * providing names and symbols for specific units * handle different character encodings (utf8, ascii, iso-8859-1 and latin1) The `units` R package uses R package [`udunits2`](https://cran.r-project.org/package=udunits2) to extend R with functionality for manipulating numeric vectors that have physical measurement units associated with them, in a similar way as `difftime` objects behave. ## Setting units, unit conversion Existing units are resolved from a database in the `units` package, called `ud_units`. We can see the first three elements of it by ```{r} library(units) ud_units[1:3] ``` We can set units to numerical values by `set_units`: ```{r} (a <- set_units(runif(10), m/s)) ``` the result, e.g. ```{r} set_units(10, m/s) ``` literally means "10 times 1 m divided by 1 s". In writing, the "1" values are omitted, and the multiplication is implicit. The `units` package comes with a list of over 3000 predefined units, ```{r} length(ud_units) ``` We can retrieve a single unit from the `ud_units` database by ```{r} with(ud_units, km/h) ``` ### Unit conversion When conversion is meaningful, such as hours to seconds or meters to kilometers, conversion can be done explicitly by setting the units of a vector ```{r} b = a units(b) <- with(ud_units, km/h) b ``` ## Basic manipulations ### Arithmetic operations Arithmetic operations verify units, and create new ones ```{r} a + a a * a a ^ 2 a ** -2 ``` and convert to the units of the first argument if necessary: ```{r} a + b # m/s + km/h -> m/s ``` Currently, powers are only supported for integer powers, so using `a ** 2.5` would result in an error. ### Unit simplification There are some basic simplification of units: ```{r} t <- with(ud_units, s) a * t ``` which also work when units need to be converted before they can be simplified: ```{r} t <- with(ud_units, min) a * t ``` Simplification to unit-less values gives the "1" as unit: ```{r} m <- with(ud_units, m) a * t / m ``` Allowed operations that require convertible units are `+`, `-`, `==`, `!=`, `<`, `>`, `<=`, `>=`. Operations that lead to new units are `*`, `/`, and the power operations `**` and `^`. ### Mathematical functions Mathematical operations allowed are: `abs`, `sign`, `floor`, `ceiling`, `trunc`, `round`, `signif`, `log`, `cumsum`, `cummax`, `cummin`. ```{r} signif(a ** 2 / 3, 3) cumsum(a) log(a) # base defaults to exp(1) log(a, base = 10) log(a, base = 2) ``` ### Summary functions Summary functions `sum`, `min`, `max`, and `range` are allowed: ```{r} sum(a) min(a) max(a) range(a) with(ud_units, min(m/s, km/h)) # converts to first unit: ``` ### Printing Following `difftime`, printing behaves differently for length-one vectors: ```{r} a a[1] ``` ### Subsetting The usual subsetting rules work: ```{r} a[2:5] a[-(1:9)] ``` ### Concatenation ```{r} c(a,a) ``` concatenation converts to the units of the first argument, if necessary: ```{r} c(a,b) # m/s, km/h -> m/s c(b,a) # km/h, m/s -> km/h ``` ## Conversion to/from `difftime` From `difftime` to `units`: ```{r} t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 (du = as_units(d)) ``` vice versa: ```{r} (dt = as_difftime(du)) class(dt) ``` ## units in `matrix` objects ```{r} set_units(matrix(1:4,2,2), m/s) set_units(matrix(1:4,2,2), m/s * m/s) ``` but ```{r} set_units(matrix(1:4,2,2), m/s) %*% set_units(4:3, m/s) ``` strips units. ## units objects in `data.frame`s units in `data.frame` objects are printed, but do not appear in `summary`:. ```{r} set.seed(131) d <- data.frame(x = runif(4), y = set_units(runif(4), s), z = set_units(1:4, m/s)) d summary(d) d$yz = with(d, y * z) d d[1, "yz"] ``` ## formatting Units are often written in the form `m2 s-1`, for square meter per second. This can be defined as unit, and also parsed by `as_units`: ```{r} (x = 1:10 * as_units("m2 s-1")) ``` udunits understands such string, and can convert them ```{r} y = 1:10 * with(ud_units, m^2/s) x + y ``` Printing units in this form is done by ```{r} deparse_unit(x) ``` ## plotting Base scatter plots and histograms support automatic unit placement in axis labels. In the following example we first convert to SI units. (Unit `in` needs a bit special treatment, because `in` is a reserved word in R.) ```{r fig=TRUE} mar = par("mar") + c(0, .3, 0, 0) displacement = mtcars$disp * ud_units[["in"]]^3 units(displacement) = with(ud_units, cm^3) weight = mtcars$wt * 1000 * with(ud_units, lb) units(weight) = with(ud_units, kg) par(mar = mar) plot(weight, displacement) ``` We can change grouping symbols from `[ ]` into `( )`: ```{r} units_options(group = c("(", ")") ) # parenthesis instead of square brackets par(mar = mar) plot(weight, displacement) ``` We can also remove grouping symbols, increase space between variable name and unit by: ```{r} units_options(sep = c("~~~", "~"), group = c("", "")) # no brackets; extra space par(mar = mar) plot(weight, displacement) ``` More complex units can be plotted either with negative powers, or as divisions, by modifying one of `units`'s global options using `units_options`: ```{r} gallon = as_units("gallon") consumption = mtcars$mpg * with(ud_units, mi/gallon) units(consumption) = with(ud_units, km/l) par(mar = mar) plot(displacement, consumption) # division in consumption units_options(negative_power = TRUE) # division becomes ^-1 plot(displacement, consumption) # division in consumption ``` As usual, units modify automatically in expressions: ```{r} units_options(negative_power = TRUE) # division becomes ^-1 par(mar = mar) plot(displacement, consumption) plot(1/displacement, 1/consumption) ``` ```{r echo=FALSE} units_options(negative_power = FALSE) # division becomes / ``` units/vignettes/647_Global_Temperature_Data_File.txt0000644000176200001440000000676313203543612022245 0ustar liggesusers Year Annual_Mean 5-year_Mean 1880 -0.19 NA 1881 -0.10 NA 1882 -0.08 -0.16 1883 -0.19 -0.19 1884 -0.26 -0.22 1885 -0.30 -0.27 1886 -0.29 -0.27 1887 -0.32 -0.24 1888 -0.19 -0.25 1889 -0.10 -0.24 1890 -0.35 -0.22 1891 -0.23 -0.24 1892 -0.25 -0.28 1893 -0.28 -0.25 1894 -0.29 -0.23 1895 -0.20 -0.20 1896 -0.14 -0.20 1897 -0.10 -0.17 1898 -0.27 -0.15 1899 -0.15 -0.15 1900 -0.08 -0.18 1901 -0.14 -0.20 1902 -0.27 -0.25 1903 -0.35 -0.29 1904 -0.43 -0.31 1905 -0.27 -0.33 1906 -0.21 -0.35 1907 -0.39 -0.35 1908 -0.42 -0.38 1909 -0.46 -0.43 1910 -0.42 -0.42 1911 -0.44 -0.40 1912 -0.34 -0.34 1913 -0.33 -0.27 1914 -0.15 -0.25 1915 -0.10 -0.26 1916 -0.33 -0.24 1917 -0.39 -0.26 1918 -0.25 -0.29 1919 -0.22 -0.26 1920 -0.25 -0.24 1921 -0.20 -0.23 1922 -0.26 -0.24 1923 -0.23 -0.23 1924 -0.27 -0.21 1925 -0.19 -0.19 1926 -0.09 -0.19 1927 -0.20 -0.20 1928 -0.21 -0.19 1929 -0.35 -0.19 1930 -0.13 -0.18 1931 -0.08 -0.20 1932 -0.15 -0.15 1933 -0.27 -0.16 1934 -0.12 -0.17 1935 -0.18 -0.14 1936 -0.14 -0.09 1937 -0.01 -0.07 1938 -0.01 -0.02 1939 -0.02 0.04 1940 0.09 0.06 1941 0.13 0.09 1942 0.10 0.15 1943 0.14 0.15 1944 0.26 0.12 1945 0.13 0.09 1946 -0.03 0.05 1947 -0.04 -0.02 1948 -0.09 -0.08 1949 -0.09 -0.09 1950 -0.18 -0.08 1951 -0.07 -0.05 1952 0.01 -0.05 1953 0.08 -0.05 1954 -0.12 -0.07 1955 -0.14 -0.07 1956 -0.19 -0.07 1957 0.04 -0.04 1958 0.06 -0.02 1959 0.03 0.03 1960 -0.03 0.03 1961 0.05 0.03 1962 0.02 -0.02 1963 0.06 -0.04 1964 -0.21 -0.06 1965 -0.10 -0.07 1966 -0.05 -0.09 1967 -0.03 -0.04 1968 -0.07 -0.01 1969 0.06 -0.02 1970 0.03 -0.01 1971 -0.09 0.03 1972 0.01 0.00 1973 0.15 -0.00 1974 -0.08 -0.01 1975 -0.01 0.03 1976 -0.11 0.01 1977 0.18 0.06 1978 0.07 0.12 1979 0.17 0.20 1980 0.28 0.19 1981 0.33 0.24 1982 0.13 0.24 1983 0.31 0.21 1984 0.16 0.18 1985 0.12 0.22 1986 0.19 0.24 1987 0.34 0.27 1988 0.40 0.33 1989 0.29 0.38 1990 0.44 0.35 1991 0.42 0.32 1992 0.23 0.33 1993 0.24 0.33 1994 0.32 0.32 1995 0.46 0.37 1996 0.34 0.44 1997 0.47 0.47 1998 0.63 0.46 1999 0.42 0.50 2000 0.42 0.53 2001 0.54 0.53 2002 0.63 0.55 2003 0.62 0.60 2004 0.54 0.62 2005 0.69 0.63 2006 0.63 0.61 2007 0.66 0.63 2008 0.53 0.64 2009 0.64 0.63 2010 0.72 0.62 2011 0.60 0.65 2012 0.63 0.67 2013 0.65 0.70 2014 0.74 NA 2015 0.87 NA units/R/0000755000176200001440000000000013547030261011616 5ustar liggesusersunits/R/summaries.R0000644000176200001440000000307713472516125013762 0ustar liggesusers# Inside the group generic functions we do have .Generic even if the diagnostics # think we do not. # !diagnostics suppress=.Generic #' @export Summary.units = function(..., na.rm = FALSE) { OK <- switch(.Generic, "sum" = , "min" = , "max" = , "range" = TRUE, FALSE) if (! OK) stop(paste("Summary operation", .Generic, "not allowed")) args <- list(...) if (length(args) > 1) { args <- do.call(c, args) # turns args into a single units vector do.call(.Generic, c(list(args), na.rm = na.rm)) # concatenate, convert if necessary, re-call with length 1 arg } else .as.units(NextMethod(), units(args[[1]])) } #' @export print.units = function (x, ...) { # nocov start gr = units_options("group") if (is.array(x) || length(x) > 1L) { cat("Units: ", paste0(gr[1], as.character(attr(x, "units")), gr[2]), "\n", sep = "") x <- drop_units(x) NextMethod() } else { cat(format(x, ...), "\n", sep="") invisible(x) } } # nocov end #' @export mean.units = function(x, ...) { .as.units(NextMethod(), units(x)) } #' @export weighted.mean.units = function(x, w, ...) { if (!missing(w) && inherits(w, "units")) w = drop_units(w) .as.units(NextMethod(), units(x)) } #' @export median.units = mean.units #' @export quantile.units = function(x, ...) { .as.units(quantile(unclass(x), ...), units(x)) } #' @export format.units = function(x, ...) { gr = units_options("group") u = paste0(gr[1], units(x), gr[2]) setNames(paste(NextMethod(), u), names(x)) } #' @export summary.units = function(object, ...) { summary(unclass(object), ...) } units/R/sysdata.rda0000644000176200001440000002744113527327534014000 0ustar liggesusersBZh91AY&SY3$HRpN (Z@G740 p>=a[a#a1À2t _v46`^ḽ짵'=v@'Xӛٸt0&'4ަM$觥2cPh4Ԋ76JS)4ڒ= @4iʟCA)"?T @OhTQOPf '@ F!<OSH=*=OD&J?SMA!4=!"D%BF$$%l!>D%DHHD& != $ ,$?/ϫ|suvmmmmmmmmm~7G{='Wg?/:~(4yz]I$I$I$I$I=6߶u]uԒI$I$~tM4M4ВI$I$I$I$I$I$I$I$I$I$I$n{>?OwAr|/Dm}>k|vەml兖 o-V߫nVmkvBnݻv۷nd,9zs~gv[V͟chQowM6v6;9rH5s'&Qi{>x'鶉+/s |o>_%ͽ9$I$I$I'OgiiiiikZnwwwwwww}LdI$u2xozef^>=zˇ^ׯ:EUI$I$I$QԒI$I$RI]yj/DVܽ_H #kzqt]ֳ [ExzS+k-x7o''ÆOOO>^~.0y>CgO ^^|~$~+gM=~sz >-Y [ExZMxmgN7՟ %Y6;!4CkHsִϲ Wt׷kf6.o}wڳ W#GWhmi_Cֳ@8yo~+Wy@9yo7yL $"Hh$BXBDGU5ݻvjիVZjѹjիVEQEQEQEQEQEQEQEQEQEQE<Ƽ^U/*ݫ~/_UUUUUUUUUUUUUUUUUUVzޱ<&~^zׯ^yB (PB (PB (PE׾/A{ׯ^zׯ^z׽^NNF 0` (PB (PB (PB (PB (PB (PB (PB (PB ^zׯ^zׯ^z|~/{{-|yE.`M~^I|7͛{ʮ/-oyjydshs-uyyZ`͒O///,|7|7|?Y?4~Ozi?W`QEQEQGwvQusIvSIݹ'u`{$ Ej4^SE-M֢nݷDk$"$~_1XCYW{ܲCsrY;|s'?'Qɛ}u~mGWUUUUUUUUUUUUUUUUUUUUP~///////////////////>c說ETQEQG?jr}W>HsttUs}_V/ɫϣg٣r{=/Weffʾg((((?eQk ª{xxxxxxxxxxxxxxxxxxxxxxxxUx~WY,K%dY,K%Y,K%o<<<7<<<<<<<<<<<<<<)%?$(nJ6b1soQj\0hDTQkу6K\m5ZQ5:hɛ5MTdE&ꢏm sUTتUYͽWG}|g}_7}_gnVϋ>*b}Es'-z0h&M_DܟG}]btZ&l(h%(7UZ`͒O檫UYѽWUhr*\uUUF $ErQutQz)m/rwM]4pfע ]XQ.bgf'6V(ɣ5MXc3wfuQD梉Qђ3tQzTd͚MUdEZ&ꢋ^I%\F̔QuZ&4Q4QQ h$-EMuz^zfsjf=Y3fM^0hh$(nJ6b1soQj\0hDTQkу6I2QDܔlE]bޣ3fEE.`Fףl{lI4${{W0E.)ܒ,X98&䘯b{bŋh$N Ź&+ط^sXb-"Ńi1nI-\,X{rB,X98&䘯b{bn˞q\I  \ZbHb4${V خ`V,\SE$XrpM&-1^Ž+"ŋonI,I͓k& 0dL8ܜ\W={ExVkݓE.`n{޵%zV)ܓ`7onI,I6Mpd\Y2qMd4${ خ`9.E{$Y81qM&M2^ɽK"ɋonI,I赓K2\&LSG|w$&N Ź&+ط^sXb-"Ńi1nIQb%X``ܒ,W8&䘯b{bŋh$N Ź&+ط^sXb-"Ńi1nI-\) o1$H1$H1$H0I4MjI-.-Dx &@ &HtsHnMRE͒i:7$ͽEb o1$Hr(\ \i"i i I4LI4LM4 ! ,1$H1$H7rh$ SE5-M֢@4SZiMj) \M4DjVE4jhSI5ȉ/^/6 ^SHkQM Z)E4jhSHkQM Z)E4jh@RMՠ!> H($  BIR$H$H I$D%A!$I HLH褒"$(%QPJ* EQPJ,"QPQPJ,QA(EDJ(%%ZQ%"JEDI)R*$TIHDJ*RIHI%"a%"R)$TIHTJU%Q*TJ%RIHI*U%XJa TJRHTII"R%DE!?_b!4$BY N8_o=m}nqq88Ap 2m[JA@RT]JRff͇!! RI$wy$[TmR}I'y$L    #_qq88n@Gqw~wwwyp ?0 2 2x88qg#6յt $$RI=?'յI$III'$I$$InͨnG?R[*bcZUUZbbҫq*SiXTUUUS5kE\/LH-kZֵֵk[ g$mI$wI$檹U^Uګy0X)XָUVk^5ӥWEi%kZUk+ұ©X*k ִ^W;߿u]뮽:2)[j[boMkZֵkZtew?뮺cmmmu%!!% mmmmӮJ1#Cnm]ⱏ*I :Rzkύa^XbZjիV[jլcmVՎUV&rO¶ڤI;$g$^u$fII$;Gjƒp GzN|ϟ<9q@tb!JDl2mmm;mmޝx ш1c1c֤I'y$L˿p mF$2IMON+jNĒI$$ImSII'y$L/{*޶+UW X)XָUVk^5ӥWEi%kZUk+ұ©X*k ִF i#ҎaU]0X)XָUVk^ kJӌJ&1LV5cRUUULTiƌ)yy@i) 4M'iM4M4à #pD@TZ$"""@$"B"@""Bbb11#6 DD@\.BgE!d#HDnp DE@bbhB7F,c!d#hD1nDHZ" "$"""""""B #'uU^jURy %Q[|]uUUUyUmmU֪mj:5.kZkWg@\x1c۷JR88!H!Yg)JRww]ufիT=Bffnf߹fT9zAOp뮺B]c3337s333`ʪC wqqqŴMeC@, |  Є!eǍ~ֵ|kZֳp 9  y=4]uI3p +mնSOrs*bcW&I$"Tp*.+jVݫZֵI>Pqq2jUu_]κ뮺뮺<=uק]CkV+%wbk\qJoS߿~?>yyd]q8ww@I$y$ p 77˚JU^UXUb @5)Ffn 2۷nݻv*WwvhRVk]d]uN<{9s9]uL<  l7gqqoqӎ7vvlpy(qUy0X)XָWÌ'G* aJƵƪXSZlkJӌJ&1LV5cRUUULT=:t]0`I18k]1*$Bx%tָZ)ƴp & @b5馚iM+hNt=n$I$$Ie+UW5V+yUbUX @L `;]uUP 2<77˚I$$IUUUWp8`@$sM,HEJ6w߿yߧ~ݻvw>uK " aaaab XXXXXXXXXX4V-XXXM44;뮺>3B" aaaab XXXXXXXXXX5t ]øϞ1TQڀøϞSm@p2 2@z 2 2>51TQeYeYn%U].TRRg`u333pjIZV'jI$I&xڵDªl0V+ V55UU&*כҫ}W"Ԗ-ȪˑjKdjqx8Z)蜲EP A5ֵb"2UUTeWbXV+]ǏkZZֵk:-VZs\יƌ)?Oߴdmmm3-mS3̷ mmmeܑjf`HHK|^kXx!% 0UUUUULUm| 2 v۷nݽN!>$\aU]`Vk\k|9yy珟<z;w}Yc]:UtV.ߓ3jc,qqwbrUU\VeY*nRշ5yW)UbkJ b @L aٛ3336UUUUGj7I'UÇ ϭ߃36 UUUW8P$JLsyyYh0 0 0 4q2_19iJR6S)LiM鄺bs'9b1```vݻm۶ukZֵZkYn@_mUU[m[Um&'wI$ 2m^*j~pIP̟?_ݫ@A e2I#2EVf[mmme2I#Ors*bcZUUZ$[F0c^F^bQDDDDBUUUUUUWr N;wwwwUUUCp kXRWjWlc0@ % aHRB0,[ ]u]u<ߞyܴʙs ZZլZٶN9vmmvm-ݭmBm]m$mmNH%9qs4 ZֵWuM֓9vmmmŶݭmHK]m$m`vA(@[[mbOֵk]R_L#87[m?' * > H>>?'|L/Jmcwws<ϖ{ILT` Q)뮺뮻]uuSmmm2}UW aJƵƪ|뮺=JZշjb+J鉭q*SX$Bc!?x$B[jb50Tm}ߟsLp)v7L$ٴI-$Smmmmmmmmmmo|%o6$II ]s Ѻ.RI$I$mmmvkmmmmmֳ߫$|)QqUzX`Vk\jULU5c_o> 2ꮰ58VcLqӢ©XW]uק]uӌ*0X)XֿljGLUWJ&*:~5ӥWEi%kZUk+ұ©XJ0x IkZԓ$N~_A@~a⪼VV*XUz`Vk\jULU5&5ӥWEi%kZUk+ұ©X*k iƌ)>/oooo7@[7v`p nnwwww~wwwyp p p ݀ddjګo[UVV[uUT ""ܑN$ units/R/symbolic_units.R0000644000176200001440000001126313420665743015020 0ustar liggesusers .symbolic_units <- function(numerator, denominator = vector("character")) { structure(list(numerator = numerator, denominator = denominator), class = "symbolic_units") } .multiply_symbolic_units <- function(value, e1, e2) { numerator <- sort(c(e1$numerator, e2$numerator)) denominator <- sort(c(e1$denominator, e2$denominator)) .simplify_units(value, .symbolic_units(numerator, denominator)) } .invert_symbolic_units <- function(e) { .symbolic_units(e$denominator, e$numerator) } .divide_symbolic_units <- function(value, e1, e2) { .multiply_symbolic_units(value, e1, .invert_symbolic_units(e2)) } .same_units <- function(e1, e2) { identical(e1$numerator, e2$numerator) && identical(e1$denominator, e2$denominator) } # Inside the group generic functions we do have .Generic even if the diagnostics # think we do not. # !diagnostics suppress=.Generic #' @export Ops.symbolic_units <- function(e1, e2) { if (nargs() == 1) stop(paste("unary", .Generic, "not defined for \"units\" objects")) eq <- switch(.Generic, "==" = , "!=" = TRUE, FALSE) if (eq) { if (.Generic == "==") .same_units(e1, e2) else !.same_units(e1, e2) } else stop(paste("operation", .Generic, "not allowed for symbolic operators")) # nocov } #' The "unit" type for vectors that are actually dimension-less. #' @export unitless <- .symbolic_units(vector("character"), vector("character")) .pretty_print_sequence <- function(terms, op, neg_power = FALSE, sep = "") { # `fix` handles cases where a unit is actually an expression. We would have to # deparse these to really do a pretty printing, but for now we leave them alone... fix <- function(term) { if (length(grep("/", term)) || length(grep("-", term))) paste0("(", term, ")") else term } fixed <- vapply(terms, fix, "") fixed_tbl <- table(fixed) names <- names(fixed_tbl) result <- vector("character", length(fixed_tbl)) for (i in seq_along(fixed_tbl)) { name <- names[i] value <- fixed_tbl[i] if (value > 1 || (value == 1 && neg_power)) { if (neg_power) value <- value * -1. result[i] <- paste0(name, "^", value) } else { result[i] <- name } } paste0(result, collapse = paste0(op, sep)) } #' @export as.character.symbolic_units <- function(x, ..., neg_power = get(".units.negative_power", envir = .units_options), escape_units = FALSE, plot_sep = "") { sep <- plot_sep numerator <- x$numerator denominator <- x$denominator if (escape_units) { numerator <- unlist(Map(function(name) paste0("`", name, "`", sep = ""), numerator)) denominator <- unlist(Map(function(name) paste0("`", name, "`", sep = ""), denominator)) } if (x == unitless) { # xxx u <- if (escape_units) unlist(Map(function(name) paste0("`", name, "`", sep = ""), units_options("unitless_symbol"))) else units_options("unitless_symbol") return(u) } num_str <- if (length(numerator) > 0) .pretty_print_sequence(numerator, "*", FALSE, plot_sep) else { # only denominator: if (! neg_power) "1" # 1/cm^2/h else character(0) } denom_str <- if (length(denominator) > 0) { sep <- if (neg_power) paste0("*", plot_sep) else "/" .pretty_print_sequence(denominator, sep, neg_power, plot_sep) } else character(0) if (length(num_str) == 0) denom_str else if (length(denom_str) == 0) num_str else paste(num_str, denom_str, sep = sep) } .simplify_units <- function(value, sym_units) { simplify = .units.simplify() if (!is.na(simplify) && !simplify) { # isFALSE(simplify) value = unclass(value) units(value) = sym_units return(value) } # This is just a brute force implementation that takes each element in the # numerator and tries to find a value in the denominator that can be converted # to the same unit. It modifies "value" to rescale the nominator to the denominator # before removing matching units. drop_ones = function(u) u[ u != "1" ] class(value) <- "units" new_numerator <- drop_ones(sym_units$numerator) new_denominator <- drop_ones(sym_units$denominator) delete_num <- c() for (i in seq_along(new_numerator)) { str1 <- new_numerator[i] for (j in seq_along(new_denominator)) { str2 <- new_denominator[j] if (are_convertible(str1, str2)) { attr(value, "units") <- units(as_units(str1)) units(value) <- str2 delete_num <- c(delete_num, i) new_denominator <- new_denominator[-j] break } } } if (length(delete_num) > 0) new_numerator <- new_numerator[-delete_num] as_units(drop_units(value), .symbolic_units(new_numerator, new_denominator)) } units/R/set_units.R0000644000176200001440000000265413463271333013771 0ustar liggesusers #' set_units #' #' A pipe friendly version of \code{units<-} #' #' @param x a numeric to be assigned units, or a units object to have units #' converted #' #' @param value a \code{units} object, or something coercible to one with #' \code{as_units}. Depending on \code{mode}, the unit is constructed from the #' supplied bare expression or from the supplied value via standard #' evaluation. #' #' @param ... passed on to \code{as_units} #' #' @param mode if \code{"symbols"} (the default), then unit is constructed from #' the expression supplied. Otherwise, if\code{mode = "standard"}, #' standard evaluation is used for the supplied value This argument can be set #' via a global option \code{units_options(set_units_mode = "standard")} #' #' @export #' @rdname set_units #' @seealso \code{\link{as_units}} set_units <- function(x, value, ..., mode = units_options("set_units_mode")) UseMethod("set_units") #' @export set_units.numeric <- function(x, value, ..., mode = units_options("set_units_mode")) { if (missing(value)) value <- unitless else if (mode == "symbols") { value <- substitute(value) if(is.numeric(value) && !identical(value, 1) && !identical(value, 1L)) stop("The only valid number defining a unit is '1', signifying a unitless unit") } units(x) <- as_units(value, ...) x } #' @export set_units.logical <- set_units.numeric #' @export set_units.units <- set_units.numeric units/R/deprecated.R0000644000176200001440000000165713472516125014057 0ustar liggesusers #' Deprecated functions #' #' The following functions are deprecated and will be removed in a future release. #' #' @param chr length 1 character string #' #' @export #' @rdname deprecated make_unit <- function(chr) { .Deprecated("as_units", msg = "make_unit() is deprecated. Please use as_units()") if (!ud_is_parseable(chr)) warning(paste(sQuote(chr), "is not a valid unit symbol recognized by udunits"), call.=FALSE) as_units.character(chr, force_single_symbol = TRUE, check_is_valid = FALSE) } #' @export #' @rdname deprecated parse_unit <- function(chr) { .Deprecated("as_units", msg = "parse_unit() is deprecated. Please use as_units()") as_units.character(chr, implicit_exponents = TRUE) } #' @export #' @name deprecated #' @param x a numeric #' @param value a units object, by default, unitless as.units <- function(x, value = unitless) { .Deprecated("as_units") # nocov as_units(x, value = value) # nocov } units/R/arith.R0000644000176200001440000001345213407161360013055 0ustar liggesusers # Inside the group generic functions we do have .Generic even if the diagnostics # think we do not. # !diagnostics suppress=.Generic #' S3 Ops Group Generic Functions for units objects #' #' Ops functions for units objects, including comparison, product and divide, add, subtract #' #' @param e1 object of class \code{units}, #' or something that can be coerced to it by \code{as_units(e1)} #' @param e2 object of class \code{units}, #' or something that can be coerced to it by \code{as_units(e2)}, #' or in case of power a number (integer n or 1/n) #' #' @return object of class \code{units} #' @export #' #' @examples #' a <- set_units(1:3, m/s) #' b <- set_units(1:3, m/s) #' a + b #' a * b #' a / b #' a <- as_units("kg m-3") #' b <- set_units(1, kg/m/m/m) #' a + b #' a = set_units(1:5, m) #' a %/% a #' a %/% set_units(2) #' set_units(1:5, m^2) %/% set_units(2, m) #' a %% a #' a %% set_units(2 ) Ops.units <- function(e1, e2) { if (missing(e2)) return(NextMethod()) eq <- .Generic %in% c("+", "-", "==", "!=", "<", ">", "<=", ">=") # requiring identical units prd <- .Generic %in% c("*", "/", "%/%") # product-type pw <- .Generic %in% c( "**", "^") # power-type mod <- .Generic == "%%" # modulo pm <- .Generic %in% c("+", "-") # addition-type if (! any(eq, prd, pw, mod)) stop(paste("operation", .Generic, "not allowed")) if (eq) { if (!(inherits(e1, "units") && inherits(e2, "units"))) stop("both operands of the expression should be \"units\" objects") # nocov units(e2) <- units(e1) # convert before we can compare; errors if unconvertible } if (prd) { if (!inherits(e1, "units")) e1 <- set_units(e1, 1) # TODO: or warn? if (!inherits(e2, "units")) e2 <- set_units(e2, 1) # TODO: or warn? ve1 <- unclass(e1) ; ue1 <- units(e1) ve2 <- unclass(e2) ; ue2 <- units(e2) if (.Generic == "*") { numerator <- sort(c(ue1$numerator, ue2$numerator)) denominator <- sort(c(ue1$denominator, ue2$denominator)) } else { numerator <- sort(c(ue1$numerator, ue2$denominator)) denominator <- sort(c(ue1$denominator, ue2$numerator)) } return(.simplify_units(NextMethod(), .symbolic_units(numerator, denominator))) } else if (pw) { # FIXME: I am not sure how to take powers of non-integers yet if (identical(units(e1), set_units(1))) return(set_units(unclass(e1) ^ e2, set_units(1))) if (inherits(e2, "units")) stop("power operation only allowed with numeric power") if (length(e2) > 1L) { if (length(unique(e2)) == 1) # all identical e2 = e2[1] else # return mixed units: return(.as.mixed_units(mapply("^", e1, e2, SIMPLIFY=FALSE))) } # if (round(e2) != e2) # stop("currently you can only take integer powers of units") # we repeat each unit the number of times given by e2. They are already # sorted so they will remain sorted. We need to flip numerator and denominator # when the power is negative and we have a special case when it is zero where # units should be removed. if (e2 == 0) u <- set_units(1) # else if (e2 > 0) # u <- .symbolic_units(rep(units(e1)$numerator, e2), # rep(units(e1)$denominator, e2)) # else # u <- .symbolic_units(rep(units(e1)$denominator, abs(e2)), # rep(units(e1)$numerator, abs(e2))) else if (e2 >= 1) { if (round(e2) != e2) { stop("currently you can only take integer powers of units above 1")} u <- .symbolic_units(rep(units(e1)$numerator, e2), rep(units(e1)$denominator, e2)) } else if (e2 <= -1) { if (round(e2) != e2) { stop("currently you can only take integer powers of units below -1")} u <- .symbolic_units(rep(units(e1)$denominator, abs(e2)), rep(units(e1)$numerator, abs(e2))) } else { # -1 < e2 < 0 || 0 < e2 < 1 if ((1/e2) %% 1 != 0) { stop("not a integer divisor")} # work on wording if (any((table(units(e1)$denominator)*e2) %% 1 != 0) || any((table(units(e1)$numerator)*e2) %% 1 != 0)) { stop("units not divisible")} # work on wording if (e2 > 0) # 0 < e2 < 1 u <- .symbolic_units( rep(unique(units(e1)$numerator),table(units(e1)$numerator)*e2), rep(unique(units(e1)$denominator),table(units(e1)$denominator)*e2)) else # -1 < e2 < 0 u <- .symbolic_units( rep(unique(units(e1)$denominator),table(units(e1)$denominator)*abs(e2)), rep(unique(units(e1)$numerator),table(units(e1)$numerator)*abs(e2))) } } else # eq, plus/minus, mod: u <- units(e1) if (eq && !pm) { dimension = dim(structure(as.numeric(e1), dim = dim(e1)) == structure(as.numeric(e2), dim = dim(e2))) structure(as.logical(NextMethod()), dim = dimension) } else .as.units(NextMethod(), u) } #' #' matrix multiplication #' #' @name matmult #' #' @param x numeric matrix or vector #' #' @param y numeric matrix or vector #' #' @export #' #' @details see \code{"\link[base]{\%*\%}"} for the base function, reimplemented #' #' as default method #' `%*%` = function(x, y) UseMethod("%*%") #' #' #' @name matmult #' #' @export #' `%*%.default` = function(x, y) { #' if (inherits(y, "units")) #' `%*%.units`(x, y) #' else #' base::`%*%`(x, y) #' } #' #' #' @name matmult #' #' @export #' #' @examples #' #' a = set_units(1:5, m) #' #' a %*% a #' #' a %*% t(a) #' #' a %*% set_units(1:5, 1) #' #' set_units(1:5, 1) %*% a #' `%*%.units` = function(x, y) { #' ret = `%*%.default`(unclass(x), unclass(y)) #' units(ret) = .multiply_symbolic_units(1, units(x), units(y)) #' ret #' } units/R/options.R0000644000176200001440000001172213420665743013450 0ustar liggesusers.units_options <- new.env(FALSE, parent = globalenv()) .default_options <- list( sep = c("~", "~"), group = c("[", "]"), negative_power = FALSE, parse = TRUE, set_units_mode = "symbols", auto_convert_names_to_symbols = TRUE, simplify = NA, allow_mixed = FALSE, unitless_symbol = "1", define_bel = TRUE ) .setopt <- function(option) { name <- paste0(".units.", substitute(option)) last <- mget(name, envir = .units_options, ifnotfound = NA)[[1]] assign(name, option, envir = .units_options) last } #' set one or more units global options #' #' set units global options, mostly related how units are printed and plotted #' @param ... named options (character) for which the value is queried #' @param sep character length two; default \code{c("~", "~")}; space separator between variable and units, and space separator between two different units #' @param group character length two; start and end group, may be two empty strings, a parenthesis pair, or square brackets; default: square brackets. #' @param negative_power logical, default \code{FALSE}; should denominators have negative power, or follow a division symbol? #' @param parse logical, default \code{TRUE}; should the units be made into an expression (so we get subscripts)? Setting to \code{FALSE} may be useful if \link{parse} fails, e.g. if the unit contains symbols that assume a particular encoding #' @param set_units_mode character; either \code{"symbols"} or \code{"standard"}; see \link{set_units}; default is \code{"symbols"} #' @param auto_convert_names_to_symbols logical, default \code{TRUE}: should names, such as \code{degree_C} be converted to their usual symbol? #' @param simplify logical, default \code{NA}; simplify units in expressions? #' @param allow_mixed logical; if \code{TRUE}, combining mixed units creates a \code{mixed_units} object, if \code{FALSE} it generates an error #' @param unitless_symbol character; set the symbol to use for unitless (1) units #' @param define_bel logical; if \code{TRUE}, define the unit \code{B} (i.e., the \emph{bel}, widely used with the \emph{deci-} prefix as \code{dB}, \emph{decibel}) as an alias of \code{lg(re 1)}. \code{TRUE} by default, unless \code{B} is already defined in the existing XML database. #' @details This sets or gets units options. Set them by using named arguments, get them by passing the option name. #' #' The default \code{NA} value for \code{simplify} means units are not simplified in \link{set_units} or \link{as_units}, but are simplified in arithmetical expressions. #' @return in case options are set, invisibly a named list with the option values that are being set; if an option is queried, the current option value. #' @examples #' old = units_options(sep = c("~~~", "~"), group = c("", "")) # more space, parenthesis #' old #' ## set back to defaults: #' units_options(sep = c("~", "~"), group = c("[", "]"), negative_power = FALSE, parse = TRUE) #' units_options("group") #' @export units_options = function(..., sep, group, negative_power, parse, set_units_mode, auto_convert_names_to_symbols, simplify, allow_mixed, unitless_symbol, define_bel) { # op = as.list(units:::.units_options) ret = list() if (!missing(sep)) { stopifnot(is.character(sep) && length(sep) == 2) ret$sep = .setopt(sep) } if (!missing(group)) { stopifnot(is.character(group) && length(group) == 2 && all(nchar(group) <= 1)) ret$group = .setopt(group) } if (!missing(negative_power)) { stopifnot(is.logical(negative_power)) ret$negative_power = .setopt(negative_power) } if (!missing(parse)) { stopifnot(is.logical(parse)) ret$parse = .setopt(parse) } if (!missing(set_units_mode)) { stopifnot(is.character(set_units_mode) && length(set_units_mode) == 1) ret$set_units_mode = .setopt(set_units_mode) } if (!missing(auto_convert_names_to_symbols)) { stopifnot(is.logical(auto_convert_names_to_symbols)) ret$auto_convert_names_to_symbols = .setopt(auto_convert_names_to_symbols) } if (!missing(simplify)) { stopifnot(is.logical(simplify)) ret$simplify = .setopt(simplify) } if (!missing(allow_mixed)) { stopifnot(is.logical(allow_mixed)) ret$allow_mixed = .setopt(allow_mixed) } if (!missing(unitless_symbol)) { stopifnot(is.character(unitless_symbol), length(unitless_symbol) == 1) ret$unitless_symbol = .setopt(unitless_symbol) } if (!missing(define_bel)) { stopifnot(is.logical(define_bel)) ret$define_bel = .setopt(define_bel) if (!identical(ret$define_bel, define_bel)) { if (!is.na(ret$define_bel)) try(remove_symbolic_unit("B"), silent = TRUE) if (define_bel) install_conversion_constant("lg(re 1)", "B", 1) } } dots = list(...) if (length(dots)) { if (length(ret) > 0) stop("either set, or get units_option, but don't try to do both in one function call") if (is.list(dots[[1]])) do.call(units_options, dots[[1]]) else get(paste0(".units.", dots[[1]]), envir = .units_options) } else invisible(ret) } .units.simplify = function() { get(".units.simplify", envir = .units_options) } units/R/valid_udunits.R0000644000176200001440000002274013527327534014632 0ustar liggesusers .message_where_udunits_db <- function() { udunits2_dir <- .get_ud_xml_dir() message("udunits system database read from " , udunits2_dir) } .get_ud_xml_dir <- function(warn = FALSE) { paths = c( Sys.getenv("UDUNITS2_XML_PATH"), "/usr/local/share/udunits/udunits2.xml", "/usr/share/xml/udunits/udunits2.xml", "/usr/share/udunits/udunits2.xml") fallback = system.file("share/udunits/udunits2.xml", package="units") w = which(file.exists(paths)) if (length(w) > 1 && warn) warning(paste("multiple udunits databases present:", paste(paths[w], collapse = " "))) p = if (length(w) == 0) fallback else paths[w[1]] if (!file.exists(p)) stop( "Failed to identify udunits system database: units will not work properly.\nPlease set the UDUNITS2_XML_PATH environment variable before attempting to read the units database") else dirname(p) } .read_ud_db_symbols <- function(dir, filename) { if (! requireNamespace("xml2", quietly = TRUE)) stop("package xml2 required to create ud_units database") database <- xml2::read_xml(file.path(dir, filename)) symbols <- xml2::xml_find_all(database, ".//symbol") unlist(Map(function(node) as.character(xml2::xml_contents(node)), symbols)) } ## EP: it seems this is used nowhere #.read_ud_db_scales <- function(dir, filename) { # if (! requireNamespace("xml2", quietly = TRUE)) # stop("package xml2 required to create ud_units database") # database <- xml2::read_xml(file.path(dir, filename)) # symbols <- xml2::xml_find_all(database, ".//value") # symbols # unlist(Map(function(node) as.numeric(as.character(xml2::xml_contents(node))), symbols)) #} .get_ud_symbols <- function() { udunits2_dir <- .get_ud_xml_dir() symbols <- c(.read_ud_db_symbols(udunits2_dir, "udunits2-base.xml"), .read_ud_db_symbols(udunits2_dir, "udunits2-derived.xml"), .read_ud_db_symbols(udunits2_dir, "udunits2-accepted.xml"), .read_ud_db_symbols(udunits2_dir, "udunits2-common.xml")) symbols } .get_ud_prefixes <- function() { udunits2_dir <- .get_ud_xml_dir() .read_ud_db_symbols(udunits2_dir, "udunits2-prefixes.xml") } .construct_ud_units <- function(){ ud_prefixes <- .get_ud_prefixes() ud_symbols <- .get_ud_symbols() expand_with_prefixes <- function(symbol) paste(ud_prefixes, symbol, sep = "") symbols <- unique(c(ud_symbols, unlist(Map(expand_with_prefixes, ud_symbols), use.names = FALSE))) ud_units <- lapply(symbols, as_units, force_single_symbol = TRUE, check_is_valid = FALSE) names(ud_units) <- symbols class(ud_units) <- "units database" ud_units } # but this gives Y' Y" etc which are NOT recognized by as_units() # Use this to generate the data -- to avoid Travis problems the result # is stored as package data #ud_units <- units:::.construct_ud_units() #usethis::use_data(ud_units, internal=TRUE, overwrite=TRUE) #' @export `with.units database` <- function(data, expr, ...) { if (all(!unlist(l10n_info()))) # ISO8859-15 data <- subset(data, Encoding(names(data)) != "UTF-8") eval(substitute(expr), data, enclos = parent.frame()) } #' @export `print.units database` <- function(x, ...) { cat("Units database, containing", length(x), "units:\n") cat(" ", paste(names(x)[1:9], collapse=", "), "...\n") } #' List containing pre-defined units from the udunits2 package. #' #' Lazy loaded when used #' @export ud_units <- NULL `%|%` <- function(x, y) ifelse(is.na(x), y, x) `%empty%` <- function(x, y) if(length(x)==0) y else x pcc <- function(...) paste0(..., collapse = ", ") .read_ud_db <- function(dir, filename) { if (! requireNamespace("xml2", quietly = TRUE)) stop("package xml2 required to create ud_units database") database <- xml2::read_xml(file.path(dir, filename)) # xml2::as_list(database) database } .ud_db_xml_list_as_dataframe <- function(db) { xml_nodes <- xml2::xml_children(db) l <- lapply(seq_len(xml2::xml_length(db)), function(i) { unit <- xml_nodes[[i]] symbols <- xml2::xml_find_all(unit, ".//symbol") symbols <- xml2::xml_text(symbols) %empty% "" symbol <- symbols[ 1] symbol_aliases <- pcc(symbols[-1]) unit_names <- xml2::xml_find_all(unit, ".//name") all_names <- unlist(lapply(unit_names, function(.x) xml2::xml_text(xml2::xml_children(.x)))) singular <- xml2::xml_find_all(unit_names, ".//singular") singular <- xml2::xml_text(singular) plural <- xml2::xml_find_all(unit_names, ".//plural") plural <- xml2::xml_text(plural) name_singular <- singular[ 1] %|% "" name_singular_aliases <- pcc(singular[-1]) %|% "" name_plural <- plural[ 1] %|% "" name_plural_aliases <- pcc(plural[-1]) %|% "" def <- xml2::xml_find_all(unit, ".//def") def <- xml2::xml_text(def) %empty% "" definition <- xml2::xml_find_all(unit, ".//definition") definition <- xml2::xml_text(definition) %empty% "" comment <- xml2::xml_find_all(unit, ".//comment") comment <- xml2::xml_text(comment) %empty% "" dimensionless <- xml2::xml_find_all(unit, ".//dimensionless") dimensionless <- as.logical(length(dimensionless)) # all node names that might be in a unit node # db %>% xml_children() %>% map(~xml_children(.x) %>% xml_name()) %>% # unique() %>% unlist() %>% unique() # [1] "base" "name" "symbol" # [4] "aliases" "definition" "def" # [7] "comment" "dimensionless" # rest_xml <- unit %>% xml_children() # rest <- map(rest_xml, xml_text) # names(rest) <- rest_xml %>% xml_name() # rest <- list(rest) data.frame(symbol, symbol_aliases, name_singular, name_singular_aliases, name_plural, name_plural_aliases, def, definition, comment, dimensionless, #, rest stringsAsFactors = FALSE) }) do.call(rbind.data.frame, c(l, stringsAsFactors = FALSE, make.row.names = FALSE)) } .read_ud_db_as_dataframe <- function(file_name) { udunits2_dir <- .get_ud_xml_dir() xml <- .read_ud_db(udunits2_dir, file_name) df <- .ud_db_xml_list_as_dataframe(xml) df$source_xml <- gsub("udunits2-|\\.xml", "", file_name) df } .get_ud_db_all <- function() { base <- .read_ud_db_as_dataframe("udunits2-base.xml") # 7 derived <- .read_ud_db_as_dataframe("udunits2-derived.xml") # 23 accepted <- .read_ud_db_as_dataframe("udunits2-accepted.xml") # 24 common <- .read_ud_db_as_dataframe("udunits2-common.xml") # 221 rbind.data.frame( base, derived, accepted, common, stringsAsFactors = FALSE, make.row.names = FALSE ) } .get_ud_prefixes_xml <- function() { udunits2_dir <- .get_ud_xml_dir() .read_ud_db(udunits2_dir, "udunits2-prefixes.xml") } #' Get information about valid units #' #' The returned dataframe is constructed at runtime by reading the xml database #' that powers unit conversion in [package:udunits2]. Inspect this dataframe to #' determine what inputs are accepted by \code{as_units} (and the other #' functions it powers: \code{as_units} , \code{set_units} , \code{units<-}). #' #' Any entry listed under \code{symbol} , \code{symbol_aliases} , \code{ #' name_singular} , \code{name_singular_aliases} , \code{name_plural} , or #' \code{name_plural_aliases} is valid. Additionally, any entry under #' \code{symbol} or \code{symbol_aliases} may can also contain a valid prefix, #' as specified by \code{valid_udunits_prefixes()} . #' #' Note, this is primarily intended for interactive use, the exact format of the #' returned dataframe may change in the future. #' #' @param quiet logical, defaults \code{TRUE} to give a message about the location of #' the udunits database being read. #' #' @return a data frame with columns \code{symbol} , \code{symbol_aliases} , #' \code{name_singular} , \code{name_singular_aliases} , \code{name_plural} , #' or \code{name_plural_aliases} , \code{def} , \code{definition} , #' \code{comment} , \code{dimensionless} and \code{source_xml} #' #' @export #' #' @name valid_udunits #' @examples #' if (requireNamespace("xml2", quietly = TRUE)) { #' valid_udunits() #' valid_udunits_prefixes() #' if(interactive()) #' View(valid_udunits()) #' } valid_udunits <- function(quiet = FALSE) { if(!requireNamespace("xml2", quietly = TRUE)) stop("Package 'xml2' is required.") if(!nzchar(.get_ud_xml_dir())) return(invisible()) if(!quiet) .message_where_udunits_db() df <- .get_ud_db_all() class(df) <- c( "tbl_df", "tbl", "data.frame") df } #' @name valid_udunits #' @export valid_udunits_prefixes <- function(quiet = FALSE) { if(!nzchar(.get_ud_xml_dir())) return(invisible()) if(!quiet) .message_where_udunits_db() pr <- .get_ud_prefixes_xml() # all prefix valid names # pr %>% xml_children() %>% map(~xml_children(.x) %>% xml_name()) %>% # unlist() %>% unique() # "value" "name" "symbol" l <- lapply( xml2::xml_children(pr), function(prefix) { symbols <- xml2::xml_find_all(prefix, ".//symbol") symbols <- xml2::xml_text(symbols) symbol <- symbols[1] symbol_aliases <- pcc(symbols[-1]) name <- xml2::xml_find_all(prefix, ".//name") name <- xml2::xml_text(name) value <- xml2::xml_find_all(prefix, ".//value") value <- xml2::xml_double(value) data.frame(symbol, symbol_aliases, name, value) }) df <- do.call(rbind.data.frame, c(l, stringsAsFactors = FALSE, make.row.names = FALSE)) class(df) <- c( "tbl_df", "tbl", "data.frame") df } units/R/make_units.R0000644000176200001440000004030613472516125014110 0ustar liggesusers# helper function: .as.units = function(x, value, dim) { if (missing(dim)) structure(x, units = value, class = "units") else structure(x, units = value, dim = dim, class = "units") } #' Unit creation #' #' A number of functions are provided for creating unit objects. #' \itemize{ #' \item \code{as_units}, a generic with methods for a #' character string and for quoted language. Note, direct usage of this function #' by users is typically not necessary, as coercion via \code{as_units} is #' automatically done with \code{`units<-`} and \code{set_units()}. #' #' \item \code{make_units()}, constructs units from bare expressions. #' \code{make_units(m/s)} is equivalent to \code{as_units(quote(m/s))} #' #' \item \code{set_units()}, a pipe_friendly version of \code{`units<-`}. By #' default it operates with bare expressions like \code{make_unit}, but this #' behavior can be disabled by a specifying \code{mode = "standard"} or setting #' \code{units_options(set_units_mode = "standard")}. #' } #' #' @export #' @rdname as_units #' #' @param bare_expression a bare R expression describing units. Must be valid R #' syntax (reserved R syntax words like \code{in} must be backticked) #' #' @noMd #' @examples #' # The easiest way to assign units to a numeric vector is like this: #' x <- y <- 1:4 #' units(x) <- "m/s" # meters / second #' #' # Alternatively, the easiest pipe-friendly way to set units: #' if(requireNamespace("magrittr", quietly = TRUE)) { #' library(magrittr) #' y %>% set_units(m/s) #' } #' #' # these are different ways of creating the same unit: #' # meters per second squared, i.e, acceleration #' x1 <- make_units(m/s^2) #' x2 <- as_units(quote(m/s^2)) #' x2 <- as_units("m/s^2") #' x3 <- as_units("m s-2") # in product power form, i.e., implicit exponents = T #' x4 <- set_units(1, m/s^2) # by default, mode = "symbols" #' x5 <- set_units(1, "m/s^2", mode = "standard") #' x6 <- set_units(1, x1, mode = "standard") #' x7 <- set_units(1, units(x1), mode = "standard") #' x8 <- as_units("m") / as_units("s")^2 #' #' all_identical <- function(...) { #' l <- list(...) #' for(i in seq_along(l)[-1]) #' if(!identical(l[[1]], l[[i]])) #' return(FALSE) #' TRUE #' } #' all_identical(x1, x2, x3, x4, x5, x6, x7, x8) #' #' # Note, direct usage of these unit creation functions is typically not #' # necessary, since coercion is automatically done via as_units(). Again, #' # these are all equivalent ways to generate the same result. #' #' x1 <- x2 <- x3 <- x4 <- x5 <- x6 <- x7 <- x8 <- 1:4 #' units(x1) <- "m/s^2" #' units(x2) <- "m s-2" #' units(x3) <- quote(m/s^2) #' units(x4) <- make_units(m/s^2) #' units(x5) <- as_units(quote(m/s^2)) #' x6 <- set_units(x6, m/s^2) #' x7 <- set_units(x7, "m/s^2", mode = "standard") #' x8 <- set_units(x8, units(x1), mode = "standard") #' #' all_identical(x1, x2, x3, x4, x5, x6, x7, x8) #' #' #' # Both unit names or symbols can be used. By default, unit names are #' # automatically converted to unit symbols. #' make_units(degree_C) #' make_units(kilogram) #' make_units(ohm) #' # Note, if the printing of non-ascii characters is garbled, then you may #' # need to specify the encoding on your system manually like this: #' # ud_set_encoding("latin1") #' # not all unit names get converted to symbols under different encodings #' #' ## Arithmetic operations and units #' # conversion between unit objects that were defined as symbols and names will #' # work correctly, although unit simplification in printing may not always occur. #' x <- 500 * make_units(micrograms/liter) #' y <- set_units(200, ug/l) #' x + y #' x * y # numeric result is correct, but units not simplified completely #' #' # note, plural form of unit name accepted too ('liters' vs 'liter'), and #' # denominator simplification can be performed correctly #' x * set_units(5, liters) #' #' # unit conversion works too #' set_units(x, grams/gallon) #' #' ## Creating custom, user defined units #' # For example, a microbiologist might work with counts of bacterial cells #' # make_units(cells/ml) # by default, throws an ERROR #' # First define the unit, then the newly defined unit is accepted. #' install_symbolic_unit("cells") #' make_units(cells/ml) #' #' # Note, install_symbolic_unit() does not add any support for unit #' # conversion, or arithmetic operations that require unit conversion. See #' # ?install_conversion_constant for defining relationships between user #' # defined units. #' #' ## set_units() #' # set_units is a pipe friendly version of `units<-`. #' if(requireNamespace("magrittr", quietly = TRUE)) { #' library(magrittr) #' 1:5 %>% set_units(N/m^2) #' # first sets to m, then converts to km #' 1:5 %>% set_units(m) %>% set_units(km) #' } #' #' # set_units has two modes of operation. By default, it operates with #' # bare symbols to define the units. #' set_units(1:5, m/s) #' #' # use `mode = "standard"` to use the value of supplied argument, rather than #' # the bare symbols of the expression. In this mode, set_units() can be #' # thought of as a simple alias for `units<-` that is pipe friendly. #' set_units(1:5, "m/s", mode = "standard") #' set_units(1:5, make_units(m/s), mode = "standard") #' #' # the mode of set_units() can be controlled via a global option #' # units_options(set_units_mode = "standard") #' #' # To remove units use #' units(x) <- NULL #' # or #' set_units(x, NULL) #' # or #' drop_units(y) make_units <- function(bare_expression, check_is_valid = TRUE) { as_units.call(substitute(bare_expression), check_is_valid = check_is_valid) } # ----- as_units.character helpers ------ backtick <- function(x) { # backtick all character runs uninterupted by one of ^()*^/`- or a space # don't double up backticks x <- gsub("`?([^() \\*^/`-]+)`?", "`\\1`", x) gsub("`([0-9]*\\.?[0-9]+)`", "\\1", x) # unbacktick bare numbers } are_exponents_implicit <- function(s) { s <- trimws(s) has <- function(chr, regex = FALSE) grepl(chr, s, fixed = !regex, perl = regex) !has("^") && !has("*") && !has("/") && has("\\s|\\D.*\\d$", regex = TRUE) } is_udunits_time <- function(s) { ud_is_parseable(s) && ud_are_convertible(s, "seconds since 1970-01-01") } #' @rdname as_units #' @export #' @noMd #' #' @param force_single_symbol Whether to perform no string parsing and force #' treatment of the string as a single symbol. #' #' @param implicit_exponents If the unit string is in product power form (e.g. #' \code{"km m-2 s-1"}). Defaults to \code{NULL}, in which case a guess is made #' based on the supplied string. Set to \code{TRUE} or \code{FALSE} if the guess is #' incorrect. #' #' @section Character strings: #' #' Generally speaking, there are 3 types of unit strings are accepted in #' \code{as_units} (and by extension, \code{`units<-`}). #' #' The first, and likely most common, is a "standard" format unit #' specification where the relationship between unit symbols or names is #' specified explicitly with arithmetic symbols for division \code{/}, #' multiplication \code{*} and power exponents \code{^}, or other mathematical #' functions like \code{log()}. In this case, the string is parsed as an R #' expression via \code{parse(text = )} after backticking all unit symbols and #' names, and then passed on to \code{as_units.call()}. A heuristic is used to #' perform backticking, such that any continuous set of characters #' uninterrupted by one of \code{()\\*^-} are backticked (unless the character #' sequence consists solely of numbers \code{0-9}), with some care to not #' double up on pre-existing backticks. This heuristic appears to be quite #' robust, and works for units would otherwise not be valid R syntax. For #' example, percent (\code{"\%"}), feet (\code{"'"}), inches (\code{"in"}), #' and Tesla (\code{"T"}) are all backticked and parsed correctly. #' #' Nevertheless, for certain complex unit expressions, this backticking heuristic #' may give incorrect results. If the string supplied fails to parse as an R #' expression, then the string is treated as a single symbolic unit and #' \code{symbolic_unit(chr)} is used as a fallback with a warning. In that #' case, automatic unit simplification may not work properly when performing #' operations on unit objects, but unit conversion and other Math operations #' should still give correct results so long as the unit string supplied #' returns \code{TRUE} for \code{ud_is_parsable()}. #' #' The second type of unit string accepted is one with implicit exponents. In #' this format, \code{/}, \code{*}, and \code{^}, may not be present in the #' string, and unit symbol or names must be separated by a space. Each unit #' symbol may optionally be followed by a single number, specifying the power. #' For example \code{"m2 s-2"} is equivalent to \code{"(m^2)*(s^-2)"}. #' #' The third type of unit string format accepted is the special case of #' udunits time duration with a reference origin, for example \code{"hours #' since 1970-01-01 00:00:00"}. Note, that the handling of time and calendar #' operations via the udunits library is subtly different from the way R #' handles date and time operations. This functionality is mostly exported for #' users that work with udunits time data, e.g., with NetCDF files. Users are #' otherwise encouraged to use \code{R}'s date and time functionality provided #' by \code{Date} and \code{POSIXt} classes. as_units.character <- function(x, check_is_valid = TRUE, implicit_exponents = NULL, force_single_symbol = FALSE, ...) { stopifnot(is.character(x), length(x) == 1) if(force_single_symbol || is_udunits_time(x)) return(symbolic_unit(x, check_is_valid = check_is_valid)) if(is.null(implicit_exponents)) implicit_exponents <- are_exponents_implicit(x) if(implicit_exponents) x <- convert_implicit_to_explicit_exponents(x) x <- backtick(x) o <- try(expr <- parse(text = x)[[1]], silent = TRUE) if(inherits(o, "try-error")) { warning("Could not parse expression: ", sQuote(x), # nocov ". Returning as a single symbolic unit()", call. = FALSE) # nocov return(symbolic_unit(x, check_is_valid = check_is_valid)) # nocov } as_units.call(expr, check_is_valid = check_is_valid) } convert_implicit_to_explicit_exponents <- function(x) { if (length(grep(c("[*/]"), x)) > 0) stop("If 'implicit_exponents = TRUE', strings cannot contain `*' or `/'") x <- gsub("\\b([^\\d-]+)([-]?\\d+)\\b", "\\1^(\\2)", x, perl =TRUE) x <- gsub("\\s+", " * ", trimws(x), perl = TRUE) x } # ----- as_units.call helpers ------ # from package:yasp, paste collapse with serial (oxford) comma pc_and <- function(..., sep = "") { x <- paste(..., sep = sep, collapse = NULL) lx <- length(x) if(lx == 0L) "" else if (lx == 1L) x else if (lx == 2L) paste0(x, collapse = " and ") else paste0( paste0(x[-lx], collapse = ", "), ", and ", x[lx]) } #`%not_in%` <- function(x, table) match(x, table, nomatch = 0L) == 0L .msg_units_not_recognized <- function(unrecognized_symbols, full_expr) { if (is.language(full_expr)) full_expr <- deparse(full_expr) is_are <- if (length(unrecognized_symbols) > 1L) "are" else "is" paste0("In ", sQuote(full_expr), ", ", pc_and(sQuote(unrecognized_symbols)), " ", is_are, " not recognized by udunits.\n\n", "See a table of valid unit symbols and names with valid_udunits().\n", "Custom user-defined units can be added with install_symbolic_unit().\n\n", "See a table of valid unit prefixes with valid_udunits_prefixes().\n", "Prefixes will automatically work with any user-defined unit.") } units_eval_env <- new.env(parent = baseenv()) units_eval_env$ln <- function(x) base::log(x) units_eval_env$lg <- function(x) base::log(x, base = 10) units_eval_env$lb <- function(x) base::log(x, base = 2) #' @export #' @rdname as_units #' #' @param check_is_valid throw an error if all the unit symbols are not either #' recognized by udunits2 via \code{ud_is_parseable()}, or a custom #' user defined via \code{install_symbolic_unit()}. If \code{FALSE}, no check #' for validity is performed. #' #' @note By default, unit names are automatically substituted with unit names #' (e.g., kilogram --> kg). To turn off this behavior, set #' \code{units_options(auto_convert_names_to_symbols = FALSE)} #' #' @section Expressions: #' #' In \code{as_units()}, each of the symbols in the unit expression is treated #' individually, such that each symbol must be recognized by the udunits #' database (checked by \code{ud_is_parseable()}, \emph{or} be a custom, #' user-defined unit symbol that was defined either by #' \code{install_symbolic_unit()} or \code{install_conversion_constant()}. To #' see which symbols and names are currently recognized by the udunits #' database, see \code{udunits_symbols()}. #' #' @return A new unit object that can be used in arithmetic, unit conversion or #' unit assignment. #' #' @seealso \code{\link{valid_udunits}} as_units.call <- function(x, check_is_valid = TRUE, ...) { if(missing(x) || identical(x, quote(expr =)) || identical(x, 1) || identical(x, 1L)) return(.as.units(1, unitless)) if (is.vector(x) && any(is.na(x))) stop("a missing value for units is not allowed") stopifnot(is.language(x)) vars <- all.vars(x) if(!length(vars)) stop(call. = FALSE, "No symbols found. Please supply bare expressions with this approach. See ?as_units for usage examples.") if (check_is_valid) { valid <- vapply(vars, ud_is_parseable, logical(1L)) if (!all(valid)) stop(.msg_units_not_recognized(vars[!valid], x), call. = FALSE) } names(vars) <- vars tmp_env <- lapply(vars, symbolic_unit, check_is_valid = FALSE) if (dont_simplify_here <- is.na(.units.simplify())) { units_options(simplify = FALSE) on.exit(units_options(simplify = NA)) } unit <- tryCatch( eval(x, tmp_env, units_eval_env), error = function(e) stop( paste0( conditionMessage(e), "\n", "Did you try to supply a value in a context where a bare expression was expected?" ), call. = FALSE )) # if(as.numeric(unit) %not_in% c(1, 0)) # 0 if log() used. # stop(call. = FALSE, #"In ", sQuote(deparse(x)), " the numeric multiplier ", sQuote(as.numeric(unit)), " is invalid. #Use `install_conversion_constant()` to define a new unit that is a multiple of another unit.") .as.units(as.numeric(unit), units(unit)) } #' @export as_units.expression <- as_units.call #' @export as_units.name <- as_units.call symbolic_unit <- function(chr, check_is_valid = TRUE) { stopifnot(is.character(chr), length(chr) == 1) if (check_is_valid && !ud_is_parseable(chr)) { msg <- paste(sQuote(chr), "is not a unit recognized by udunits or a user-defined unit") stop(msg, call. = FALSE) } auto_convert <- units_options("auto_convert_names_to_symbols") if (auto_convert && ud_is_parseable(chr)) { sym <- ud_get_symbol(chr) if (nzchar(sym)) chr <- sym } .as.units(1, .symbolic_units(chr)) } #' Drop Units #' #' Drop units attribute and class. #' #' @param x an object with units metadata. #' #' @return the numeric without any units attributes, while preserving other #' attributes like dimensions or other classes. #' #' @details Equivalent to \code{units(x) <- NULL}, or the pipe-friendly version #' \code{set_units(x, NULL)}, but \code{drop_units} will fail if the object has #' no units metadata. Use the alternatives if you want this operation to succeed #' regardless of the object type. #' #' A \code{data.frame} method is also provided, which checks every column and #' drops units if any. #' #' @export #' @examples #' x <- 1 #' y <- set_units(x, m/s) #' #' # this succeeds #' drop_units(y) #' set_units(y, NULL) #' set_units(x, NULL) #' #' \dontrun{ #' # this fails #' drop_units(x) #' } #' #' df <- data.frame(x=x, y=y) #' df #' drop_units(df) #' drop_units <- function(x) UseMethod("drop_units") #' @name drop_units #' @export drop_units.units <- function(x) { class(x) <- setdiff(class(x), "units") attr(x, "units") <- NULL x } #' @name drop_units #' @export drop_units.data.frame <- function(x) { for (i in seq_along(x)) { if (inherits(x[[i]], "units")) x[[i]] <- drop_units(x[[i]]) } x } units/R/RcppExports.R0000644000176200001440000000475513547030261014245 0ustar liggesusers# Generated by using Rcpp::compileAttributes() -> do not edit by hand # Generator token: 10BE3573-1514-4C36-9D1C-5A225CD40393 udunits_init <- function(path) { invisible(.Call('_units_udunits_init', PACKAGE = 'units', path)) } udunits_exit <- function() { invisible(.Call('_units_udunits_exit', PACKAGE = 'units')) } R_ut_parse <- function(name) { .Call('_units_R_ut_parse', PACKAGE = 'units', name) } R_ut_get_dimensionless_unit_one <- function(name) { .Call('_units_R_ut_get_dimensionless_unit_one', PACKAGE = 'units', name) } R_ut_are_convertible <- function(a, b) { .Call('_units_R_ut_are_convertible', PACKAGE = 'units', a, b) } R_convert_doubles <- function(from, to, val) { .Call('_units_R_convert_doubles', PACKAGE = 'units', from, to, val) } R_ut_new_dimensionless_unit <- function(name) { invisible(.Call('_units_R_ut_new_dimensionless_unit', PACKAGE = 'units', name)) } R_ut_new_base_unit <- function(name) { invisible(.Call('_units_R_ut_new_base_unit', PACKAGE = 'units', name)) } R_ut_remove_unit <- function(name) { invisible(.Call('_units_R_ut_remove_unit', PACKAGE = 'units', name)) } R_ut_scale <- function(nw, old, d) { invisible(.Call('_units_R_ut_scale', PACKAGE = 'units', nw, old, d)) } R_ut_offset <- function(nw, old, d) { invisible(.Call('_units_R_ut_offset', PACKAGE = 'units', nw, old, d)) } R_ut_divide <- function(numer, denom) { .Call('_units_R_ut_divide', PACKAGE = 'units', numer, denom) } R_ut_multiply <- function(a, b) { .Call('_units_R_ut_multiply', PACKAGE = 'units', a, b) } R_ut_invert <- function(a) { .Call('_units_R_ut_invert', PACKAGE = 'units', a) } R_ut_raise <- function(a, i) { .Call('_units_R_ut_raise', PACKAGE = 'units', a, i) } R_ut_root <- function(a, i) { .Call('_units_R_ut_root', PACKAGE = 'units', a, i) } R_ut_log <- function(a, base) { .Call('_units_R_ut_log', PACKAGE = 'units', a, base) } R_ut_format <- function(p, names = FALSE, definition = FALSE, ascii = FALSE) { .Call('_units_R_ut_format', PACKAGE = 'units', p, names, definition, ascii) } R_ut_set_encoding <- function(enc_str) { invisible(.Call('_units_R_ut_set_encoding', PACKAGE = 'units', enc_str)) } R_ut_get_symbol <- function(ustr) { .Call('_units_R_ut_get_symbol', PACKAGE = 'units', ustr) } R_ut_get_name <- function(ustr) { .Call('_units_R_ut_get_name', PACKAGE = 'units', ustr) } R_ut_map_name_to_unit <- function(name, inunit) { .Call('_units_R_ut_map_name_to_unit', PACKAGE = 'units', name, inunit) } units/R/init.R0000644000176200001440000000133613463271135012713 0ustar liggesusers#' @import utils #' @import stats #' @import graphics #' @importFrom Rcpp evalCpp #' @useDynLib units NULL .onLoad = function(libname, pkgname) { udunits_init(file.path(.get_ud_xml_dir(), "udunits2.xml")) if (ud_is_parseable("B")) .default_options$define_bel <- FALSE do.call(units_options, .default_options) native <- if (l10n_info()[["UTF-8"]]) "utf8" else if (l10n_info()[["Latin-1"]]) "latin1" else "ascii" ud_set_encoding(native) } .onAttach <- function(libname, pkgname) { msg <- paste("udunits system database from", .get_ud_xml_dir(TRUE)) packageStartupMessage(msg) } .onUnload = function(libname, pkgname) { # force run weak finalizers before freeing sys invisible(gc()) udunits_exit() } units/R/misc.R0000644000176200001440000001127413401522640012675 0ustar liggesusers#' @export c.units <- function(..., recursive = FALSE, allow_mixed = units_options("allow_mixed")) { args <- list(...) args[sapply(args, is.null)] <- NULL # remove NULLs u <- units(args[[1]]) if (length(args) == 1) .as.units(NextMethod(), u) else if (.units_are_convertible(args[-1], u)) { args <- set_units.mixed_units(args, as.character(u)) .as.units(do.call(c, lapply(args, drop_units)), u) } else if (allow_mixed) do.call(c, lapply(args, mixed_units)) else stop("units are not convertible, and cannot be mixed; try setting units_options(allow_mixed = TRUE)?") } .units_are_convertible = function(x, u) { for (i in seq_along(x)) if (! ud_are_convertible(units(x[[i]]), u)) return(FALSE) TRUE } #' @export diff.units = function(x, ...) { u = units(x) # units(x) = u will not work here, as units(x) is NULL! .as.units(NextMethod(), u) } #' @export rep.units = function(x, ...) { u = units(x) .as.units(NextMethod(), u) } #' deparse unit to string in product power form (e.g. km m-2 s-1) #' #' deparse unit to string in product power form (e.g. km m-2 s-1) #' @param x object of class units #' @return length one character vector #' @examples #' u = as_units("kg m-2 s-1", implicit_exponents = TRUE) #' u #' deparse_unit(u) #' @export deparse_unit = function(x) { stopifnot(inherits(x, "units")) u = units(x) tn = table(u$numerator) nm1 = names(tn) vals1 = as.character(tn) vals1[vals1 == "1"] = "" td = - table(u$denominator) nm2 = names(td) vals2 = as.character(td) paste(c(paste0(nm1, vals1), paste0(nm2, vals2)), collapse=" ") } # This should perhaps be an option in format.symbolic_units #' @export #' @name deparse_unit #' @details \code{as_cf} is deprecated; use \code{deparse_unit}. as_cf = function(x) { .Deprecated("deparse_unit") # nocov deparse_unit(x) # nocov } #' @method all.equal units #' @export all.equal.units = function(target, current, ...) { current = set_units(current, units(target), mode = "standard") all.equal(unclass(target), unclass(current), ...) } #' seq method for units objects #' @param from see \link[base]{seq} #' @param to see \link[base]{seq} #' @param by see \link[base]{seq} #' @param length.out see \link[base]{seq} #' @param along.with see \link[base]{seq} #' @param ... see \link[base]{seq} #' @details arguments with units are converted to have units of the first argument (which is either \code{from} or \code{to}) #' @export #' @examples #' seq(to = set_units(10, m), by = set_units(1, m), length.out = 5) #' seq(set_units(10, m), by = set_units(1, m), length.out = 5) #' seq(set_units(10, m), set_units(19, m)) #' seq(set_units(10, m), set_units(.1, km), set_units(10000, mm)) seq.units = function(from, to, by = ((to - from)/(length.out - 1)), length.out = NULL, along.with = NULL, ...) { mf = missing(from) mt = missing(to) uuu = if (mf) units(to) else units(from) if (! mf) from = as.numeric(from) if (! mt) to = as.numeric(set_units(to, uuu, mode = "standard")) if (! missing(by)) by = as.numeric(set_units(by, uuu, mode = "standard")) set_units(NextMethod(), uuu, mode = "standard") } #' type_sum function for units #' @name tibble #' @param x see \link[pillar]{type_sum} #' @param ... see \link[pillar]{type_sum} #' @rawNamespace if(getRversion() >= "3.6.0") { #' S3method(pillar::type_sum, units) #' S3method(pillar::type_sum, mixed_units) #' S3method(pillar::pillar_shaft, units) #' S3method(pillar::pillar_shaft, mixed_units) #' S3method(pillar::format_type_sum, type_sum_units) #' } else { #' export(type_sum.units) #' export(type_sum.mixed_units) #' export(pillar_shaft.units) #' export(pillar_shaft.mixed_units) #' export(format_type_sum.type_sum_units) #' } type_sum.units <- function(x, ...) { gr = units_options("group") # see https://github.com/r-lib/pillar/issues/73 : currently the [ and ] mess up things. structure(paste0(gr[1], as.character(units(x)), gr[2]), class = "type_sum_units") } #' @name tibble #' @param width ignored format_type_sum.type_sum_units <- function(x, width, ...) { if (! requireNamespace("pillar", quietly = TRUE)) stop("package pillar not available: install first?") pillar::style_subtle(x) } #' pillar_shaft function for units #' @name tibble pillar_shaft.units <- function(x, ...) { u_char <- as.character(units(x)) if (! requireNamespace("pillar", quietly = TRUE)) stop("package pillar not available: install first?") #out <- paste(format(unclass(x), ...), pillar::style_subtle(u_char)) out <- format(unclass(x), ...) pillar::new_pillar_shaft_simple(out, align = "right", min_width = 8) } #' @export str.units = function(object, ...) { cat("Object of class units:\n") str(unclass(object), ...) } units/R/math.R0000644000176200001440000000666713401522640012705 0ustar liggesusers# Inside the group generic functions we do have .Generic even if the diagnostics # think we do not. # !diagnostics suppress=.Generic #' Mathematical operations for units objects #' #' @param x object of class units #' @param ... parameters passed on to the Math functions #' #' @details Logarithms receive a special treatment by the underlying \pkg{udunits2} #' library. If a natural logarithm is applied to some \code{unit}, the result is #' \code{ln(re 1 unit)}, which means \emph{natural logarithm referenced to #' \code{1 unit}}. For base 2 and base 10 logarithms, the output \code{lb(...)} #' and \code{lg(...)} respectively instead of \code{ln(...)}. #' #' This is particularly important for some units that are typically expressed in #' a logarithmic scale (i.e., \emph{bels}, or, more commonly, \emph{decibels}), #' such as Watts or Volts. For some of these units, the default \pkg{udunits2} #' database contains aliases: e.g., \code{BW} (bel-Watts) is an alias of #' \code{lg(re 1 W)}; \code{Bm} (bel-milliWatts) is an alias of #' \code{lg(re 0.001 W)}; \code{BV} is an alias of \code{lg(re 1 V)} (bel-Volts), #' and so on and so forth (see the output of \code{valid_udunits()} for further #' reference). #' #' Additionally, the \pkg{units} package defines \code{B}, the \emph{bel}, by #' default (because it is not defined by \pkg{udunits2}) as an alias of #' \code{lg(re 1)}, unless a user-provided XML database already contains a #' definition of \code{B}, or the \code{define_bel} option is set to \code{FALSE} #' (see \code{help(units_options)}). #' #' @export #' #' @examples #' # roundings, cummulative functions #' x <- set_units(sqrt(1:10), m/s) #' signif(x, 2) #' cumsum(x) #' #' # trigonometry #' sin(x) # not meaningful #' x <- set_units(sqrt(1:10), rad) #' sin(x) #' cos(x) #' x <- set_units(seq(0, 1, 0.1), 1) #' asin(x) #' acos(x) #' #' # logarithms #' x <- set_units(sqrt(1:10), W) #' log(x) # base exp(1) #' log(x, base = 3) #' log2(x) #' log10(x) #' set_units(x, dBW) # decibel-watts #' set_units(x, dBm) # decibel-milliwatts Math.units = function(x, ...) { if (.Generic == "sqrt") return(x^0.5) if (.Generic == "sign") return(as.numeric(NextMethod())) OK <- switch(.Generic, "abs" = , "sign" = , "floor" = , "ceiling" = , "log" = , "log1p" =, "trunc" = , "round" = , "signif" = , "cumsum" = , "cummax" = , "cummin" = TRUE, FALSE) rad = units(as_units("rad")) deg = units(as_units("degree")) if (!OK && (units(x) == rad || units(x) == deg)) { OK <- switch(.Generic, sin =, cos =, tan =, sinpi =, cospi =, tanpi = TRUE, FALSE) if (OK) { units(x) <- "rad" # convert deg -> rad x <- set_units(x) # result has unit 1 } } if (!OK && units(x) == unitless) { OK <- switch(.Generic, asin =, acos =, atan = TRUE, FALSE) if (OK) units(x) <- "rad" # unit of the answer (also unitless) } if (!OK) { warning(paste("Operation", .Generic, "not meaningful for units")) x <- drop_units(x) NextMethod() } else { if (.Generic %in% c("log", "log1p")) { base <- if (missing(...)) exp(1) else c(...)[1] uptr <- R_ut_parse(as.character(units(x))) u <- R_ut_format(R_ut_log(uptr, base), ascii=TRUE) .as.units(NextMethod(), units(symbolic_unit(u))) } else .as.units(NextMethod(), units(x)) } } #' @export #' @method log10 units log10.units <- function(x) log(x, 10) #' @export #' @method log2 units log2.units <- function(x) log(x, 2) units/R/conversion.R0000644000176200001440000001625413420464657014150 0ustar liggesusers# Helper functions for testing if we can convert and how using either # user-defined conversion functions or udunits. are_convertible <- function(from, to) { ud_are_convertible(from, to) } convert <- function(value, from, to) { stopifnot(ud_are_convertible(from, to)) ud_convert(unclass(value), from, to) } #' Set measurement units on a numeric vector #' #' @param x numeric vector, or object of class \code{units} #' @param value object of class \code{units} or \code{symbolic_units}, or in the case of \code{set_units} expression with symbols that can be resolved in \link{ud_units} (see examples). #' #' @return object of class \code{units} #' @details if \code{value} is of class \code{units} and has a value unequal to 1, this value is ignored unless \code{units_options("simplifiy")} is \code{TRUE}. If \code{simplify} is \code{TRUE}, \code{x} is multiplied by this value. #' @export #' @name units #' #' @examples #' x = 1:3 #' class(x) #' units(x) <- as_units("m/s") #' class(x) #' y = 2:5 `units<-.numeric` <- function(x, value) { if(is.null(value)) return(x) if(!inherits(value, "units") && !inherits(value, "symbolic_units")) value <- as_units(value) if (inherits(value, "units")) { if (any(is.na(value))) stop("a missing value for units is not allowed") if (isTRUE(.units.simplify())) x <- x * unclass(value) else if (any(unclass(value) != 1.0)) warning(paste("numeric value", unclass(value), "is ignored in unit assignment")) value <- units(value) } attr(x, "units") = value class(x) <- "units" x } #' Convert units #' #' @name units #' @export #' #' @examples #' a <- set_units(1:3, m/s) #' units(a) <- with(ud_units, km/h) #' a #' # convert to a mixed_units object: #' units(a) = c("m/s", "km/h", "km/h") #' a `units<-.units` <- function(x, value) { if(is.null(value)) return(drop_units(x)) if(!inherits(value, "units") && !inherits(value, "symbolic_units")) { if ((is.character(value) && length(value) > 1)) return(set_units(mixed_units(x), value)) value <- as_units(value) } dimx = dim(x) if (inherits(value, "units")) { if (!identical(as.numeric(value), 1)) x <- .as.units(unclass(x) * unclass(value), units(x)) value <- units(value) } if (identical(units(x), value)) # do nothing; possibly user-defined units: return(x) str1 <- as.character(units(x)) str2 <- as.character(value) if (are_convertible(str1, str2)) .as.units(convert(x, str1, str2), value, dim = dimx) else stop(paste("cannot convert", units(x), "into", value), call. = FALSE) } #unit_ambiguous = function(value) { # msg = paste("ambiguous argument:", value, "is interpreted by its name, not by its value") # warning(msg, call. = FALSE) #} #' @name units #' @export `units<-.logical` <- function(x, value) { if (!all(is.na(x))) stop("x must be numeric, non-NA logical not supported") x <- as.numeric(x) units(x) <- value x } #' retrieve measurement units from \code{units} object #' #' @export #' @name units #' @return the units method retrieves the units attribute, which is of class \code{symbolic_units} units.units <- function(x) { attr(x, "units") } #' @export units.symbolic_units <- function(x) { x } #' convert object to a units object #' #' @param x object of class units #' @param value an object of class units, or something coercible to one with #' \code{as_units} #' @param ... passed on to other methods #' #' @export as_units <- function(x, ...) { UseMethod("as_units") } #' @export as_units.units <- function(x, value, ...) { if(!missing(value) && !identical(units(value), units(x))) warning("Use set_units() to perform unit conversion. Return unit unmodified") x } #' @export as_units.symbolic_units <- function(x, value, ...) { if(!missing(value)) warning("supplied value ignored") .as.units(1L, x) } #' @export #' @name as_units as_units.default <- function(x, value = unitless, ...) { if (is.null(x)) return(x) units(x) <- value x } #' difftime objects to units #' #' @export #' @name as_units #' #' @examples #' s = Sys.time() #' d = s - (s+1) #' as_units(d) as_units.difftime <- function(x, value, ...) { u <- attr(x, "units") x <- unclass(x) attr(x, "units") <- NULL # convert from difftime to udunits2: if (u == "secs") # secs -> s x <- x * symbolic_unit("s") else if (u == "mins") # mins -> min x <- x * symbolic_unit("min") else if (u == "hours") # hours -> h x <- x * symbolic_unit("h") else if (u == "days") # days -> d x <- x * symbolic_unit("d") else if (u == "weeks") { # weeks -> 7 days x <- 7 * x x <- x * symbolic_unit("d") } else stop(paste("unknown time units", u, "in difftime object")) if (!missing(value)) # convert optionally: units(x) <- value x } #' @export as.data.frame.units <- function(x, row.names = NULL, optional = FALSE, ...) { df = as.data.frame(unclass(x), row.names, optional, ...) if (!optional && ncol(df) == 1) colnames(df) <- deparse(substitute(x)) for (i in seq_along(df)) units(df[[i]]) = units(x) df } #' @export as.list.units <- function(x, ...) mapply(set_units, unclass(x), x, mode="standard", SIMPLIFY=FALSE) #' convert units object into difftime object #' #' @param x object of class \code{units} #' #' @export #' @examples #' #' t1 = Sys.time() #' t2 = t1 + 3600 #' d = t2 - t1 #' du <- as_units(d) #' dt = as_difftime(du) #' class(dt) #' dt as_difftime <- function(x) { stopifnot(inherits(x, "units")) u <- as.character(units(x)) if (u == "s") as.difftime(x, units = "secs") else if (u == "min") as.difftime(x, units = "mins") else if (u == "h") as.difftime(x, units = "hours") else if (u == "d") as.difftime(x, units = "days") else stop(paste("cannot convert unit", u, "to difftime object")) } # #' Convert units to hms # #' # #' Convert units to hms # #' @param x object of class units # #' @param ... passed on to as.hms.difftime # #' @return object of class hms # #' @examples # #' if (require(hms)) { # #' as.hms(1:10 * with(ud_units, s)) # #' as.hms(1:10 * with(ud_units, min)) # #' as.hms(1:10 * with(ud_units, h)) # #' as.hms(1:10 * with(ud_units, d)) # #' } # #' @export # as.hms.units = function(x, ...) { # hms::as.hms(as_difftime(x), ...) # } #' @export `[.units` <- function(x, i, j, ..., drop = TRUE) .as.units(NextMethod(), units(x)) #' @export `[[.units` <- function(x, i, j, ...) .as.units(NextMethod(), units(x)) #' @export as.POSIXct.units = function (x, tz = "UTC", ...) { units(x) = symbolic_unit("seconds since 1970-01-01 00:00:00 +00:00") as.POSIXct.numeric(as.numeric(x), tz = tz, origin = as.POSIXct("1970-01-01 00:00:00", tz = "UTC")) } #' @method as.Date units #' @export as.Date.units = function (x, ...) { units(x) = symbolic_unit("days since 1970-01-01") as.Date(as.numeric(x), origin = as.Date("1970-01-01 00:00:00")) } #' @export as_units.POSIXt = function(x, value, ...) { u = as.numeric(as.POSIXct(x)) units(u) = symbolic_unit("seconds since 1970-01-01 00:00:00 +00:00") if (! missing(value)) units(u) = symbolic_unit(value) u } #' @export as_units.Date = function(x, value, ...) { u = as.numeric(x) units(u) = symbolic_unit("days since 1970-01-01") if (!missing(value)) units(u) = symbolic_unit(value) u } units/R/plot.R0000644000176200001440000001200113420464630012712 0ustar liggesusers#' create axis label with appropriate labels #' #' create axis label with appropriate labels #' @param lab length one character; name of the variable to plot #' @param u vector of class \code{units} #' @param sep length two character vector, defaulting to \code{c("~","~")}, with #' the white space between unit name and unit symbols, and between subsequent #' symbols. #' @param group length two character vector with grouping symbols, e.g. #' \code{c("(",")")} for parenthesis, or \code{c("","")} for no group symbols #' @param parse logical; indicates whether a parseable expression should be #' returned (typically needed for super scripts), or a simple character string #' without special formatting. #' @export #' @name plot.units #' @details \link{units_options} can be used to set and change the defaults for #' \code{sep}, \code{group} and \code{doParse}. make_unit_label = function(lab, u, sep = units_options("sep"), group = units_options("group"), parse = units_options("parse")) { if (parse) { str = paste0("group('", group[1], "',", as.character(units(u), escape_units = TRUE, plot_sep = sep[2]), ",'", group[2], "')") if (length(grep("[^\t ]", lab)) > 0) { str = paste0(lab, "*", sep[1], str) } parse(text = str) } else { paste0(lab, " ", group[1], as.character(units(u)), group[2]) } } #' plot unit objects #' #' plot unit objects #' @param x object of class units, to plot along the x axis, or, if y is missing, along the y axis #' @param y object to plot along the y axis, or missing #' @param xlab character; x axis label #' @param ylab character; y axis label #' @param ... other parameters, passed on to \link{plot.default} #' @export #' @examples #' oldpar = par(mar = par("mar") + c(0, .3, 0, 0)) #' displacement = mtcars$disp * ud_units[["in"]]^3 #' # an example that would break if parse were (default) TRUE, since 'in' is a reserved word: #' units_options(parse=FALSE) #' make_unit_label("displacement", displacement) #' units_options(parse=TRUE) #' units(displacement) = with(ud_units, cm^3) #' weight = mtcars$wt * 1000 * with(ud_units, lb) #' units(weight) = with(ud_units, kg) #' plot(weight, displacement) #' units_options(group = c("(", ")") ) # parenthesis instead of square brackets #' plot(weight, displacement) #' units_options(sep = c("~~~", "~"), group = c("", "")) # no brackets; extra space #' plot(weight, displacement) #' units_options(sep = c("~", "~~"), group = c("[", "]")) #' gallon = as_units("gallon") #' consumption = mtcars$mpg * with(ud_units, mi/gallon) #' units(consumption) = with(ud_units, km/l) #' plot(displacement, consumption) # division in consumption #' units_options(negative_power = TRUE) # division becomes ^-1 #' plot(displacement, consumption) #' plot(1/displacement, 1/consumption) #' par(oldpar) plot.units <- function(x, y, xlab = NULL, ylab = NULL, ...) { # We define the axis labels if they are not already provided and then let # the default plotting function take over... xlab0 = paste(deparse(substitute(x), 500), collapse = "\\n") if (missing(y)) { # from xy.coords: if (is.null(ylab)) ylab <- make_unit_label(deparse(substitute(x)), x) if (is.null(xlab)) xlab <- "Index" y <- x x <- seq_along(x) return(NextMethod("plot", x, y, xlab=xlab, ylab=ylab)) } if (is.null(xlab)) { xlab <- make_unit_label(xlab0, x) } if (is.null(ylab) && inherits(y, "units")) { ylab <- make_unit_label(deparse(substitute(y)), y) } NextMethod("plot", xlab=xlab, ylab=ylab) } #' histogram for unit objects #' #' histogram for unit objects #' @param x object of class units, for which we want to plot the histogram #' @param xlab character; x axis label #' @param main character; title of histogram #' @param ... parameters passed on to \link{hist.default} #' @export #' @examples #' units_options(parse = FALSE) # otherwise we break on the funny symbol! #' u = set_units(rnorm(100), degree_C) #' hist(u) hist.units <- function(x, xlab = NULL, main = paste("Histogram of", xname), ...) { # We define the axis labels if they are not already provided and then let # the default plotting function take over... xname <- paste(deparse(substitute(x), 500), collapse = "\n") if (is.null(xlab)) { xlab <- make_unit_label(xname, x) } NextMethod("hist", xlab=xlab, main=main) } #' boxplot for unit objects #' #' boxplot for unit objects #' @param x object of class units, for which we want to plot the boxplot #' @param ... parameters passed on to \link{boxplot.default} #' @param horizontal logical indicating if the boxplots should be horizontal; #' default FALSE means vertical boxes. #' @export #' @examples #' units_options(parse = FALSE) # otherwise we break on the funny symbol! #' u = set_units(rnorm(100), degree_C) #' boxplot(u) boxplot.units <- function(x, ..., horizontal = FALSE) { xlab <- ylab <- NULL lab <- make_unit_label(deparse(substitute(x)), x) if (horizontal) xlab <- lab else ylab <- lab x <- drop_units(x) NextMethod("boxplot", xlab=xlab, ylab=ylab) } units/R/mixed.R0000644000176200001440000000740013463271135013054 0ustar liggesusers.as.mixed_units = function(x) { stopifnot(is.list(unclass(x))) structure(x, class = "mixed_units") } # constructor function: #' Create or convert to a mixed units list-column #' @param x numeric, or vector of class \code{units} #' @param values character vector with units encodings, or list with symbolic units of class \code{mixed_symbolic_units} #' @param value see values #' @param ... ignored #' @details if \code{x} is of class \code{units}, \code{values} should be missing or of class \code{mixed_symbolic_units}; if \code{x} is numeric, \code{values} should be a character vector the length of \code{x}. #' @examples #' a <- 1:4 #' u <- c("m/s", "km/h", "mg/L", "g") #' mixed_units(a, u) #' units(a) = as_units("m/s") #' mixed_units(a) # converts to mixed representation #' @export mixed_units <- function(x, values, ...) UseMethod("mixed_units") #' @export mixed_units.units = function(x, values, ...) { stopifnot(missing(values)) u = as.character(units(x)) mixed_units(unclass(x), rep(u, length(x))) } #' @export mixed_units.numeric = function(x, values, ...) { #stopifnot(length(x) == length(values), is.character(values), is.numeric(x)) stopifnot(is.character(values), is.numeric(x)) .as.mixed_units(mapply(set_units, x, values, mode = "standard", SIMPLIFY = FALSE)) } #' @export #' @name mixed_units `units<-.mixed_units` = function(x, value) { set_units(x, value) } #' @export format.mixed_units = function(x, ...) { sapply(x, format, ...) } #' @export `[.mixed_units` = function(x, i, ...) { .as.mixed_units(unclass(x)[i]) } c.mixed_units = function(...) { args = list(...) .as.mixed_units(do.call(c, lapply(args, unclass))) } #' @export set_units.mixed_units = function(x, value, ..., mode = "standard") { if (! is.character(value)) stop("use character string to denote target unit") # FIXME: rlang::quo stuff needed here? #do.call(c, lapply(x, set_units, value = value, mode = mode, ...)) .as.mixed_units(mapply(set_units, x, value, mode = mode, SIMPLIFY = FALSE)) } #' @export as_units.mixed_units = function(x, ...) { set_units(do.call(c, x), value = units(x[[1]]), mode = "standard") } #' @export units.mixed_units = function(x) { structure(lapply(x, units), class = "mixed_symbolic_units") } #' @export as.character.mixed_symbolic_units = function(x, ...) { sapply(x, as.character) } #' @export print.mixed_units = function(x, ...) { cat("Mixed units: ") tbl = table(as.character(units(x))) tbl = paste(names(tbl), " (", as.numeric(tbl), ")", sep = "") cat(paste(tbl, collapse = ", "), "\n") cat(paste(format(x, ...), collapse = ", "), "\n") } #' @name drop_units #' @export drop_units.mixed_units = function(x) { sapply(x, drop_units) } #' @export Ops.mixed_units = function(e1, e2) { if (inherits(e2, "units")) e2 = mixed_units(e2) ret = switch(.Generic, "==" = mapply(function(x, y) { x == y }, e1, e2, SIMPLIFY = TRUE), "!=" = mapply(function(x, y) { x != y }, e1, e2, SIMPLIFY = TRUE), "*" = mapply(function(x, y) { x * y }, e1, e2, SIMPLIFY = FALSE), "/" = mapply(function(x, y) { x / y }, e1, e2, SIMPLIFY = FALSE), "+" = mapply(function(x, y) { x + y }, e1, e2, SIMPLIFY = FALSE), "-" = mapply(function(x, y) { x - y }, e1, e2, SIMPLIFY = FALSE), stop(paste("operation", .Generic, "not supported")) ) if (is.list(ret)) ret = .as.mixed_units(ret) ret } #' @name tibble type_sum.mixed_units <- function(x, ...) { "mixed_units" } #' @name tibble pillar_shaft.mixed_units <- function(x, ...) { if (! requireNamespace("pillar", quietly = TRUE)) stop("package pillar not available: install first?") out <- format(x, ...) pillar::new_pillar_shaft_simple(out, align = "right", min_width = 6) } #' @export str.mixed_units = function(object, ...) { cat("Object of class mixed_units:\n") str(unclass(object), ...) } units/R/udunits.R0000644000176200001440000000110313306477535013443 0ustar liggesusersud_are_convertible = function(u1, u2) { res <- try(R_ut_are_convertible(R_ut_parse(as.character(u1)), R_ut_parse(as.character(u2))), silent = TRUE) ! inherits(res, "try-error") && res } ud_get_symbol = function(u) { sy = R_ut_get_symbol(u) if (sy == "") R_ut_get_name(u) else sy } ud_is_parseable = function(u) { res <- try(R_ut_parse(u), silent = TRUE) ! inherits(res, "try-error") } ud_convert = function(value, from, to) { R_convert_doubles(R_ut_parse(from), R_ut_parse(to), value) } ud_set_encoding = function(enc) { R_ut_set_encoding(as.character(enc)) } units/R/user_conversion.R0000644000176200001440000001073113472516125015173 0ustar liggesusers#' Define new symbolic units #' #' Adding a symbolic unit allows it to be used in \code{as_units}, #' \code{make_units} and \code{set_units}. No installation is performed if the #' unit is already known by udunits. #' #' @param name a length 1 character vector that is the unit name or symbol. #' @param warn warns if the supplied unit symbol is already a valid unit symbol #' recognized by udunits. #' @param dimensionless logical; if \code{TRUE}, a new dimensionless unit is created, if \code{FALSE} a new base unit is created. Dimensionless units are convertible to other dimensionless units (such as \code{rad}), new base units are not convertible to other existing units. #' #' @details \code{install_symbolic_unit} installs a new dimensionless unit; these are directly compatible to any other dimensionless unit. To install a new unit that is a scaled or shifted version of an existing unit, use \code{install_conversion_constant} or \code{install_conversion_offset} directly. #' @export #' @rdname install_symbolic_unit #' @seealso \code{\link{install_conversion_constant}}, \code{\link{install_conversion_offset}} #' @examples #' install_symbolic_unit("person") #' set_units(1, rad) + set_units(1, person) # that is how dimensionless units work! install_symbolic_unit <- function(name, warn = TRUE, dimensionless = TRUE) { check_unit_format(name) if(ud_is_parseable(name)) { if (warn) warning(sQuote(name), " is already a valid unit recognized by udunits; removing and reinstalling.") remove_symbolic_unit(name) } if (dimensionless) R_ut_new_dimensionless_unit(name) else R_ut_new_base_unit(name) } #' @export #' @rdname install_symbolic_unit remove_symbolic_unit <- function(name) { R_ut_remove_unit(name) } #' Install a conversion constant or offset between user-defined units. #' #' @description Tells the \code{units} package how to convert between units that #' have a linear relationship, i.e. can be related on the form \eqn{y = \alpha #' x} (constant) or \eqn{y = \alpha + x} (offset). #' #' @param from String for the symbol of the unit being converted from. #' @param to String for the symbol of the unit being converted to. One of \code{from} and \code{to} must be an existing unit name. #' @param const The constant \eqn{\alpha} in the conversion. #' #' @details This function handles the very common case where units are related #' through a linear function, that is, you can convert from one to the other #' as \eqn{y = \alpha x}. Using this function, you specify that you #' can go from values of type \code{from} to values of type \code{to} by #' multiplying by a constant, or adding a constant. #' #' @examples #' #' # one orange is worth two apples #' install_symbolic_unit("orange") #' install_conversion_constant("orange", "apple", 2) # apple = 2 * orange #' apples <- 2 * as_units("apple") #' oranges <- 1 * as_units("orange") #' apples + oranges #' oranges + apples #' #' @export #' @seealso \code{\link{install_symbolic_unit}}, \code{\link{remove_symbolic_unit}} install_conversion_constant <- function(from, to, const) { stopifnot(is.finite(const), const != 0.0) if (! xor(ud_is_parseable(from), ud_is_parseable(to))) stop("exactly one of (from, to) must be a known unit") if (ud_is_parseable(to)) R_ut_scale(check_unit_format(from), to, as.double(const)) else R_ut_scale(check_unit_format(to), from, 1.0 / as.double(const)) } #' @export #' @name install_conversion_constant #' @examples #' install_conversion_offset("meter", "newmeter", 1) #' m = set_units(1:3, meter) #' n = set_units(1:3, newmeter) #' m + n #' n + m install_conversion_offset <- function(from, to, const) { stopifnot(is.finite(const)) if (! xor(ud_is_parseable(from), ud_is_parseable(to))) stop("exactly one of (from, to) must be a known unit") if (ud_is_parseable(to)) R_ut_offset(check_unit_format(from), to, -as.double(const)) else R_ut_offset(check_unit_format(to), from, as.double(const)) } check_unit_format <- function(x) { cond <- c( # leading and trailing numbers grepl("^[[:space:]]*[0-9]+", x), grepl("[0-9]+[[:space:]]*$", x), # arithmetic operators grepl("\\+|\\-|\\*|\\/|\\^", x), # intermediate spaces grepl("[[:alnum:][:punct:]]+[[:space:]]+[[:alnum:][:punct:]]+", x) ) if (any(cond)) stop("the following elements are not allowed in new unit names/symbols:\n", " - leading or trailing numbers\n", " - arithmetic operators\n", " - intermediate white spaces") x } units/NEWS.md0000644000176200001440000000767613527456607012551 0ustar liggesusers# version 0.6-5 # version 0.6-4 * fix support for weights with units in `weighted.mean`; #205 * invalid names for new units now trigger a proper error message; #209 addressing #208 * fix issues in strict latin1 environments; #202 # version 0.6-3 * improve platform dependent encodings handling; #183 * don't force `as.numeric` when unnecessary; #182 addressing #181 * fix valgrind issues on CRAN and tidy up tests; #193 addressing #192 * new method `drop_units` for data frames; #191 addressing #187 # version 0.6-2 * fix support for logarithms and decibels; #177 addressing #176 * add delayed S3 registration mechanism for R >= 3.6.0 # version 0.6-1 * vectors with mixed units are now supported; #145 * `NA` values for units now trigger a proper error message; #163 # version 0.6-0 * print units as [unit] more consistently, e.g. for single unit and in data.frames; #132 * improve printing of unitless units; provide option to print something else than 1; #150 * fix printing unitless in labels when `negative_power` is `TRUE`; #133 * `install_symbolic_unit` now adds a dimensionless unit, integrated in the units system, meaning that prefixes on it work as well; #71 * `install_conversion_constant` and `install_conversion_offset` now install a new unit that is a function of an existing udunits unit.; #71, #84 * unit simplification can now be user-controlled by `units_options`; #89 * `set_units(15, mg/kg)` is now no longer simplified to 1e-9 unitless; #89 * directly uses the udunits2 C library; drop dependence on R package `udunits2`, fixing R package `udunits2` memory leaks; #135 * drops `%*%`, no longer gives warning when loading # version 0.5-1 # version 0.5-0 * deal with trigonometric functions for units degree; return units rad on inverse trigonometric functions. * Unit creation has been significantly refactored. `units<-` now accepts strings or quoted language objects on the right hand side, powered by new S3 methods for `as_units`. All valid unit symbols and unit names recognized by package 'udunits2' are now accepted. New user facing function `make_units()` (plural s) is also provided. See `?as_units` for details. @t-kalinowski * new functions `valid_udunits()` and `valid_udunits_prefixes()` generate tidy dataframes listing all the valid unit names, symbols, and prefixes recognized by udunits. @t-kalinowski * new function `install_symbolic_unit()` for adding custom, user-defined units. @t-kalinowski * `make_unit` and `parse_unit` (singular unit) have been deprecated, please use `as_units` instead. * `ud_units` is no longer necessary and is soft-deprecated, and may be removed in a future release. * add `%*%` as an S3 generic; #54 * add `%%` and `%/%` to `Ops.units` * support unary + and - ; #56 * add `seq` method for `units`, converting units to those of the first argument * Deprecate `as.dt` for `as_difftime`, `as.units` for `as_units` and `as_cf` for `deparse_unit` # version 0.4-6 * add `all.equal` method for `units`; #51 * add `deparse_unit` to replace `as_cf` * add calender/time conversions between `udunits` time units like `minutes from 1900-0-0`, and R's `POSIXct` and `Date` * add `as_units` to replace `as.units` * rename `as.dt` to `as_difftime` # version 0.4-5 * add support for user-defined unit conversion; #31 * allow for 1/n integer powers, as in `set_units(1:10, m^-2) ^ 0.5`; #29 * properly set log units after log transform; #33 * `sin`, `cos` and `tan` no longer complain when units is `rad`, and return `unitless`; #40 * now allow for `set_units(1:3, "°C")` and also `set_units(1:3, "degree_Celsius")` by resolving names to symbols first; #43 * `set_units(x)` with `x` numeric sets units to `unitless`; #41 # version 0.4-4 * fix a result units bug when multiplying or dividing units vectors of different length, #34 * add a `rep` method for `units` vectors # version 0.4-3 * support for `set_units(1:10, m)` which does not require to declare or define, `m` (`m` is resolved automatically from `ud_units`) units/MD50000644000176200001440000001135413547072622011740 0ustar liggesusers7431915230aad900aa6de17978ce31fc *DESCRIPTION 8b4100577ed702507727f645aed31cc5 *NAMESPACE fa00cb744ded904dfbc3dd39fe9e3319 *NEWS.md 47fed243a4b8257aeaffbb1cbe7d1a33 *R/RcppExports.R e51836208e0e9fc7f425d44e3d8b7f38 *R/arith.R d8ba3223925f48a8f6801cdec363e547 *R/conversion.R 79ebd4d9e6bce57c0de6cd7b3287fbb0 *R/deprecated.R 1f79a68f3a77b340ae8ef77871423018 *R/init.R 31d207bdb0b2d668b470d16ab71a24a2 *R/make_units.R 66820b4feb69ea8f7e77ddc7ac5068d1 *R/math.R 17aa60ad9941134d835c216c62ea967c *R/misc.R aab3ea00bbd872299a84f41185eb0d11 *R/mixed.R 601be55e668916fd4cee04b8d57f13d2 *R/options.R 6d5b3528eab4d0f0e0daa9f2caea44ec *R/plot.R 56565256d8be0d156b436825ddb4f18b *R/set_units.R 2b9cb0ee33675779502da44f038f0a6a *R/summaries.R 9418d19699c307717e650f1e8f322da3 *R/symbolic_units.R 782267b96c82551cdef395d6e62fc460 *R/sysdata.rda 62044bc37a676d3a4ea3abd4bc27bcb8 *R/udunits.R 0ae0c87a52c1873fb92ca0456bf47968 *R/user_conversion.R a515e011d053843fd3dc242c8415e995 *R/valid_udunits.R 1e66dcb1df3435c11eca0acd6891bfa2 *TODO a6cf310f1cf3b5dbfddcc1d5657d7277 *build/vignette.rds 5cc65e8e0f99d3c430cc7da84dfdfe26 *cleanup d988f4af8d972ba487529f2716ffc0d7 *configure b1e8639b41b801c4a9fe8ac0fa515f1a *configure.ac a5b1424e81e8a55f734e0ec33b67129b *demo/00Index 3e83819b17560bb844b5404db80edbe5 *demo/cf.R a3d9c06754b67d2bddc9c636f142f34f *demo/ggforce.R 9233f4cd2d39d8850034e7f080b45444 *demo/year.R cf1d077dd7e8d918645b6bdeb54ded66 *inst/CITATION b610d7909c7e2387274f747777e12b17 *inst/doc/measurement_units_in_R.R 3821bde2663cf80383feb79125f253a9 *inst/doc/measurement_units_in_R.Rmd 1e0f933a1d0fb9b2d43d83e265e926cc *inst/doc/measurement_units_in_R.html c76664843f4ba1b0671d13540043d688 *inst/doc/units.R dbfc5ec4aaaffc153d301008da35269c *inst/doc/units.Rmd 69a03bc49cb69c00abe2a12bdf16de45 *inst/doc/units.html 26f28956899a13203f9d11baf0f03a1d *inst/share/udunits/udunits2-accepted.xml cf5342a71d0250353fda59ad83c35a9e *inst/share/udunits/udunits2-base.xml 92b3d24d148513296f9f24449373ddfb *inst/share/udunits/udunits2-common.xml 4cffbdeeca15b507f2ecf26f6e7391b3 *inst/share/udunits/udunits2-derived.xml b1080ec53f0733b4fde871655c8403fb *inst/share/udunits/udunits2-prefixes.xml 43619d63e8dcd58f2c0034cfb4b50b59 *inst/share/udunits/udunits2.xml 336d35023db53142d7a3c1384561ab10 *man/Math.units.Rd 9afed6e4d36c8a4b66fd6f904f0c8397 *man/Ops.units.Rd 4f82d72ec5f9c4544840b87864cbd893 *man/as_difftime.Rd 6872fd457e0093877c95a457e32a9c90 *man/as_units.Rd f7a15e212918afc407e02a9a83318d59 *man/boxplot.units.Rd 4425ed2ed002f21903ae51e850cfaf3d *man/deparse_unit.Rd f8d8b35a9065a46d473d0b38613b3bb4 *man/deprecated.Rd e0288da875def374ff55636c5b99820a *man/drop_units.Rd e37f78daa1f83de34f588f24eeb84326 *man/hist.units.Rd d8051b52c9c9668811c0f89a058d914b *man/install_conversion_constant.Rd 32aea8fe9ba07d67e45a88556191d172 *man/install_symbolic_unit.Rd f03a9f015e954d146d969d15d81078c2 *man/mixed_units.Rd 3f91d9c1ac6bf3f4a022145f35a0b936 *man/plot.units.Rd 18ff7261600fd81bce687d8dea420aaf *man/seq.units.Rd f5f2061fe2ec0d15f09b61c02b02e2f1 *man/set_units.Rd 809abd1e59768712a157808863eb229d *man/tibble.Rd 710f73f394d037530d2c4002c20a46a4 *man/ud_units.Rd 3a048d8dc9c443ea453072f4dfc9c785 *man/unitless.Rd 576f6feabe98832d9fb7d8d56ce980e1 *man/units.Rd 5db6ed08e77370241c74bd3e2c68a1d8 *man/units_options.Rd 5c6b4bb8763dd0aa45d8a7e0c06bf6eb *man/valid_udunits.Rd 5616720d7505dc0b4a29e283c2db1466 *src/Makevars.in a55dca63209a921c02c39226dc99392f *src/Makevars.win dd5d621206dea23d9a9033e9d4d170d7 *src/RcppExports.cpp 157d44590d70c16461ff7d3eaae377d3 *src/io.c 619ecf85ce558d6fb70539b3a51c3c99 *src/io.h 57412d648bc46f9b6b97890349c969a6 *src/udunits.cpp 876599d16da43ed688e718aaf68d1bec *tests/plot.R 46555b7133c513540299a821fdf49b08 *tests/set_units.R 303cf34dc97f3cb9280035eb0b23c752 *tests/testthat.R 7ec60c876a36e4ab75f8e2879b342e9e *tests/testthat/test_arith.R b2248fa073e48e0161ad489fd39f5c48 *tests/testthat/test_conversion.R cf6e3f5b1bb44456fc24ff55b0a32d99 *tests/testthat/test_math.R f0faba4b01d81920acb8942cd6a24f66 *tests/testthat/test_misc.R 6314304f0cc412c2e6717f1ea8a5762d *tests/testthat/test_mixed.R 8161c6dcadf9a2e7ccba6a9963f3dba5 *tests/testthat/test_summaries.R 6ed86dcfb0f5468edbde970bcdd2bb5d *tests/testthat/test_symbolic_units.R 676c830cb0467003e76ef73fe8f62792 *tests/testthat/test_time.R 56129ebb518504791f9b1b9c176c4af0 *tests/testthat/test_udunits.R 785d9548cea1197324f4dee04199d827 *tests/testthat/test_unit_creation.R d8a64f8322acef482bdda5046982d7cc *tests/testthat/test_user_conversion.R b166a2158410d4f1fac6239bb4a98ff2 *tools/winlibs.R bec300764a420bd3aee8c784d3529562 *vignettes/647_Global_Temperature_Data_File.txt 3821bde2663cf80383feb79125f253a9 *vignettes/measurement_units_in_R.Rmd e6ec28bdf61bb55062a44b78724bab1a *vignettes/measurement_units_in_R.bib dbfc5ec4aaaffc153d301008da35269c *vignettes/units.Rmd units/inst/0000755000176200001440000000000013547030302012366 5ustar liggesusersunits/inst/doc/0000755000176200001440000000000013547030302013133 5ustar liggesusersunits/inst/doc/measurement_units_in_R.Rmd0000644000176200001440000004713713430273643020341 0ustar liggesusers--- title: "Measurement units in R" author: "Edzer Pebesma, Thomas Mailund, and James Hiebert" output: html_document: toc: true toc_float: collapsed: false smooth_scroll: false toc_depth: 2 bibliography: measurement_units_in_R.bib link-citations: yes vignette: > %\VignetteIndexEntry{Measurement units in R} %\VignetteEngine{knitr::rmarkdown} %\VignetteEncoding{UTF-8} --- ```{r echo=FALSE} knitr::opts_chunk$set(collapse = TRUE) ``` This vignette is identical to @rj, except for two changes: * it has been synchronized with updates to the [units](https://cran.r-project.org/package=units) package * it has been converted to R-markdown ## Abstract We briefly review SI units, and discuss R packages that deal with measurement units, their compatibility and conversion. Built upon [udunits2](https://cran.r-project.org/package=udunits2) and the UNIDATA udunits library, we introduce the package [units](https://cran.r-project.org/package=units) that provides a class for maintaining unit metadata. When used in expression, it automatically converts units, and simplifies units of results when possible; in case of incompatible units, errors are raised. The class flexibly allows expansion beyond predefined units. Using [units](https://cran.r-project.org/package=units) may eliminate a whole class of potential scientific programming mistakes. We discuss the potential and limitations of computing with explicit units. ## Introduction Two quotes from @cobb -- _Data are not just numbers, they are numbers with a context_ and _in data analysis, context provides meaning_ -- illustrate that for a data analysis to be meaningful, knowledge of the data's context is needed. Pragmatic aspects of this context include who collected or generated the data, how this was done, and for which purpose [@scheider]; semantic aspects concern what the data represents: which aspect of the world do the data refer to, when and where were they measured, and what a value of `1` means. R does allow for keeping some context with data, for instance * `data.frame` columns must have and `list` elements may have names that can be used to describe context, using freetext * `matrix` or `array` objects may have `dimnames` * for variables of class `factor` or `ordered`, `levels` may indicate, using freetext, the categories of nominal or ordinal variables * `POSIXt` and `Date` objects specify how numbers should be interpreted as time or date, with fixed units (second and day, respectively) and origin (Jan 1, 1970, 00:00 UTC) * `difftime` objects specify how time duration can be represented by numbers, with flexible units (secs, mins, hours, days, weeks); [lubridate](https://cran.r-project.org/package=lubridate) [@lubridate] extends some of this functionality. Furthermore, if spatial objects as defined in package [sp](https://cran.r-project.org/package=sp) [@sp] have a proper coordinate reference system set, they can be transformed to other datums, or converted to various flat (projected) representations of the Earth [@iliffe]. In many cases however, R drops contextual information. As an example, we look at annual global land-ocean temperature index (from `http://climate.nasa.gov/vital-signs/global-temperature/`) since 1960: ```{r} temp_data = subset(read.table("647_Global_Temperature_Data_File.txt", header=TRUE)[1:2], Year >= 1960) temp_data$date = as.Date(paste0(temp_data$Year, "-01-01")) temp_data$time = as.POSIXct(temp_data$date) Sys.setenv(TZ="UTC") head(temp_data, 3) year_duration = diff(temp_data$date) mean(year_duration) ``` Here, the time difference units are reported for the `difftime` object `year_duration`, but if we would use it in a linear algebra operation ```{r} year_duration %*% rep(1, length(year_duration)) / length(year_duration) ``` the unit is dropped. Similarly, for linear regression coefficients we see ```{r} coef(lm(Annual_Mean ~ date, temp_data)) coef(lm(Annual_Mean ~ time, temp_data)) ``` where the unit of change is in degrees Celsius but either _per day_ (`date`) or _per second_ (`time`). For purely mathematical manipulations, R often strips context from numbers when it is carried in attributes, the linear algebra routines being a prime example. Most variables are somehow attributed with information about their _units_, which specify what the value `1` of this variable represents. This may be counts of something, e.g. `1 apple`, but it may also refer to some _physical unit_, such as distance in meter. This article discusses how strong unit support can be introduced in R. ## SI The [BIPM](http://www.bipm.org/) (Bureau International des Poids et Mesures) is "_the intergovernmental organization through which Member States act together on matters related to measurement science and measurement standards. Its recommended practical system of units of measurement is the International System of Units (Syst\`{e}me International d'Unit\'{e}s, with the international abbreviation SI)_ (http://www.bipm.org/en/measurement-units/)". @si describe the SI units, where, briefly, _SI units_ * consist of seven base units (length, mass, time \& duration, electric current, thermodynamic temperature, amount of substance, and luminous intensity), each with a name and abbreviation (see table below) * consist of _derived units_ that are formed by products of powers of base units, such as m/s$^2$, many of which have special names and symbols (e.g. angle: 1 rad = 1 m/m; force: 1 N = 1 m kg s$^{-2}$) * consist of _coherent derived units_ when derived units include no numerical factors other than one (with the exception of `kg`; as a base unit, kg can be part of coherent derived units); an example of a coherent derived unit is 1 watt = 1 joule per 1 second, * may contain SI prefixes (k = kilo for $10^3$, m = milli for $10^{-3}$, etc.) * contain special quantities where units disappear (e.g., m/m) or have the nature of a count, in which cases the unit is 1. base quantities, SI units and their symbols (from @si, p. 23): | Base quantity | | SI base unit | | | -----------|--------|----------|------| | Name |Symbol|Name | Symbol | length | $l,x,r,$ etc.| meter | m | | mass | $m$ | kilogram | kg | | time, duration | $t$ | second | s | | electric current| $I, i$ | ampere | A | | thermodynamic temperature | $T$ | kelvin | K | | amount of substance | $n$ | mole | mol | | luminous intensity | $I_v$ | candela | cd | ## Related work in R Several R packages provide unit conversions. For instance, [measurements](https://cran.r-project.org/package=measurements) [@measurements] provides a collection of tools to make working with physical measurements easier. It converts between metric and imperial units, or calculates a dimension's unknown value from other dimensions' measurements. It does this by the `conv_unit` function: ```{r, eval=requireNamespace("measurements", quietly=TRUE)} library(measurements) conv_unit(2.54, "cm", "inch") conv_unit(c("101 44.32","3 19.453"), "deg_dec_min", "deg_min_sec") conv_unit(10, "cm_per_sec", "km_per_day") ``` but uses for instance `kph` instead of `km_per_hour`, and then `m3_per_hr` for flow -- unit names seem to come from convention rather than systematic composition. Object `conv_unit_options` contains all 173 supported units, categorized by the physical dimension they describe: ```{r, eval=requireNamespace("measurements", quietly=TRUE)} names(conv_unit_options) conv_unit_options$volume ``` Function `conv_dim` allows for the conversion of units in products or ratios, e.g. ```{r, eval=requireNamespace("measurements", quietly=TRUE)} conv_dim(x = 100, x_unit = "m", trans = 3, trans_unit = "ft_per_sec", y_unit = "min") ``` computes how many minutes it takes to travel 100 meters at 3 feet per second. Package [NISTunits](https://cran.r-project.org/package=NISTunits) [@NISTunits] provides fundamental physical constants (Quantity, Value, Uncertainty, Unit) for SI and non-SI units, plus unit conversions, based on the data from NIST (National Institute of Standards and Technology). The package provides a single function for every unit conversion; all but 5 from its 896 functions are of the form `NISTxxxTOyyy` where `xxx` and `yyy` refer to two different units. For instance, converting from W m$^{-2}$ to W inch$^{-2}$ is done by ```{r, eval=requireNamespace("NISTunits", quietly=TRUE)} library(NISTunits) NISTwattPerSqrMeterTOwattPerSqrInch(1:5) ``` Both [measurements](https://cran.r-project.org/package=measurements) and [NISTunits](https://cran.r-project.org/package=NISTunits) are written entirely in R. ## UNIDATA's udunits library and the `udunits2` R package Udunits, developed by UCAR/UNIDATA, advertises itself on [its web page](https://www.unidata.ucar.edu/software/udunits/) as: "_The udunits package supports units of physical quantities. Its C library provides for arithmetic manipulation of units and for conversion of numeric values between compatible units. The package contains an extensive unit database, which is in XML format and user-extendable._" The R package [udunits2](https://cran.r-project.org/package=udunits2) [@udunits2] provides a low-level R interface to the most important functions in the udunits2 C library. The functions provided by [udunits2](https://cran.r-project.org/package=udunits2) are ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} library(udunits2) ls(2) ``` Dropping the `ud` prefix, `is.parseable` verifies whether a unit is parseable ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.is.parseable("m/s") ud.is.parseable("q") ``` `are.convertible` specifies whether two units are convertible ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.are.convertible("m/s", "km/h") ud.are.convertible("m/s", "s") ``` `convert` converts units that are convertible, and throws an error otherwise ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.convert(1:3, "m/s", "km/h") ``` and `get.name`, `get.symbol` and `set.encoding` get name, get symbol or modify encoding of the character unit arguments. ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} ud.get.name("kg") ud.get.symbol("kilogram") ud.set.encoding("utf8") ``` Unlike the [measurements](https://cran.r-project.org/package=measurements) and [NISTunits](https://cran.r-project.org/package=NISTunits), [udunits2](https://cran.r-project.org/package=udunits2) parses units as expressions, and bases its logic upon the convertibility of expressions, rather than the comparison of fixed strings: ```{r, eval=requireNamespace("udunits2", quietly=TRUE)} m100_a = paste(rep("m", 100), collapse = "*") dm100_b = "dm^100" ud.is.parseable(m100_a) ud.is.parseable(dm100_b) ud.are.convertible(m100_a, dm100_b) ``` This has the advantage that through complex computations, intermediate objects can have units that are arbitrarily complex, and that can potentially be simplified later on. It also means that the package practically supports an unlimited amount of derived units. ## Udunits versus the Unified Code for Units of Measure (UCUM) Another set of encodings for measurement units is the Unified Code for Units of Measure (UCUM, @ucum). A dedicated web site\footnote{\url{http://coastwatch.pfeg.noaa.gov/erddap/convert/units.html}} describes the details of the differences between udunits and UCUM, and provides a conversion service between the two encoding sets. The UCUM website refers to some Java implementations, but some of the links seem to be dead. UCUM is the preferred encoding for standards from the Open Geospatial Consortium. udunits on the other hand is the units standard of choice by the climate science community, and is adopted by the CF (Climate and Forecast) conventions, which mostly uses NetCDF. NetCDF [@netcdf] is a binary data format that is widely used for atmospheric and climate model predictions. The udunits library is a C library that has strong support from UNIDATA, and we decided to build our developments on this, rather than on Java implementations of UCUM with a less clear provenance. ## Handling data with units in R: the units package The [units](https://cran.r-project.org/package=units) package builds `units` objects from scratch, e.g. where ```{r} library(units) x = set_units(1:5, m/s) str(x) ``` represents speed values in `m/s`. The units `m` and `s` are retrieved from the `ud_units` database, which is part of [units](https://cran.r-project.org/package=units), and was derived from the xml units database that is part of udunits2 C library. Units can be used in arbitrary R expressions like ```{r} set_units(1:3, m/s^2) ``` Several manipulations with `units` objects will now be illustrated. Manipulations that do not involve unit conversion are for instance addition: ```{r} x = set_units(1:3, m/s) x + 2 * x ``` Explicit unit conversion is done by assigning new units: ```{r} (x = set_units(x, cm/s)) as.numeric(x) ``` similar to the behaviour of `difftime` objects, this modifies the numeric values without modifying their meaning (what the numbers refer to). When mixing units in sums, comparisons or concatenation, units are automatically converted to those of the first argument: ```{r} y = set_units(1:3, km/h) x + y y + x x == y c(y, x) ``` where `c(y, x)` concatenates `y` and `x` after converting `x` to the units of `y`. Derived units are created where appropriate: ```{r} x * y x^3 ``` and meaningful error messages appear when units are not compatible: ```{r} e = try(z <- x + x * y) attr(e, "condition")[[1]] ``` The full set of methods and method groups for `units` objects is shown by ```{r} methods(class = "units") ``` where the method groups * `Ops` include operations that require compatible units, converting when necessary (`+`, `-`, `==`, `!=`, `<`, `>`, `<=`, `>=`), and operations that create new units (`*`, `/`, `^` and `**`), * `Math` include `abs`, `sign`, `floor`, `ceiling`, `trunc`, `round`, `signif`, `log`, `cumsum`, `cummax`, `cummin`, and * `Summary` include `sum`, `min`, `max` and `range`, and all convert to the unit of the first argument. When possible, new units are simplified: ```{r} a = set_units(1:10, m/s) b = set_units(1:10, h) a * b ustr1 = paste(rep("m", 101), collapse = "*") ustr2 = "dm^100" as_units(ustr1) / as_units(ustr2) ``` Units are printed as simple R expressions, e.g. ```{r} set_units(1, m^5/s^4) ``` Another way to print units commonly seen in Climate and Forecast Conventions\footnote{CF, \url{http://cfconventions.org/Data/cf-standard-names/34/build/cf-standard-name-table.html}} is `m2 s-1` for m$^2$/s. These are not R expressions, but they can be parsed by `as_units`, and created by `deparse_unit`: ```{r} as_units("m2 s-1") deparse_unit(set_units(1, m^2*s^-1)) ``` The `plot` and `hist` methods add units to default axis labels, an example is shown in the following figures. For [ggplot2](https://cran.r-project.org/package=ggplot2) plots [@ggplot2], automatic unit placement in default axis label is provided by package [ggforce](https://cran.r-project.org/package=ggforce) [@ggforce]; `demo(ggforce)` gives an example. ```{r fig=TRUE, height=3.8, width=7} library(units) units_options(negative_power = TRUE) # initialize variables with units: mtcars$consumption = set_units(mtcars$mpg, mi/gallon) # "in" is also a reserved R keyword, and so needs back-quotes: mtcars$displacement = set_units(mtcars$disp, `in`^3) # convert to SI: mtcars$consumption = set_units(mtcars$consumption, km/l) mtcars$displacement = set_units(mtcars$displacement, cm^3) par(mar = par("mar") + c(0, .3, 0, 0)) with(mtcars, plot(1/displacement, 1/consumption)) ``` ```{r fig=TRUE, height=3.8, width=7, eval=requireNamespace("ggforce", quietly=TRUE)} library(ggforce) if (utils::packageVersion("ggplot2") > "2.2.1") ggplot(mtcars) + geom_point(aes(x = 1/displacement, y = 1/consumption)) ``` Automatic conversion between `units` and `difftime` is provided: ```{r} (dt = diff(Sys.time() + c(0, 1, 1+60, 1+60+3600))) # class difftime (dt.u = as_units(dt)) identical(as_difftime(dt.u), dt) ``` as well as to and from `POSIXct` or `Date`: ```{r} (t1 <- as_units(as.POSIXct("2017-08-20 17:03:00"))) (t2 <- as_units(as.POSIXct("2017-08-20 17:03:00"), "hours since 2017-08-20")) (d1 <- as_units(as.Date("2017-08-20"))) as.POSIXct(t1) as.Date(d1) ``` Objects of class `units` can be used as columns in `data.frame` objects, as well as in `tbl_df` [@tibble]. They can also be `matrix` or `array`, with the constraint that a single unit holds for all elements. ## Discussion and conclusions The [units](https://cran.r-project.org/package=units) R package provides a new class, `units`, for numeric data with associated measurement units. Operations on objects of this class retain the unit metadata and provide automated dimensional analysis: dimensions are taken into consideration in computations and comparisons. Combining different units that are compatible triggers automatic unit conversion, derived units are automatically generated and simplified where possible, and meaningful error messages are given when a user tries to add objects with incompatible units. This verifies that computations are not only syntactically and numerically allowed, but also semantically, and in the case of physical units, physically allowed, which may support code verification and provenance tracking. Using this package may eliminate a whole class of potential scientific programming mistakes. Where the R packages [measurements](https://cran.r-project.org/package=measurements) and [NISTunits](https://cran.r-project.org/package=NISTunits) provide conversion between a fixed number of units, with the help of the udunits2 C library and unit database, R package [units](https://cran.r-project.org/package=units) handles arbitrarily complex derived units. By treating units as expressions it can derive, convert and simplify units. In addition, beyond the SI units packaged, [units](https://cran.r-project.org/package=units) handles user-defined units. Data in `units` vectors can be stored as columns in `data.frame` or `tbl_df` objects, and can be converted to and from `difftime`. When `units` objects have associated time and location information, they could be stored in spatial or spatio-temporal objects provided by [sp](https://cran.r-project.org/package=sp) or [spacetime](https://cran.r-project.org/package=spacetime) [@spacetime] as these store attribute data in `data.frame` slots, but for instance not in `zoo` [@zoo] or `xts` [@xts] objects, as these latter two set the class attribute of a vector or matrix. Despite all standardization efforts, units may still be ambiguous, or subject to interpretation. For instance for the duration of one year [NISTunits](https://cran.r-project.org/package=NISTunits) or [udunits2](https://cran.r-project.org/package=udunits2) give us an answer that depends on whether we want a common, leap, Gregorian, Julian, tropical or siderial year (@lang, see also `demo(year)`). This illustrates that those who apply unit conversion should be aware of possible pitfalls. Support for calendars in udunits seems not as well developed as in R. Future work includes extending packages that read external data from formats, databases or interfaces with support for measurement unit information into R, preserving the measurement unit information. Examples would be interfaces to HDF5 (e.g., [h5](https://cran.r-project.org/package=h5), @h5), [RNetCDF](https://cran.r-project.org/package=RNetCDF) [@RNetCDF] or [sos4R](https://cran.r-project.org/package=sos4R) [@sos4R]. It would be nice to see units of measurements propagate into units of regression coefficient estimates. # Acknowledgements We acknowledge three anonymous reviewers and the handling editor for their constructive comments, and Thomas Lin Pedersen for implementing the ggplot extensions in package `ggforce` that automatically add units to default ggplot axis labels. # References units/inst/doc/measurement_units_in_R.R0000644000176200001440000001147513547030276020016 0ustar liggesusers## ----echo=FALSE---------------------------------------------------------- knitr::opts_chunk$set(collapse = TRUE) ## ------------------------------------------------------------------------ temp_data = subset(read.table("647_Global_Temperature_Data_File.txt", header=TRUE)[1:2], Year >= 1960) temp_data$date = as.Date(paste0(temp_data$Year, "-01-01")) temp_data$time = as.POSIXct(temp_data$date) Sys.setenv(TZ="UTC") head(temp_data, 3) year_duration = diff(temp_data$date) mean(year_duration) ## ------------------------------------------------------------------------ year_duration %*% rep(1, length(year_duration)) / length(year_duration) ## ------------------------------------------------------------------------ coef(lm(Annual_Mean ~ date, temp_data)) coef(lm(Annual_Mean ~ time, temp_data)) ## ---- eval=requireNamespace("measurements", quietly=TRUE)---------------- library(measurements) conv_unit(2.54, "cm", "inch") conv_unit(c("101 44.32","3 19.453"), "deg_dec_min", "deg_min_sec") conv_unit(10, "cm_per_sec", "km_per_day") ## ---- eval=requireNamespace("measurements", quietly=TRUE)---------------- names(conv_unit_options) conv_unit_options$volume ## ---- eval=requireNamespace("measurements", quietly=TRUE)---------------- conv_dim(x = 100, x_unit = "m", trans = 3, trans_unit = "ft_per_sec", y_unit = "min") ## ---- eval=requireNamespace("NISTunits", quietly=TRUE)------------------- library(NISTunits) NISTwattPerSqrMeterTOwattPerSqrInch(1:5) ## ---- eval=requireNamespace("udunits2", quietly=TRUE)-------------------- library(udunits2) ls(2) ## ---- eval=requireNamespace("udunits2", quietly=TRUE)-------------------- ud.is.parseable("m/s") ud.is.parseable("q") ## ---- eval=requireNamespace("udunits2", quietly=TRUE)-------------------- ud.are.convertible("m/s", "km/h") ud.are.convertible("m/s", "s") ## ---- eval=requireNamespace("udunits2", quietly=TRUE)-------------------- ud.convert(1:3, "m/s", "km/h") ## ---- eval=requireNamespace("udunits2", quietly=TRUE)-------------------- ud.get.name("kg") ud.get.symbol("kilogram") ud.set.encoding("utf8") ## ---- eval=requireNamespace("udunits2", quietly=TRUE)-------------------- m100_a = paste(rep("m", 100), collapse = "*") dm100_b = "dm^100" ud.is.parseable(m100_a) ud.is.parseable(dm100_b) ud.are.convertible(m100_a, dm100_b) ## ------------------------------------------------------------------------ library(units) x = set_units(1:5, m/s) str(x) ## ------------------------------------------------------------------------ set_units(1:3, m/s^2) ## ------------------------------------------------------------------------ x = set_units(1:3, m/s) x + 2 * x ## ------------------------------------------------------------------------ (x = set_units(x, cm/s)) as.numeric(x) ## ------------------------------------------------------------------------ y = set_units(1:3, km/h) x + y y + x x == y c(y, x) ## ------------------------------------------------------------------------ x * y x^3 ## ------------------------------------------------------------------------ e = try(z <- x + x * y) attr(e, "condition")[[1]] ## ------------------------------------------------------------------------ methods(class = "units") ## ------------------------------------------------------------------------ a = set_units(1:10, m/s) b = set_units(1:10, h) a * b ustr1 = paste(rep("m", 101), collapse = "*") ustr2 = "dm^100" as_units(ustr1) / as_units(ustr2) ## ------------------------------------------------------------------------ set_units(1, m^5/s^4) ## ------------------------------------------------------------------------ as_units("m2 s-1") deparse_unit(set_units(1, m^2*s^-1)) ## ----fig=TRUE, height=3.8, width=7--------------------------------------- library(units) units_options(negative_power = TRUE) # initialize variables with units: mtcars$consumption = set_units(mtcars$mpg, mi/gallon) # "in" is also a reserved R keyword, and so needs back-quotes: mtcars$displacement = set_units(mtcars$disp, `in`^3) # convert to SI: mtcars$consumption = set_units(mtcars$consumption, km/l) mtcars$displacement = set_units(mtcars$displacement, cm^3) par(mar = par("mar") + c(0, .3, 0, 0)) with(mtcars, plot(1/displacement, 1/consumption)) ## ----fig=TRUE, height=3.8, width=7, eval=requireNamespace("ggforce", quietly=TRUE)---- library(ggforce) if (utils::packageVersion("ggplot2") > "2.2.1") ggplot(mtcars) + geom_point(aes(x = 1/displacement, y = 1/consumption)) ## ------------------------------------------------------------------------ (dt = diff(Sys.time() + c(0, 1, 1+60, 1+60+3600))) # class difftime (dt.u = as_units(dt)) identical(as_difftime(dt.u), dt) ## ------------------------------------------------------------------------ (t1 <- as_units(as.POSIXct("2017-08-20 17:03:00"))) (t2 <- as_units(as.POSIXct("2017-08-20 17:03:00"), "hours since 2017-08-20")) (d1 <- as_units(as.Date("2017-08-20"))) as.POSIXct(t1) as.Date(d1) units/inst/doc/units.Rmd0000644000176200001440000001555513230500577014761 0ustar liggesusers--- title: "Units of Measurement for R Vectors: an Introduction" output: html_document: toc: true theme: united vignette: > %\VignetteIndexEntry{Units of Measurement for R Vectors: an Introduction} %\VignetteEngine{knitr::rmarkdown} %\VignetteEncoding{UTF-8} --- ```{r echo=FALSE} knitr::opts_chunk$set(collapse = TRUE) ``` ```{r echo=FALSE} units:::units_options(negative_power = FALSE) ``` R has little support for physical measurement units. The exception is formed by time differences: time differences objects of class `difftime` have a `units` attribute that can be modified: ```{r} t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 class(d) units(d) d units(d) = "secs" d ``` We see here that the `units` method is used to retrieve and modify the unit of time differences. The `units` package generalizes this idea to other physical units, building upon the [udunits2](https://cran.r-project.org/package=udunits2) R package, which in turn is build upon the [udunits2](https://www.unidata.ucar.edu/software/udunits/) C library. The `udunits2` library provides the following operations: * validating whether an expression, such as `m/s` is a valid physical unit * verifying whether two units such as `m/s` and `km/h` are convertible * converting values between two convertible units * providing names and symbols for specific units * handle different character encodings (utf8, ascii, iso-8859-1 and latin1) The `units` R package uses R package [`udunits2`](https://cran.r-project.org/package=udunits2) to extend R with functionality for manipulating numeric vectors that have physical measurement units associated with them, in a similar way as `difftime` objects behave. ## Setting units, unit conversion Existing units are resolved from a database in the `units` package, called `ud_units`. We can see the first three elements of it by ```{r} library(units) ud_units[1:3] ``` We can set units to numerical values by `set_units`: ```{r} (a <- set_units(runif(10), m/s)) ``` the result, e.g. ```{r} set_units(10, m/s) ``` literally means "10 times 1 m divided by 1 s". In writing, the "1" values are omitted, and the multiplication is implicit. The `units` package comes with a list of over 3000 predefined units, ```{r} length(ud_units) ``` We can retrieve a single unit from the `ud_units` database by ```{r} with(ud_units, km/h) ``` ### Unit conversion When conversion is meaningful, such as hours to seconds or meters to kilometers, conversion can be done explicitly by setting the units of a vector ```{r} b = a units(b) <- with(ud_units, km/h) b ``` ## Basic manipulations ### Arithmetic operations Arithmetic operations verify units, and create new ones ```{r} a + a a * a a ^ 2 a ** -2 ``` and convert to the units of the first argument if necessary: ```{r} a + b # m/s + km/h -> m/s ``` Currently, powers are only supported for integer powers, so using `a ** 2.5` would result in an error. ### Unit simplification There are some basic simplification of units: ```{r} t <- with(ud_units, s) a * t ``` which also work when units need to be converted before they can be simplified: ```{r} t <- with(ud_units, min) a * t ``` Simplification to unit-less values gives the "1" as unit: ```{r} m <- with(ud_units, m) a * t / m ``` Allowed operations that require convertible units are `+`, `-`, `==`, `!=`, `<`, `>`, `<=`, `>=`. Operations that lead to new units are `*`, `/`, and the power operations `**` and `^`. ### Mathematical functions Mathematical operations allowed are: `abs`, `sign`, `floor`, `ceiling`, `trunc`, `round`, `signif`, `log`, `cumsum`, `cummax`, `cummin`. ```{r} signif(a ** 2 / 3, 3) cumsum(a) log(a) # base defaults to exp(1) log(a, base = 10) log(a, base = 2) ``` ### Summary functions Summary functions `sum`, `min`, `max`, and `range` are allowed: ```{r} sum(a) min(a) max(a) range(a) with(ud_units, min(m/s, km/h)) # converts to first unit: ``` ### Printing Following `difftime`, printing behaves differently for length-one vectors: ```{r} a a[1] ``` ### Subsetting The usual subsetting rules work: ```{r} a[2:5] a[-(1:9)] ``` ### Concatenation ```{r} c(a,a) ``` concatenation converts to the units of the first argument, if necessary: ```{r} c(a,b) # m/s, km/h -> m/s c(b,a) # km/h, m/s -> km/h ``` ## Conversion to/from `difftime` From `difftime` to `units`: ```{r} t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 (du = as_units(d)) ``` vice versa: ```{r} (dt = as_difftime(du)) class(dt) ``` ## units in `matrix` objects ```{r} set_units(matrix(1:4,2,2), m/s) set_units(matrix(1:4,2,2), m/s * m/s) ``` but ```{r} set_units(matrix(1:4,2,2), m/s) %*% set_units(4:3, m/s) ``` strips units. ## units objects in `data.frame`s units in `data.frame` objects are printed, but do not appear in `summary`:. ```{r} set.seed(131) d <- data.frame(x = runif(4), y = set_units(runif(4), s), z = set_units(1:4, m/s)) d summary(d) d$yz = with(d, y * z) d d[1, "yz"] ``` ## formatting Units are often written in the form `m2 s-1`, for square meter per second. This can be defined as unit, and also parsed by `as_units`: ```{r} (x = 1:10 * as_units("m2 s-1")) ``` udunits understands such string, and can convert them ```{r} y = 1:10 * with(ud_units, m^2/s) x + y ``` Printing units in this form is done by ```{r} deparse_unit(x) ``` ## plotting Base scatter plots and histograms support automatic unit placement in axis labels. In the following example we first convert to SI units. (Unit `in` needs a bit special treatment, because `in` is a reserved word in R.) ```{r fig=TRUE} mar = par("mar") + c(0, .3, 0, 0) displacement = mtcars$disp * ud_units[["in"]]^3 units(displacement) = with(ud_units, cm^3) weight = mtcars$wt * 1000 * with(ud_units, lb) units(weight) = with(ud_units, kg) par(mar = mar) plot(weight, displacement) ``` We can change grouping symbols from `[ ]` into `( )`: ```{r} units_options(group = c("(", ")") ) # parenthesis instead of square brackets par(mar = mar) plot(weight, displacement) ``` We can also remove grouping symbols, increase space between variable name and unit by: ```{r} units_options(sep = c("~~~", "~"), group = c("", "")) # no brackets; extra space par(mar = mar) plot(weight, displacement) ``` More complex units can be plotted either with negative powers, or as divisions, by modifying one of `units`'s global options using `units_options`: ```{r} gallon = as_units("gallon") consumption = mtcars$mpg * with(ud_units, mi/gallon) units(consumption) = with(ud_units, km/l) par(mar = mar) plot(displacement, consumption) # division in consumption units_options(negative_power = TRUE) # division becomes ^-1 plot(displacement, consumption) # division in consumption ``` As usual, units modify automatically in expressions: ```{r} units_options(negative_power = TRUE) # division becomes ^-1 par(mar = mar) plot(displacement, consumption) plot(1/displacement, 1/consumption) ``` ```{r echo=FALSE} units_options(negative_power = FALSE) # division becomes / ``` units/inst/doc/measurement_units_in_R.html0000644000176200001440000454627013547030300020557 0ustar liggesusers Measurement units in R

This vignette is identical to E. Pebesma, Mailund, and Hiebert (2016), except for two changes:

  • it has been synchronized with updates to the units package
  • it has been converted to R-markdown

Abstract

We briefly review SI units, and discuss R packages that deal with measurement units, their compatibility and conversion. Built upon udunits2 and the UNIDATA udunits library, we introduce the package units that provides a class for maintaining unit metadata. When used in expression, it automatically converts units, and simplifies units of results when possible; in case of incompatible units, errors are raised. The class flexibly allows expansion beyond predefined units. Using units may eliminate a whole class of potential scientific programming mistakes. We discuss the potential and limitations of computing with explicit units.

Introduction

Two quotes from Cobb and Moore (1997)Data are not just numbers, they are numbers with a context and in data analysis, context provides meaning – illustrate that for a data analysis to be meaningful, knowledge of the data’s context is needed. Pragmatic aspects of this context include who collected or generated the data, how this was done, and for which purpose (Scheider et al. 2016); semantic aspects concern what the data represents: which aspect of the world do the data refer to, when and where were they measured, and what a value of 1 means.

R does allow for keeping some context with data, for instance

  • data.frame columns must have and list elements may have names that can be used to describe context, using freetext
  • matrix or array objects may have dimnames
  • for variables of class factor or ordered, levels may indicate, using freetext, the categories of nominal or ordinal variables
  • POSIXt and Date objects specify how numbers should be interpreted as time or date, with fixed units (second and day, respectively) and origin (Jan 1, 1970, 00:00 UTC)
  • difftime objects specify how time duration can be represented by numbers, with flexible units (secs, mins, hours, days, weeks); lubridate (Grolemund and Wickham 2011) extends some of this functionality.

Furthermore, if spatial objects as defined in package sp (E. Pebesma and Bivand 2005) have a proper coordinate reference system set, they can be transformed to other datums, or converted to various flat (projected) representations of the Earth (Iliffe and Lott 2008).

In many cases however, R drops contextual information. As an example, we look at annual global land-ocean temperature index (from http://climate.nasa.gov/vital-signs/global-temperature/) since 1960:

temp_data = subset(read.table("647_Global_Temperature_Data_File.txt", 
    header=TRUE)[1:2], Year >= 1960)
temp_data$date = as.Date(paste0(temp_data$Year, "-01-01"))
temp_data$time = as.POSIXct(temp_data$date)
Sys.setenv(TZ="UTC")
head(temp_data, 3)
##    Year Annual_Mean       date       time
## 81 1960       -0.03 1960-01-01 1960-01-01
## 82 1961        0.05 1961-01-01 1961-01-01
## 83 1962        0.02 1962-01-01 1962-01-01
year_duration = diff(temp_data$date)
mean(year_duration)
## Time difference of 365.2545 days

Here, the time difference units are reported for the difftime object year_duration, but if we would use it in a linear algebra operation

year_duration %*% rep(1, length(year_duration)) / length(year_duration)
##          [,1]
## [1,] 365.2545

the unit is dropped. Similarly, for linear regression coefficients we see

coef(lm(Annual_Mean ~ date, temp_data))
##  (Intercept)         date 
## 1.833671e-02 4.364763e-05
coef(lm(Annual_Mean ~ time, temp_data))
##  (Intercept)         time 
## 1.833671e-02 5.051809e-10

where the unit of change is in degrees Celsius but either per day (date) or per second (time). For purely mathematical manipulations, R often strips context from numbers when it is carried in attributes, the linear algebra routines being a prime example.

Most variables are somehow attributed with information about their units, which specify what the value 1 of this variable represents. This may be counts of something, e.g. 1 apple, but it may also refer to some physical unit, such as distance in meter. This article discusses how strong unit support can be introduced in R.

SI

The BIPM (Bureau International des Poids et Mesures) is “the intergovernmental organization through which Member States act together on matters related to measurement science and measurement standards. Its recommended practical system of units of measurement is the International System of Units (Syst`{e}me International d’Unit'{e}s, with the international abbreviation SI) (http://www.bipm.org/en/measurement-units/)”.

International Bureau of Weights and Measures, Taylor, and Thompson (2001) describe the SI units, where, briefly, SI units

  • consist of seven base units (length, mass, time & duration, electric current, thermodynamic temperature, amount of substance, and luminous intensity), each with a name and abbreviation (see table below)
  • consist of derived units that are formed by products of powers of base units, such as m/s\(^2\), many of which have special names and symbols (e.g. angle: 1 rad = 1 m/m; force: 1 N = 1 m kg s\(^{-2}\))
  • consist of coherent derived units when derived units include no numerical factors other than one (with the exception of kg; as a base unit, kg can be part of coherent derived units); an example of a coherent derived unit is 1 watt = 1 joule per 1 second,
  • may contain SI prefixes (k = kilo for \(10^3\), m = milli for \(10^{-3}\), etc.)
  • contain special quantities where units disappear (e.g., m/m) or have the nature of a count, in which cases the unit is 1.

base quantities, SI units and their symbols (from International Bureau of Weights and Measures, Taylor, and Thompson (2001), p. 23):

Base quantity SI base unit
Name Symbol Name Symbol
length \(l,x,r,\) etc. meter m
mass \(m\) kilogram kg
time, duration \(t\) second s
electric current \(I, i\) ampere A
thermodynamic temperature \(T\) kelvin K
amount of substance \(n\) mole mol
luminous intensity \(I_v\) candela cd

UNIDATA’s udunits library and the udunits2 R package

Udunits, developed by UCAR/UNIDATA, advertises itself on its web page as: “The udunits package supports units of physical quantities. Its C library provides for arithmetic manipulation of units and for conversion of numeric values between compatible units. The package contains an extensive unit database, which is in XML format and user-extendable.

The R package udunits2 (Hiebert 2015) provides a low-level R interface to the most important functions in the udunits2 C library.

The functions provided by udunits2 are

library(udunits2)
## udunits system database read
ls(2)
## [1] "ud.are.convertible"  "ud.convert"          "ud.get.name"        
## [4] "ud.get.symbol"       "ud.have.unit.system" "ud.is.parseable"    
## [7] "ud.set.encoding"

Dropping the ud prefix, is.parseable verifies whether a unit is parseable

ud.is.parseable("m/s")
## [1] TRUE
ud.is.parseable("q")
## [1] FALSE

are.convertible specifies whether two units are convertible

ud.are.convertible("m/s", "km/h")
## [1] TRUE
ud.are.convertible("m/s", "s")
## [1] FALSE

convert converts units that are convertible, and throws an error otherwise

ud.convert(1:3, "m/s", "km/h")
## [1]  3.6  7.2 10.8

and get.name, get.symbol and set.encoding get name, get symbol or modify encoding of the character unit arguments.

ud.get.name("kg")
## [1] "kilogram"
ud.get.symbol("kilogram")
## [1] "kg"
ud.set.encoding("utf8")
## NULL

Unlike the measurements and NISTunits, udunits2 parses units as expressions, and bases its logic upon the convertibility of expressions, rather than the comparison of fixed strings:

m100_a = paste(rep("m", 100), collapse = "*")
dm100_b = "dm^100"
ud.is.parseable(m100_a)
## [1] TRUE
ud.is.parseable(dm100_b)
## [1] TRUE
ud.are.convertible(m100_a, dm100_b)
## [1] TRUE

This has the advantage that through complex computations, intermediate objects can have units that are arbitrarily complex, and that can potentially be simplified later on. It also means that the package practically supports an unlimited amount of derived units.

Udunits versus the Unified Code for Units of Measure (UCUM)

Another set of encodings for measurement units is the Unified Code for Units of Measure (UCUM, Schadow and McDonald (2009)). A dedicated web site describes the details of the differences between udunits and UCUM, and provides a conversion service between the two encoding sets.

The UCUM website refers to some Java implementations, but some of the links seem to be dead. UCUM is the preferred encoding for standards from the Open Geospatial Consortium. udunits on the other hand is the units standard of choice by the climate science community, and is adopted by the CF (Climate and Forecast) conventions, which mostly uses NetCDF. NetCDF (Rew and Davis 1990) is a binary data format that is widely used for atmospheric and climate model predictions.

The udunits library is a C library that has strong support from UNIDATA, and we decided to build our developments on this, rather than on Java implementations of UCUM with a less clear provenance.

Handling data with units in R: the units package

The units package builds units objects from scratch, e.g. where

library(units)
## udunits system database from /usr/share/xml/udunits
x = set_units(1:5, m/s)
str(x)
## Object of class units:
##  int [1:5] 1 2 3 4 5
##  - attr(*, "units")=List of 2
##   ..$ numerator  : chr "m"
##   ..$ denominator: chr "s"
##   ..- attr(*, "class")= chr "symbolic_units"

represents speed values in m/s. The units m and s are retrieved from the ud_units database, which is part of units, and was derived from the xml units database that is part of udunits2 C library.

Units can be used in arbitrary R expressions like

set_units(1:3, m/s^2)
## Units: [m/s^2]
## [1] 1 2 3

Several manipulations with units objects will now be illustrated. Manipulations that do not involve unit conversion are for instance addition:

x = set_units(1:3, m/s)
x + 2 * x
## Units: [m/s]
## [1] 3 6 9

Explicit unit conversion is done by assigning new units:

(x = set_units(x, cm/s))
## Units: [cm/s]
## [1] 100 200 300
as.numeric(x)
## [1] 100 200 300

similar to the behaviour of difftime objects, this modifies the numeric values without modifying their meaning (what the numbers refer to).

When mixing units in sums, comparisons or concatenation, units are automatically converted to those of the first argument:

y = set_units(1:3, km/h)
x + y
## Units: [cm/s]
## [1] 127.7778 255.5556 383.3333
y + x
## Units: [km/h]
## [1]  4.6  9.2 13.8
x == y
## [1] FALSE FALSE FALSE
c(y, x)
## Units: [km/h]
## [1]  1.0  2.0  3.0  3.6  7.2 10.8

where c(y, x) concatenates y and x after converting x to the units of y. Derived units are created where appropriate:

x * y
## Units: [cm*km/h/s]
## [1] 100 400 900
x^3
## Units: [cm^3/s^3]
## [1] 1.0e+06 8.0e+06 2.7e+07

and meaningful error messages appear when units are not compatible:

e = try(z <- x + x * y)
## Error : cannot convert cm*km/h/s into cm/s
attr(e, "condition")[[1]]
## [1] "cannot convert cm*km/h/s into cm/s"

The full set of methods and method groups for units objects is shown by

methods(class = "units")
##  [1] Math          Ops           Summary       [             [[           
##  [6] all.equal     as.Date       as.POSIXct    as.data.frame as.list      
## [11] as_units      boxplot       c             diff          drop_units   
## [16] format        hist          log10         log2          mean         
## [21] median        mixed_units   plot          print         quantile     
## [26] rep           seq           set_units     str           summary      
## [31] units         units<-       weighted.mean
## see '?methods' for accessing help and source code

where the method groups

  • Ops include operations that require compatible units, converting when necessary (+, -, ==, !=, <, >, <=, >=), and operations that create new units (*, /, ^ and **),
  • Math include abs, sign, floor, ceiling, trunc, round, signif, log, cumsum, cummax, cummin, and
  • Summary include sum, min, max and range, and all convert to the unit of the first argument.

When possible, new units are simplified:

a = set_units(1:10, m/s)
b = set_units(1:10, h)
a * b
## Units: [m]
##  [1]   3600  14400  32400  57600  90000 129600 176400 230400 291600 360000
ustr1 = paste(rep("m", 101), collapse = "*")
ustr2 = "dm^100"
as_units(ustr1) / as_units(ustr2)
## 1e+100 [m]

Units are printed as simple R expressions, e.g.

set_units(1, m^5/s^4)
## 1 [m^5/s^4]

Another way to print units commonly seen in Climate and Forecast Conventions is m2 s-1 for m\(^2\)/s. These are not R expressions, but they can be parsed by as_units, and created by deparse_unit:

as_units("m2 s-1")
## 1 [m^2/s]
deparse_unit(set_units(1, m^2*s^-1))
## [1] "m2 s-1"

The plot and hist methods add units to default axis labels, an example is shown in the following figures. For ggplot2 plots (Wickham 2009), automatic unit placement in default axis label is provided by package ggforce (Pedersen 2016); demo(ggforce) gives an example.

library(units)
units_options(negative_power = TRUE)
# initialize variables with units:
mtcars$consumption = set_units(mtcars$mpg, mi/gallon)
# "in" is also a reserved R keyword, and so needs back-quotes:
mtcars$displacement = set_units(mtcars$disp, `in`^3)
# convert to SI:
mtcars$consumption = set_units(mtcars$consumption, km/l)
mtcars$displacement = set_units(mtcars$displacement, cm^3)
par(mar = par("mar") + c(0, .3, 0, 0))
with(mtcars, plot(1/displacement, 1/consumption))

library(ggforce)
## Loading required package: ggplot2
if (utils::packageVersion("ggplot2") > "2.2.1")
  ggplot(mtcars) + geom_point(aes(x = 1/displacement, y = 1/consumption))

Automatic conversion between units and difftime is provided:

(dt = diff(Sys.time() + c(0, 1, 1+60, 1+60+3600))) # class difftime
## Time differences in secs
## [1]    1   60 3600
(dt.u = as_units(dt))
## Units: [s]
## [1]    1   60 3600
identical(as_difftime(dt.u), dt)
## [1] TRUE

as well as to and from POSIXct or Date:

(t1 <- as_units(as.POSIXct("2017-08-20 17:03:00")))
## 1503248580 [(seconds since 1970-01-01 00:00:00 +00:00)]
(t2 <- as_units(as.POSIXct("2017-08-20 17:03:00"), "hours since 2017-08-20"))
## 17.05 [(hours since 2017-08-20)]
(d1 <- as_units(as.Date("2017-08-20")))
## 17398 [(days since 1970-01-01)]
as.POSIXct(t1)
## [1] "2017-08-20 17:03:00 UTC"
as.Date(d1)
## [1] "2017-08-20"

Objects of class units can be used as columns in data.frame objects, as well as in tbl_df (Wickham, Francois, and Müller 2016). They can also be matrix or array, with the constraint that a single unit holds for all elements.

Discussion and conclusions

The units R package provides a new class, units, for numeric data with associated measurement units. Operations on objects of this class retain the unit metadata and provide automated dimensional analysis: dimensions are taken into consideration in computations and comparisons. Combining different units that are compatible triggers automatic unit conversion, derived units are automatically generated and simplified where possible, and meaningful error messages are given when a user tries to add objects with incompatible units. This verifies that computations are not only syntactically and numerically allowed, but also semantically, and in the case of physical units, physically allowed, which may support code verification and provenance tracking. Using this package may eliminate a whole class of potential scientific programming mistakes.

Where the R packages measurements and NISTunits provide conversion between a fixed number of units, with the help of the udunits2 C library and unit database, R package units handles arbitrarily complex derived units. By treating units as expressions it can derive, convert and simplify units. In addition, beyond the SI units packaged, units handles user-defined units.

Data in units vectors can be stored as columns in data.frame or tbl_df objects, and can be converted to and from difftime. When units objects have associated time and location information, they could be stored in spatial or spatio-temporal objects provided by sp or spacetime (E. Pebesma 2012) as these store attribute data in data.frame slots, but for instance not in zoo (Zeileis and Grothendieck 2005) or xts (Ryan and Ulrich 2014) objects, as these latter two set the class attribute of a vector or matrix.

Despite all standardization efforts, units may still be ambiguous, or subject to interpretation. For instance for the duration of one year NISTunits or udunits2 give us an answer that depends on whether we want a common, leap, Gregorian, Julian, tropical or siderial year (Lang (2006), see also demo(year)). This illustrates that those who apply unit conversion should be aware of possible pitfalls. Support for calendars in udunits seems not as well developed as in R.

Future work includes extending packages that read external data from formats, databases or interfaces with support for measurement unit information into R, preserving the measurement unit information. Examples would be interfaces to HDF5 (e.g., h5, Annau (2016)), RNetCDF (Michna and Woods 2016) or sos4R (Nüst, Stasch, and Pebesma 2011). It would be nice to see units of measurements propagate into units of regression coefficient estimates.

Acknowledgements

We acknowledge three anonymous reviewers and the handling editor for their constructive comments, and Thomas Lin Pedersen for implementing the ggplot extensions in package ggforce that automatically add units to default ggplot axis labels.

References

Annau, Mario. 2016. H5: Interface to the ’Hdf5’ Library. https://CRAN.R-project.org/package=h5.

Birk, Matthew A. 2016. Measurements: Tools for Units of Measurement. https://CRAN.R-project.org/package=measurements.

Cobb, George W., and David S. Moore. 1997. “Mathematics, Statistics, and Teaching.” American Mathematical Monthly, 801–23.

Gama, Jose. 2014. NISTunits: Fundamental Physical Constants and Unit Conversions from Nist. https://CRAN.R-project.org/package=NISTunits.

Grolemund, Garrett, and Hadley Wickham. 2011. “Dates and Times Made Easy with Lubridate.” Journal of Statistical Software 40 (1): 1–25. doi:10.18637/jss.v040.i03.

Hiebert, James. 2015. Udunits2: Udunits-2 Bindings for R.

Iliffe, Jonathan, and Roger Lott. 2008. Datums and Map Projections: For Remote Sensing, Gis and Surveying. CRC Inc.

International Bureau of Weights and Measures, Barry N Taylor, and Ambler Thompson. 2001. “The International System of Units (SI).” US Department of Commerce, Technology Administration, National Institute of Standards; Technology.

Lang, K.R. 2006. Astrophysical Formulae Volume Ii: Space, Time, Matter and Cosmology, 3rd Edition 1999. 2nd Printing. Springer.

Michna, Pavel, and Milton Woods. 2016. RNetCDF: Interface to Netcdf Datasets. https://CRAN.R-project.org/package=RNetCDF.

Nüst, D., C. Stasch, and E. J. Pebesma. 2011. “Connecting R to the Sensor Web.” In, edited by S. Geertman, W. Reinhardt, and F. Toppen, 227–46. Lecture Notes in Geoinformation and Cartography. Springer.

Pebesma, Edzer. 2012. “Spacetime: Spatio-Temporal Data in R.” Journal of Statistical Software 51 (1): 1–30. doi:10.18637/jss.v051.i07.

Pebesma, Edzer, and Roger Bivand. 2005. “Classes and Methods for Spatial Data in R.” R News 5 (2): 9–13. https://cran.r-project.org/doc/Rnews/.

Pebesma, Edzer, Thomas Mailund, and James Hiebert. 2016. “Measurement Units in R.” The R Journal 8 (2): 486–94. doi:10.32614/RJ-2016-061.

Pedersen, Thomas Lin. 2016. Ggforce: Accelerating ’Ggplot2’. https://CRAN.R-project.org/package=ggforce.

Rew, Russ, and Glenn Davis. 1990. “NetCDF: An Interface for Scientific Data Access.” IEEE Computer Graphics and Applications 10 (4). IEEE: 76–82.

Ryan, Jeffrey A., and Joshua M. Ulrich. 2014. Xts: EXtensible Time Series. https://CRAN.R-project.org/package=xts.

Schadow, Gunther, and Clement J McDonald. 2009. “The Unified Code for Units of Measure.” Regenstrief Institute and UCUM Organization: Indianapolis, IN, USA.

Scheider, Simon, Benedikt Gräler, Edzer Pebesma, and Christoph Stasch. 2016. “Modeling Spatiotemporal Information Generation.” International Journal of Geographical Information Science 30 (10): 1980–2008. http://dx.doi.org/10.1080/13658816.2016.1151520.

Wickham, Hadley. 2009. Ggplot2: Elegant Graphics for Data Analysis. Springer-Verlag New York.

Wickham, Hadley, Romain Francois, and Kirill Müller. 2016. Tibble: Simple Data Frames. https://CRAN.R-project.org/package=tibble.

Zeileis, Achim, and Gabor Grothendieck. 2005. “Zoo: S3 Infrastructure for Regular and Irregular Time Series.” Journal of Statistical Software 14 (6): 1–27. doi:10.18637/jss.v014.i06.

units/inst/doc/units.R0000644000176200001440000001140713547030301014422 0ustar liggesusers## ----echo=FALSE---------------------------------------------------------- knitr::opts_chunk$set(collapse = TRUE) ## ----echo=FALSE---------------------------------------------------------- units:::units_options(negative_power = FALSE) ## ------------------------------------------------------------------------ t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 class(d) units(d) d units(d) = "secs" d ## ------------------------------------------------------------------------ library(units) ud_units[1:3] ## ------------------------------------------------------------------------ (a <- set_units(runif(10), m/s)) ## ------------------------------------------------------------------------ set_units(10, m/s) ## ------------------------------------------------------------------------ length(ud_units) ## ------------------------------------------------------------------------ with(ud_units, km/h) ## ------------------------------------------------------------------------ b = a units(b) <- with(ud_units, km/h) b ## ------------------------------------------------------------------------ a + a a * a a ^ 2 a ** -2 ## ------------------------------------------------------------------------ a + b # m/s + km/h -> m/s ## ------------------------------------------------------------------------ t <- with(ud_units, s) a * t ## ------------------------------------------------------------------------ t <- with(ud_units, min) a * t ## ------------------------------------------------------------------------ m <- with(ud_units, m) a * t / m ## ------------------------------------------------------------------------ signif(a ** 2 / 3, 3) cumsum(a) log(a) # base defaults to exp(1) log(a, base = 10) log(a, base = 2) ## ------------------------------------------------------------------------ sum(a) min(a) max(a) range(a) with(ud_units, min(m/s, km/h)) # converts to first unit: ## ------------------------------------------------------------------------ a a[1] ## ------------------------------------------------------------------------ a[2:5] a[-(1:9)] ## ------------------------------------------------------------------------ c(a,a) ## ------------------------------------------------------------------------ c(a,b) # m/s, km/h -> m/s c(b,a) # km/h, m/s -> km/h ## ------------------------------------------------------------------------ t1 = Sys.time() t2 = t1 + 3600 d = t2 - t1 (du = as_units(d)) ## ------------------------------------------------------------------------ (dt = as_difftime(du)) class(dt) ## ------------------------------------------------------------------------ set_units(matrix(1:4,2,2), m/s) set_units(matrix(1:4,2,2), m/s * m/s) ## ------------------------------------------------------------------------ set_units(matrix(1:4,2,2), m/s) %*% set_units(4:3, m/s) ## ------------------------------------------------------------------------ set.seed(131) d <- data.frame(x = runif(4), y = set_units(runif(4), s), z = set_units(1:4, m/s)) d summary(d) d$yz = with(d, y * z) d d[1, "yz"] ## ------------------------------------------------------------------------ (x = 1:10 * as_units("m2 s-1")) ## ------------------------------------------------------------------------ y = 1:10 * with(ud_units, m^2/s) x + y ## ------------------------------------------------------------------------ deparse_unit(x) ## ----fig=TRUE------------------------------------------------------------ mar = par("mar") + c(0, .3, 0, 0) displacement = mtcars$disp * ud_units[["in"]]^3 units(displacement) = with(ud_units, cm^3) weight = mtcars$wt * 1000 * with(ud_units, lb) units(weight) = with(ud_units, kg) par(mar = mar) plot(weight, displacement) ## ------------------------------------------------------------------------ units_options(group = c("(", ")") ) # parenthesis instead of square brackets par(mar = mar) plot(weight, displacement) ## ------------------------------------------------------------------------ units_options(sep = c("~~~", "~"), group = c("", "")) # no brackets; extra space par(mar = mar) plot(weight, displacement) ## ------------------------------------------------------------------------ gallon = as_units("gallon") consumption = mtcars$mpg * with(ud_units, mi/gallon) units(consumption) = with(ud_units, km/l) par(mar = mar) plot(displacement, consumption) # division in consumption units_options(negative_power = TRUE) # division becomes ^-1 plot(displacement, consumption) # division in consumption ## ------------------------------------------------------------------------ units_options(negative_power = TRUE) # division becomes ^-1 par(mar = mar) plot(displacement, consumption) plot(1/displacement, 1/consumption) ## ----echo=FALSE---------------------------------------------------------- units_options(negative_power = FALSE) # division becomes / units/inst/doc/units.html0000644000176200001440000377311313547030302015202 0ustar liggesusers Units of Measurement for R Vectors: an Introduction

R has little support for physical measurement units. The exception is formed by time differences: time differences objects of class difftime have a units attribute that can be modified:

t1 = Sys.time() 
t2 = t1 + 3600 
d = t2 - t1
class(d)
## [1] "difftime"
units(d)
## [1] "hours"
d
## Time difference of 1 hours
units(d) = "secs"
d
## Time difference of 3600 secs

We see here that the units method is used to retrieve and modify the unit of time differences.

The units package generalizes this idea to other physical units, building upon the udunits2 R package, which in turn is build upon the udunits2 C library. The udunits2 library provides the following operations:

  • validating whether an expression, such as m/s is a valid physical unit
  • verifying whether two units such as m/s and km/h are convertible
  • converting values between two convertible units
  • providing names and symbols for specific units
  • handle different character encodings (utf8, ascii, iso-8859-1 and latin1)

The units R package uses R package udunits2 to extend R with functionality for manipulating numeric vectors that have physical measurement units associated with them, in a similar way as difftime objects behave.

Setting units, unit conversion

Existing units are resolved from a database in the units package, called ud_units. We can see the first three elements of it by

library(units)
ud_units[1:3]
## $m
## 1 [m]
## 
## $kg
## 1 [kg]
## 
## $s
## 1 [s]

We can set units to numerical values by set_units:

(a <- set_units(runif(10),  m/s))
## Units: [m/s]
##  [1] 0.36127025 0.43905581 0.99845243 0.19955417 0.27954245 0.86322245
##  [7] 0.83101044 0.08345579 0.13455004 0.29473114

the result, e.g.

set_units(10, m/s)
## 10 [m/s]

literally means “10 times 1 m divided by 1 s”. In writing, the “1” values are omitted, and the multiplication is implicit.

The units package comes with a list of over 3000 predefined units,

length(ud_units)
## [1] 3248

We can retrieve a single unit from the ud_units database by

with(ud_units, km/h)
## 1 [km/h]

Unit conversion

When conversion is meaningful, such as hours to seconds or meters to kilometers, conversion can be done explicitly by setting the units of a vector

b = a
units(b) <- with(ud_units, km/h)
b
## Units: [km/h]
##  [1] 1.3005729 1.5806009 3.5944287 0.7183950 1.0063528 3.1076008 2.9916376
##  [8] 0.3004408 0.4843802 1.0610321

Basic manipulations

Arithmetic operations

Arithmetic operations verify units, and create new ones

a + a
## Units: [m/s]
##  [1] 0.7225405 0.8781116 1.9969049 0.3991083 0.5590849 1.7264449 1.6620209
##  [8] 0.1669116 0.2691001 0.5894623
a * a
## Units: [m^2/s^2]
##  [1] 0.130516192 0.192770002 0.996907248 0.039821869 0.078143983
##  [6] 0.745153000 0.690578352 0.006964869 0.018103714 0.086866447
a ^ 2
## Units: [m^2/s^2]
##  [1] 0.130516192 0.192770002 0.996907248 0.039821869 0.078143983
##  [6] 0.745153000 0.690578352 0.006964869 0.018103714 0.086866447
a ** -2
## Units: [s^2/m^2]
##  [1]   7.661885   5.187529   1.003102  25.111830  12.796891   1.342006
##  [7]   1.448062 143.577723  55.237283  11.511925

and convert to the units of the first argument if necessary:

a + b # m/s + km/h -> m/s
## Units: [m/s]
##  [1] 0.7225405 0.8781116 1.9969049 0.3991083 0.5590849 1.7264449 1.6620209
##  [8] 0.1669116 0.2691001 0.5894623

Currently, powers are only supported for integer powers, so using a ** 2.5 would result in an error.

Unit simplification

There are some basic simplification of units:

t <- with(ud_units, s)
a * t
## Units: [m]
##  [1] 0.36127025 0.43905581 0.99845243 0.19955417 0.27954245 0.86322245
##  [7] 0.83101044 0.08345579 0.13455004 0.29473114

which also work when units need to be converted before they can be simplified:

t <- with(ud_units, min)
a * t
## Units: [m]
##  [1] 21.676215 26.343348 59.907146 11.973250 16.772547 51.793347 49.860626
##  [8]  5.007347  8.073003 17.683869

Simplification to unit-less values gives the “1” as unit:

m <- with(ud_units, m)
a * t / m
## Units: [1]
##  [1] 21.676215 26.343348 59.907146 11.973250 16.772547 51.793347 49.860626
##  [8]  5.007347  8.073003 17.683869

Allowed operations that require convertible units are +, -, ==, !=, <, >, <=, >=. Operations that lead to new units are *, /, and the power operations ** and ^.

Mathematical functions

Mathematical operations allowed are: abs, sign, floor, ceiling, trunc, round, signif, log, cumsum, cummax, cummin.

signif(a ** 2 / 3, 3)
## Units: [m^2/s^2]
##  [1] 0.04350 0.06430 0.33200 0.01330 0.02600 0.24800 0.23000 0.00232
##  [9] 0.00603 0.02900
cumsum(a)
## Units: [m/s]
##  [1] 0.3612702 0.8003261 1.7987785 1.9983327 2.2778751 3.1410976 3.9721080
##  [8] 4.0555638 4.1901138 4.4848450
log(a) # base defaults to exp(1)
## Units: [(ln(re 1 m.s-1))]
##  [1] -1.018128993 -0.823128750 -0.001548772 -1.611669527 -1.274601109
##  [6] -0.147082856 -0.185112920 -2.483438256 -2.005819074 -1.221691717
log(a, base = 10)
## Units: [(lg(re 1 m.s-1))]
##  [1] -0.4421678034 -0.3574802740 -0.0006726233 -0.6999391823 -0.5535522284
##  [6] -0.0638772729 -0.0803935198 -1.0785435307 -0.8711161556 -0.5305739714
log(a, base = 2)
## Units: [(lb(re 1 m.s-1))]
##  [1] -1.468849649 -1.187523766 -0.002234406 -2.325147635 -1.838860699
##  [6] -0.212195708 -0.267061492 -3.582844056 -2.893785231 -1.762528582

Summary functions

Summary functions sum, min, max, and range are allowed:

sum(a)
## 4.484845 [m/s]
min(a)
## 0.08345579 [m/s]
max(a)
## 0.9984524 [m/s]
range(a)
## Units: [m/s]
## [1] 0.08345579 0.99845243
with(ud_units, min(m/s, km/h)) # converts to first unit:
## 0.2777778 [m/s]

Printing

Following difftime, printing behaves differently for length-one vectors:

a
## Units: [m/s]
##  [1] 0.36127025 0.43905581 0.99845243 0.19955417 0.27954245 0.86322245
##  [7] 0.83101044 0.08345579 0.13455004 0.29473114
a[1]
## 0.3612702 [m/s]

Subsetting

The usual subsetting rules work:

a[2:5]
## Units: [m/s]
## [1] 0.4390558 0.9984524 0.1995542 0.2795425
a[-(1:9)]
## 0.2947311 [m/s]

Concatenation

c(a,a)
## Units: [m/s]
##  [1] 0.36127025 0.43905581 0.99845243 0.19955417 0.27954245 0.86322245
##  [7] 0.83101044 0.08345579 0.13455004 0.29473114 0.36127025 0.43905581
## [13] 0.99845243 0.19955417 0.27954245 0.86322245 0.83101044 0.08345579
## [19] 0.13455004 0.29473114

concatenation converts to the units of the first argument, if necessary:

c(a,b) # m/s, km/h -> m/s
## Units: [m/s]
##  [1] 0.36127025 0.43905581 0.99845243 0.19955417 0.27954245 0.86322245
##  [7] 0.83101044 0.08345579 0.13455004 0.29473114 0.36127025 0.43905581
## [13] 0.99845243 0.19955417 0.27954245 0.86322245 0.83101044 0.08345579
## [19] 0.13455004 0.29473114
c(b,a) # km/h, m/s -> km/h
## Units: [km/h]
##  [1] 1.3005729 1.5806009 3.5944287 0.7183950 1.0063528 3.1076008 2.9916376
##  [8] 0.3004408 0.4843802 1.0610321 1.3005729 1.5806009 3.5944287 0.7183950
## [15] 1.0063528 3.1076008 2.9916376 0.3004408 0.4843802 1.0610321

Conversion to/from difftime

From difftime to units:

t1 = Sys.time() 
t2 = t1 + 3600 
d = t2 - t1
(du = as_units(d))
## 1 [h]

vice versa:

(dt = as_difftime(du))
## Time difference of 1 hours
class(dt)
## [1] "difftime"

units in matrix objects

set_units(matrix(1:4,2,2), m/s)
## Units: [m/s]
##      [,1] [,2]
## [1,]    1    3
## [2,]    2    4
set_units(matrix(1:4,2,2), m/s * m/s)
## Units: [m^2/s^2]
##      [,1] [,2]
## [1,]    1    3
## [2,]    2    4

but

set_units(matrix(1:4,2,2), m/s) %*% set_units(4:3, m/s)
##      [,1]
## [1,]   13
## [2,]   20

strips units.

units objects in data.frames

units in data.frame objects are printed, but do not appear in summary:.

set.seed(131)
d <- data.frame(x = runif(4), 
                    y = set_units(runif(4), s), 
                    z = set_units(1:4, m/s))
d
##           x             y       z
## 1 0.2064370 0.8463468 [s] 1 [m/s]
## 2 0.1249422 0.5292048 [s] 2 [m/s]
## 3 0.2932732 0.5186254 [s] 3 [m/s]
## 4 0.3757797 0.2378545 [s] 4 [m/s]
summary(d)
##        x                y                z       
##  Min.   :0.1249   Min.   :0.2379   Min.   :1.00  
##  1st Qu.:0.1861   1st Qu.:0.4484   1st Qu.:1.75  
##  Median :0.2499   Median :0.5239   Median :2.50  
##  Mean   :0.2501   Mean   :0.5330   Mean   :2.50  
##  3rd Qu.:0.3139   3rd Qu.:0.6085   3rd Qu.:3.25  
##  Max.   :0.3758   Max.   :0.8463   Max.   :4.00
d$yz = with(d, y * z)
d
##           x             y       z            yz
## 1 0.2064370 0.8463468 [s] 1 [m/s] 0.8463468 [m]
## 2 0.1249422 0.5292048 [s] 2 [m/s] 1.0584095 [m]
## 3 0.2932732 0.5186254 [s] 3 [m/s] 1.5558761 [m]
## 4 0.3757797 0.2378545 [s] 4 [m/s] 0.9514180 [m]
d[1, "yz"]
## 0.8463468 [m]

formatting

Units are often written in the form m2 s-1, for square meter per second. This can be defined as unit, and also parsed by as_units:

(x = 1:10 * as_units("m2 s-1"))
## Units: [m^2/s]
##  [1]  1  2  3  4  5  6  7  8  9 10

udunits understands such string, and can convert them

y = 1:10 * with(ud_units, m^2/s)
x + y
## Units: [m^2/s]
##  [1]  2  4  6  8 10 12 14 16 18 20

Printing units in this form is done by

deparse_unit(x)
## [1] "m2 s-1"

plotting

Base scatter plots and histograms support automatic unit placement in axis labels. In the following example we first convert to SI units. (Unit in needs a bit special treatment, because in is a reserved word in R.)

mar = par("mar") + c(0, .3, 0, 0)
displacement = mtcars$disp * ud_units[["in"]]^3
units(displacement) = with(ud_units, cm^3)
weight = mtcars$wt * 1000 * with(ud_units, lb)
units(weight) = with(ud_units, kg)
par(mar = mar)
plot(weight, displacement)

We can change grouping symbols from [ ] into ( ):

units_options(group = c("(", ")") )  # parenthesis instead of square brackets
par(mar = mar)
plot(weight, displacement)

We can also remove grouping symbols, increase space between variable name and unit by:

units_options(sep = c("~~~", "~"), group = c("", ""))  # no brackets; extra space
par(mar = mar)
plot(weight, displacement)

More complex units can be plotted either with negative powers, or as divisions, by modifying one of units’s global options using units_options:

gallon = as_units("gallon")
consumption = mtcars$mpg * with(ud_units, mi/gallon)
units(consumption) = with(ud_units, km/l)
par(mar = mar)
plot(displacement, consumption) # division in consumption

units_options(negative_power = TRUE) # division becomes ^-1
plot(displacement, consumption) # division in consumption

As usual, units modify automatically in expressions:

units_options(negative_power = TRUE) # division becomes ^-1
par(mar = mar)
plot(displacement, consumption)

plot(1/displacement, 1/consumption)

units/inst/CITATION0000644000176200001440000000061113463271136013532 0ustar liggesusersbibentry( header = "To cite 'units' in publications use:", bibtype = "Article", title = "Measurement Units in {R}", author = c(person("Edzer", "Pebesma"), person("Thomas", "Mailund"), person("James", "Hiebert")), year = "2016", journal = "R Journal", doi = "10.32614/RJ-2016-061", pages = "486--494", volume = "8", number = "2" ) units/inst/share/0000755000176200001440000000000013306730152013473 5ustar liggesusersunits/inst/share/udunits/0000755000176200001440000000000013306730152015166 5ustar liggesusersunits/inst/share/udunits/udunits2-derived.xml0000644000176200001440000002062213306730152021107 0ustar liggesusers SI derived unit radian rad standard unit of angular measure, an angle that creates an arc in a circle equal in length to that circle's radius (roughly 57.3 degrees); as a ratio of two lengths, it has no dimension SI derived unit rad^2 steradian sr standard unit of solid angle measure, it is the solid angle which cuts out an area on a sphere that is the square of the sphere's radius; as a ratio of two areas, it has no dimension SI derived unit 1/s hertz Hz unit of frequency meaning one cycle per second SI derived unit 1e-3 kg gram g unit of mass equal to one thousandth of a kilogram SI derived unit m.kg/s^2 newton N unit of force; the amount needed to accelerate 1 kilogram of mass at the rate of 1 metre per second squared SI derived unit N/m^2 pascal Pa unit of pressure (force per unit area) equal to one newton per square meter SI derived unit N.m joule J standard unit of work or energy, equal to the work done by a force of one newton acting along a distance of one meter SI derived unit J/s watt W standard unit of power, equivalent to one joule per second, and equal to one ampere flowing across a potential difference of one volt SI derived unit s.A coulomb C standard unit of electric charge, the quantity of electricity transported in one second by a current of one ampere SI derived unit W/A volt V standard unit of electric potential difference (and electromotive force); the difference of potential between two points of a conductor carrying a constant current of one ampere and dissipating one watt of power SI derived unit C/V farad F standard unit of capacitance; the amount which, when a capacitor is charged to a potential difference of one volt, carries a charge of one coulomb SI derived unit V/A ohm Ω standard unit of electrical resistance; the resistance between two points of a conductor when a constant potential difference of 1.0 volt, applied to these points, produces in the conductor a current of 1.0 ampere SI derived unit A/V siemens S unit of electric conductance; the reciprocal of one ohm SI derived unit V.s weber Wb unit of magnetic flux (product of the average magnetic field times the perpendicular area that it penetrates), expressed as volt-seconds SI derived unit Wb/m^2 tesla T unit of flux density, equal to one weber per square meter SI derived unit Wb/A henry H unit of inductance; where a circuit's current changes at a constant rate of 1 ampere per second, results in a generation of 1 V of potential difference SI derived unit K @ 273.15 degree_Celsius degrees_Celsius °C unit (and scale) of temperature, with same magnitude as the kelvin and a zero-point offset of 273.15 SI derived unit cd.sr lumen lm unit of luminous flux, a measure of the total "amount" of visible light emitted by a source; one candela-steradian SI derived unit lm/m^2 lux lx unit of illuminance and luminous emittance, measuring luminous flux per unit area, and used as a measure of intensity of light; equal to one lumen per square meter SI derived unit mol/s katal kat unit of catalytic activity (property of a catalyst, such as an enzyme); expresses the ability to break 1 mole of bonds per second under specified conditions SI derived unit with special names/symbols admitted for reasons of safeguarding human health 1/s becquerel Bq unit of radioactivity; the activity of a quantity of material in which one nucleus decays per second (hence, equivalent to one unit per second) SI derived unit with special names/symbols admitted for reasons of safeguarding human health J/kg gray Gy unit of ionizing radiation, a measure of the absorbed dose of radiation; absorption of one joule of radiation energy by one kilogram of matter SI derived unit with special names/symbols admitted for reasons of safeguarding human health J/kg sievert Sv unit of ionizing radiation dose, measuring the health effect of low levels of ionizing radiation on the human body units/inst/share/udunits/udunits2-prefixes.xml0000644000176200001440000000440013306730152021306 0ustar liggesusers 1e24 yotta Y 1e21 zetta Z 1e18 exa E 1e15 peta P 1e12 tera T 1e9 giga G 1e6 mega M 1e3 kilo k 100 hecto h 10 deka da .1 deci d .01 centi c 1e-3 milli m 1e-6 micro µ μ u 1e-9 nano n 1e-12 pico p 1e-15 femto f 1e-18 atto a 1e-21 zepto z 1e-24 yocto y units/inst/share/udunits/udunits2-accepted.xml0000644000176200001440000002654113306730152021243 0ustar liggesusers 60 s minute min period of time equal to 60 seconds 60 min hour h hr period of time equal to 60 minutes 24 h day d period of time equal to 24 hours This "unit" is useful in the definition of subsequent units. 3.141592653589793238462643383279 pi π mathematical constant equal to the ratio of a circle's circumference to its diameter (pi/180) rad arc_degree ° angular_degree degree arcdeg measurement of a plane angle representing 1/360 of a full rotation °/60 arc_minute ' angular_minute arcminute arcmin measurement of a plane angle equal to 1/60 arc degree '/60 arc_second " angular_second arcsecond arcsec measurement of a plane angle equal to 1/60 arc minute The definition is exact. From 1901 to 1964, however, 1 liter was 1.000028 dm^3 (volume of 1 kg of water under standard conditions). dm^3 liter L litre l unit of capacity equal to 1000 cubic centimeters 1000 kg metric_ton t tonne unit of weight equal to 1000 kilograms Unit's value is obtained experimentally 1.60217733e-19 J electronvolt eV electron_volt unit of energy equal to the work accelerating an electron through a potential difference of one volt Unit's value is obtained experimentally 1.6605402e-27 kg unified_atomic_mass_unit u atomic_mass_unit atomicmassunit amu standard unit for indicating mass on an atomic or molecular scale; is approximately the mass of one nucleon (either a single proton or neutron), and equivalent to 1 g/mol According to resolution by the International Astronomical Union (IAU) in 2012 1.49597870700e11 m astronomical_unit au Exact definition according to 2012 resolution by the International Astronomical Union (IAU). Ostensibly equal to the mean distance from the center of the earth to the center of the sun. Pre-2012 resolution by the IAU 1.495979e11 m astronomical_unit_BIPM_2006 ua unit of measurement equal to 149.6 million kilometers, the mean distance from the center of the earth to the center of the sun according to the International Bureau of Weights and Measures (BIPM) in 2006 Unit is temporarily accepted for use with the SI. 1852 m nautical_mile unit of distance at sea, set at 1852 meters (approximately one minute of arc measured along any meridian) Unit is temporarily accepted for use with the SI. nautical_mile/hour international_knot knot_international knot derived unit of speed at sea Unit is temporarily accepted for use with the SI. 1e-10 m angstrom ångström Å unit of length equal to one hundred-millionth of a centimeter (1 meter/10**10) Unit is temporarily accepted for use with the SI. dam^2 are a unit of area equal to 100 square meters Unit is temporarily accepted for use with the SI. 100 are hectare unit of area equal to 100 are ('hectoare'), or 10000 square meters Unit is temporarily accepted for use with the SI. 100 fm^2 barn b unit of area, approximately the cross-sectional area of a uranium nucleus (10e-28 square meters) Unit is temporarily accepted for use with the SI. 1000 hPa bar unit of pressure equal to 100000 Pascals, or about 0.987 atmospheres of pressure Unit is temporarily accepted for use with the SI. cm/s^2 gal unit of acceleration equal to 1 cm per second squared Unit is temporarily accepted for use with the SI. 3.7e10 Bq curie Ci unit of radioactivity corresponding to 3.7 * 10e10 disintegrations per second Unit is temporarily accepted for use with the SI. 2.58e-4 C/kg roentgen R unit of ionizing radiation, the amount producing one electrostatic unit of positive or negative ionic charge in one cubic centimeter of air under standard conditions; rarely used Unit is temporarily accepted for use with the SI. cSv rem unit of radiation dosage applied to humans; equal to one hundredth of a sievert units/inst/share/udunits/udunits2.xml0000644000176200001440000000100713306730152017463 0ustar liggesusers udunits2-prefixes.xml udunits2-base.xml udunits2-derived.xml udunits2-accepted.xml udunits2-common.xml units/inst/share/udunits/udunits2-common.xml0000644000176200001440000024613313306730152020764 0ustar liggesusers Synonym for SI unit s sec unit of time, synonym for second Synonym for SI unit A amp unit of electric current, synonym for ampere Synonym for SI unit K °K degree_kelvin degrees_kelvin degree_K degrees_K degreeK degreesK deg_K degs_K degK degsK unit of temperature, synonym for kelvin Synonym for SI unit cd candle unit of luminous intensity, synonym for candela Synonym for SI unit mole einstein unit of chemical mass, synonym for mole Synonym for SI unit Hz baud Bd bps unit of frequency, synonym for hertz Synonym for SI unit degree_Celsius celsius degree_C degrees_C degreeC degreesC deg_C degs_C degC degsC unit of temperature, synonym for 'K @ 273.15' (degree_Celsius) Synonym for SI unit knot kt kts unit of speed, synonym for nautical_mile/hour Constant; value is +-30e15 6.02214179e23/mol avogadro_constant number of constituent particles (usually atoms or molecules) per mole of a given substance Constant 0.01 percent % number of parts per hundred Constant 1e-6 ppm ppmv parts per million Constant 1e-9 ppb ppbv parts per billion Constant 1e-12 ppt pptv parts per trillion Constant 1e-15 ppq ppqv parts per quadrillion 0.9 arc_degree grade 1/100 of a right angle (90 degrees) 2 pi rad circle cycle turn revolution rotation unit of angle in a plane signifying a full 360-degree circle arc_degree degree_north degrees_north degree_N degrees_N degreeN degreesN degree_east degrees_east degree_E degrees_E degreeE degreesE degree_true degrees_true degree_T degrees_T degreeT degreesT unit of angle on a sphere -1 degree_east degree_west degrees_west degree_W degrees_W degreeW degreesW unit of angle on a sphere (units for negative direction) 2.916667e-2 kg assay_ton reference unit of mass for a body of ore; roughly equal to 29167 milligrams 2.834952e-2 kg avoirdupois_ounce unit of mass equal to 1/16 avoirdupois pound, commonly used in the United States (16 oz = 1 pound = 7000 grains) 4.5359237e-1 kg avoirdupois_pound pound lb unit of mass in avoirdupois system of weights (a system commonly used in United States) 2e-4 kg carat unit of mass equal to 0.2 gram (defined 1907) 6.479891e-5 kg grain gr unit of mass equal to 1/7000 pound 5.080235e1 kg long_hundredweight unit of mass; a British hundredweight, which is 8 stone * 14 pounds/stone 1.555174e-3 kg pennyweight unit of mass; based on historical US troy weight system (is 1/20 troy ounce) 4.535924e1 kg short_hundredweight unit of mass, a US hundredweight, which is 100 pounds 14.59390 kg slug unit of mass associated with Imperial units; a mass that accelerates by 1 ft/s2 when a force of one pound-force (lbF) is exerted on it 3.110348e-2 kg troy_ounce apothecary_ounce unit of mass; based on historical US troy weight system (is 1/12 troy pound) 3.732417e-1 kg troy_pound apothecary_pound unit of mass; based on historical US troy weight system (is 5760 grain) 20 grain scruple unit of mass in apothecaries' weight system (is 1/3 apdram) 60 grain apdram unit of mass in apothecaries' weight system (is 1/8 apounce) exact avoirdupois_ounce/16 dram dr unit of mass in the avoirdupois system (the system commonly used in the United States) 480 grain apounce unit of mass in apothecaries' weight system (is 1/16 appound) 5760 grain appound unit of mass in apothecaries' weight system (is same as a troy pound) 94 pound bag unit of mass, for a traditional bag of portland cement 2000 pound short_ton ton unit of mass based on US weight system 2240 pound long_ton unit of mass based on British imperial weight system 1e-15 m fermi unit of length equal to 10e-15 meters, a typical length-scale of nuclear physics 9.46073e15 m light_year unit of length equal to the distance traversed by light in one mean solar year (365.2422 days), a typical length-scale of astronomy 1e-6 m micron unit of length, a typical length-scale of technology and science fields 2.54e-5 m mil unit of length equal to 0.001 inch, a typical length-scale for measuring wire diameters 3.085678e16 m parsec unit of length corresponding to the distance at which the mean radius of the earth's orbit subtends an angle of one second of arc, a typical length-scale of astronomy 3.514598e-4 m printers_point unit of length equal to 1/72.27 inch, the original (standardized 1886) unit for measuring font size and other small items on a printed page (see also big_point) 2.011684e1 m chain unit of length equal to 66 feet (4 poles), or 1/10 furlong, a typical (historical) scale of land surveying 12 printers_point printers_pica pica unit of length equal to 1/6 inch (12 printers points) nautical_mile nmile unit of length in the US Customary System, equal to 6,076 feet; typically used for air and sea navigation (1200/3937) m US_survey_foot US_survey_feet unit of length used for earlier survey data in some countries, slightly different than the current international foot 3 US_survey_feet US_survey_yard unit of length used in earlier survey data in some countries, slightly different than the current international yard 5280 US_survey_feet US_survey_mile US_statute_mile unit of length used for earlier survey data in some countries, slightly slightly different than the current international mile 16.5 US_survey_feet rod pole perch unit of length equal to one-fourth of a surveyor's chain 660 US_survey_feet furlong unit of length equal to 1/8 mile or 10 chains 6 US_survey_feet fathom unit of length equal to 6 feet in the imperial and US customary systems, typically used for measuring depth of water 2.54 cm international_inch inch in unit of length equal to 25.4 mm by definition, used in imperial and US customary systems 12 international_inches international_foot international_feet foot feet ft unit of length equal to 12 international inches, in the imperial and US customary systems; primarily used in the United States 3 international_feet international_yard yard yd unit of length equal to 3 international feet, in the imperial and US customary systems; primarily used in the United States 5280 international_feet international_mile mile mi unit of length equal to 5280 feet, equal to 12 international inches, in the imperial and US customary systems; primarily used in the United States and other smaller countries with ties to the US or United Kingdom inch/72 big_point unit of length equal to 1/72 inch, standardized unit in modern computer-based publishing for measuring font size and other small items on a printed page (contrast to printers_point) inch/3 barleycorn unit of length based in medieval laws of England and Wales, defining an inch as being 3 barleycorns long (length of a corn of barley); still the basis for current shoe sizes in Great Britain and Ireland 191.835 foot arpentlin unit of length in French regions; a linear arpent is of length 10 perch (10 rod) exact rotation/second rotation_per_second rotations_per_second rps cps unit of angular velocity exact rotation/minute rpm unit of angular velocity measuring the angular distance covered by a rotating object, divided by the amount of time used to cover that distance; measured perpendicular to the plane of rotation, with direction usually indicated by the right-hand rule 1.111111e-7 kg/m denier unit of lineic mass density for fibers, equal to the mass in grams per 9000 meters (more common in United States and United Kingdom); a single strand of silk is approximately one denier exact 1e-6 kg/m tex unit of lineic mass density for fibers, defined as mass in grams per 1000 meters (more common in Canada and Continental Europe) 5.72135e-11 kg/(Pa.s.m^2) perm_0C perms_0C unit of mass per unit time (includes flow) for how fast water vapor flows through substance, or permeance; equals 1 gram of water vapor per hour, per square meter, per millimeter of mercury at 0 degrees C 5.74525e-11 kg/(Pa.s.m^2) perm_23C perms_23C unit of mass per unit time for how fast water vapor flows through substance, or permeance; equals 1 gram of water vapor per hour, per square meter, per millimeter of mercury at 23 degrees C 5.067075e-10 m^2 circular_mil unit of area equal to the area of a one-mil diameter circle porous solid permeability 9.869233e-13 m^2 darcy unit of area for measuring permeability to fluid, equal to 1 cubic centimeter of fluid with 1 centipoise viscosity in 1 second through a 1-square-centimeter cross section of porous medium 1 centimeter long at 1 atmosphere exact 160 rod^2 acre unit of area in the US Customary System, used in land and sea floor measurement, equal to 43560 square feet An "acre.foot", however, is 1233.4867714897 m^3. Odd. 1.233489e3 m^3 acre_foot acre_feet unit of volume used to describe large-scale water resources in the United State; equal to the volume of one acre of surface area with one foot of depth depth 2.359737e-3 m^3 board_foot board_feet unit of volume equal to the cubic contents of a piece of lumber one foot square and one inch thick, used in measuring logs and lumber in the United States and Canada 3.523907e-2 m^3 bushel bu unit of volume defined as 2150.42 cubic inches or 4 pecks in the US Customary system (and formerly in England), where it is used as a dry measure exact bushel/4 peck pk unit of volume defined as 537.6 cubic inches in the US Customary system (and formerly in England), where it is used as a dry measure exact 4.546090e-3 m^3 Canadian_liquid_gallon unit of volume for liquids in the Imperial system 4.404884e-3 m^3 US_dry_gallon unit of volume for dry measure in the US Customary system, defined as 1/2 peck or 1/8 bushel exact cm^3 cc unit of volume equal to the volume of a cube 1 centimeter on each side exact 1 m^3 stere unit of volume equal to a cubic meter, originally defined primarily as a measure for firewood 2.831685 m^3 register_ton unit of volume used for internal capacity of ships, equal to 100 cubic feet exact US_dry_gallon/4 US_dry_quart dry_quart unit of volume for dry measure in the US Customary system, equal to 1/32 US bushel exact US_dry_gallon/8 US_dry_pint dry_pint unit of volume for dry measure in the US Customary system, equal to 1/2 US dry quart 3.785412e-3 m^3 US_liquid_gallon liquid_gallon gallon unit of volume for liquid measure in the US Customary system, defined as 3.785412 liters The following is the definition of the petroleum industry 42 US_liquid_gallon barrel bbl unit of volume used by US and Canadian petroleum organizations The following is exact regardless of the definition of "barrel" barrel/4 firkin unit of volume whose exact quantity depends on the type of barrel on which it is defined; in this table it is defined based on the oil barrel used by the petroleum industry exact US_liquid_gallon/4 US_liquid_quart liquid_quart quart unit of volume for liquid measure in the US Customary system, equal to 1/4 liquid gallon exact US_liquid_gallon/8 US_liquid_pint liquid_pint pint pt unit of volume for liquid measure in the US Customary system, equal to 1/8 liquid gallon exact US_liquid_gallon/16 US_liquid_cup liquid_cup cup unit of volume for liquid measure in the US Customary system, equal to 1/16 liquid gallon exact US_liquid_gallon/32 US_liquid_gill liquid_gill gill unit of volume for liquid measure in the US Customary system, equal to 1/32 liquid gallon exact US_liquid_gallon/128 US_fluid_ounce US_liquid_ounce fluid_ounce liquid_ounce oz floz unit of volume for liquid measure in the US Customary system, equal to 1/128 liquid gallon exact US_fluid_ounce/2 tablespoon Tbl Tbsp tbsp Tblsp tblsp unit of volume for liquid measure in the US Customary system, equal to 1/2 liquid ounce exact US_fluid_ounce/8 fluid_dram fldr unit of volume for liquid measure in the apothecary system, equal to 1/8 liquid ounce exact tablespoon/3 teaspoon tsp unit of volume defined as 1/3 tablespoon, the actual volume of which can vary depending on the measurement system (but is based on the US Customary system in this database) exact 4.546090e-3 m^3 UK_liquid_gallon unit of volume for liquid measure in the Imperial system exact UK_liquid_gallon/4 UK_liquid_quart unit of volume for liquid measure in the Imperial system, equal to 1/4 liquid gallon exact UK_liquid_gallon/8 UK_liquid_pint unit of volume for liquid measure in the Imperial system, equal to 1/8 liquid gallon exact UK_liquid_gallon/16 UK_liquid_cup unit of volume for liquid measure in the Imperial system, equal to 1/16 liquid gallon exact UK_liquid_gallon/32 UK_liquid_gill unit of volume for liquid measure in the Imperial system, equal to 1/32 liquid gallon exact UK_liquid_gallon/160 UK_fluid_ounce UK_liquid_ounce unit of volume for liquid measure in the Imperial system, equal to 1/160 liquid gallon lg(re (1e-6 m)^3) BZ logarithmic unit used to compare the reflectivity (Z) of an unknown remote object, to the reflective return created by a droplet of rain with a diameter of 1 mm; is the base unit for "dBz", which is the typical logarithmic unit for measuring atmospheric radar reflectivity; a value of 0 Bz (0 DBz) corresponds to the return from a single cubic micron; a value of 6 Bz (60 DBz) corresponds to extremely heavy rain. 1e-8 s shake unit of time approximating the lifetime of an individual neutron, useful for describing very brief durations, e.g., in nuclear physics 8.616409e4 s sidereal_day unit of time that it takes the earth to complete one revolution with respect to a star, roughly 23 hours, 56 minutes, 4 seconds 3.590170e3 s sidereal_hour unit of time equal to 1/24 sidereal day 5.983617e1 s sidereal_minute unit of time equal to 1/60 sidereal hour 0.9972696 s sidereal_second unit of time equal to 1/60 sidereal second 3.155815e7 s sidereal_year unit of time for the earth to make one complete revolution around the sun, relative to the fixed stars 3.15569259747e7 s tropical_year year yr unit of time; Interval between 2 successive passages of sun through vernal equinox (365.242198781 days). See http://www.ast.cam.ac.uk/pubinfo/leaflets/, http://aa.usno.navy.mil/AA/, and http://adswww.colorado.edu/adswww/astro_coord.html 29.530589 day lunar_month unit of time equal to the average time between successive new or full moons; equal to approximately 29 days, 12 hours, 44 minutes 365 day common_year unit of time corresponding to a 'normal' calendar year, that is, one without insertion of a leap day 366 day leap_year unit of time corresponding to a calendar year with a leap day inserted 365.25 day Julian_year unit of time recognized by the International Astronomical Union for use in astronomy, defined as 365.25 days of 86400 seconds 365.2425 day Gregorian_year unit of time based on the Gregorian Calendar, the one commonly used today; approximates the tropical year as 365 + 97/400 days 27.321661 day sidereal_month unit of time based on 1/12 of the sidereal year 27.321582 day tropical_month unit of time based on 1/12 of the tropical year 14 day fortnight unit of time commonly defined as 14 days 7 day week unit of time commonly defined as 7 days multiple values have been proposed for the amount of time represented by a 'jiffy' 0.01 s jiffy unit of time used in computer animation as a method of defining playback rate 1e9 year eon unit of time defined in astronomy as 1 billion years year/12 month unit of time defined as the average length of time for a calendar month exact 1e6 m^3/s sverdrup unit of volume transport, used almost exclusively to measure the volumetric rate of ocean currents exact 9.806650 m/s^2 standard_free_fall unit of acceleration corresponding to the nominal gravitational acceleration of an object in a vacuum near the surface of earth should be local standard_free_fall gravity unit of acceleration synonymous with standard rate of free fall (in earth's gravity) exact gravity 1000 kg/m^3 conventional_water water H2O h2o specifies the acceleration at the earth's surface of a substance with the density of water gravity 999.972 kg/m^3 water_4C waters_4C water_39F waters_39F specifies the acceleration at the earth's surface of a substance with the density of water at 4 degrees C gravity 999.001 kg/m^3 water_60F waters_60F specifies the acceleration at the earth's surface of a substance with the density of water at 60 degrees F gravity 13595.10 kg/m^3 mercury_0C mercuries_0C mercury_32F mercuries_32F conventional_mercury conventional_mercuries Hg specifies the acceleration at the earth's surface of a substance with the density of mercury at 0 degrees C gravity 13556.8 kg/m^3 mercury_60F mercuries_60F specifies the acceleration at the earth's surface of a substance with the density of mercury at 60 degrees F standard_free_fall force unit of force equivalent to the force generated by the effect of gravity exact 1e-5 N dyne unit of force, equal to the force that produces an acceleration of one centimeter per second per second on a mass of one gram (the standard centimeter-gram-second unit of force) exact 9.806650e-3 N pond unit of force, equal to the magnitude of the force exerted by one gram of mass in a 9.80665 m/s2 gravitational field exact 9.806650 N force_kilogram kilogram_force kilograms_force kgf unit of force, equal to the magnitude of the force exerted by one kilogram of mass in a 9.80665 m/s2 gravitational field exact 2.780139e-1 N force_ounce ounce_force ounces_force ozf unit of force, equal to the magnitude of the force exerted by one ounce of mass in a 9.80665 m/s2 gravitational field exact 4.4482216152605 N force_pound pound_force pounds_force lbf unit of force, equal to the magnitude of the force exerted by one pound of mass in a 9.80665 m/s2 gravitational field exact 1.382550e-1 N poundal unit of force, that which is necessary to accelerate 1 pound-mass to 1 foot per second per second exact gram force gram_force grams_force force_gram gf unit of force, equal to the magnitude of the force exerted by one gram of mass in a 9.80665 m/s2 gravitational field exact 2000 force_pound force_ton ton_force tons_force unit of force, equal to the magnitude of the force exerted by one ton of mass in a 9.80665 m/s2 gravitational field (specifically a short ton of mass) exact 1000 lbf kip unit of force, equal to the magnitude of the force exerted by one thousand pounds of mass in a 9.80665 m/s2 gravitational field exact 1.01325e5 Pa standard_atmosphere atmosphere atm unit of pressure, an international reference pressure intended to represent the mean atmospheric pressure at mean sea level at the latitude of Paris, France exact; note that the symbol 'at' clashes with that of the katal ('kat'), the SI unit of catalytic activity 1 kg gravity/cm2 technical_atmosphere at unit of pressure equal to one kilogram force per square centimeter cm H2O cm_H2O cmH2O unit of pressure derived from pressure head calculations using metrology; represents the pressure exerted by a column of water of 1 cm height at 4 degrees C exact inch water_39F inch_H2O_39F inches_H2O_39F unit of pressure representing the pressure exerted by a column of water of 1 inch height at 39 degrees F exact inch water_60F inch_H2O_60F inches_H2O_60F unit of pressure representing the pressure exerted by a column of water of 1 inch height at 60 degrees F foot water foot_water feet_water foot_H2O feet_H2O footH2O feetH2O ftH2O fth2o unit of pressure representing the pressure exerted by a column of water of 1 foot height at 4 degrees C cm Hg cm_Hg cmHg unit of pressure representing the pressure exerted by a column of mercury of 1 cm height at 0 degrees C exact mm mercury_0C millimeter_Hg_0C millimeters_Hg_0C unit of pressure representing the pressure exerted by a column of mercury of 1 mm height at 0 degrees C exact inch mercury_32F inch_Hg_32F inches_Hg_32F unit of pressure representing the pressure exerted by a column of mercury of 1 inch height at 32 degrees F exact inch mercury_60F inch_Hg_60F inches_Hg_60F unit of pressure representing the pressure exerted by a column of mercury of 1 inch height at 60 degrees F mm Hg millimeter_Hg millimeters_Hg torr mm_Hg mm_hg mmHg mmhg unit of pressure representing the pressure exerted by a column of mercury of 1 mm height at 0 degrees C; approximately (within 0.000015%, generally below measurement error) 1 Torr, which is 1/760 standard atmospheric pressure inch Hg inch_Hg inches_Hg in_Hg inHg unit of pressure representing the pressure exerted by a column of mercury of 1 inch height at 0 degrees C exact 1 pound gravity/in^2 psi unit of pressure representing the pressure exerted, due to gravity, by a one-pound mass, of area one square inch; commonly referred to as "pounds per square inch" exact kip/in^2 ksi unit of pressure representing the pressure exerted, due to gravity, by a 1000-pound mass, of area one square inch exact 0.1 N/m^2 barie barye unit of pressure equal to one dyne per square centimeter sound pressure level lg(re 20e-6 Pa) B_SPL logarithmic unit used to compare the sound pressure of an unknown sound to a standard reference sound pressure; is the base unit for "dB_SPL", a more typical logarithmic unit for measuring sound pressure (the SI unit for sound pressure is pascal); the standard reference sound pressure in air or other gases is 20 microPascal, which is usually considered the threshold of human hearing (at 1 kHz) exact 1e-1 Pa.s poise unit of dynamic viscosity, corresponding to 0.1 pascal-second (pascal-second: a fluid placed between two plates, when one plate is pushed sideways with a shear stress of one pascal, moves a distance equal to the thickness of the layer between the plates in one second) exact 1e-4 m^2/s stokes St unit of kinematic viscosity, measuring the ratio of the dynamic viscosity to the density of the fluid; water at 20 degrees C has a kinematic viscosity about 100 stokes, or more cmomonly, 1 cSt exact 10/(Pa.s) rhe unit of fluidity (reciprocal of velocity), measured in reciprocal poise exact 1e-7 J erg unit of work, equal to the amount of work done by a force of one dyne exerted for a distance of one centimeter (in CGS base units, one gram centimeter-squared per second-squared) exact 1.05505585262e3 J IT_Btu IT_Btus Btu Btus unit of energy, equal to the energy needed to cool or heat one pound of water by one degree F; this uses the International Steam Table (IT) calorie , defined by the Fifth International Conference on the properties of Steam (1956) exact (reference NIST Guide to SI Units) 1.05506e8 J EC_therm unit of energy legally defined by the Council Directive of 20 December 1979, Council of the European Communities (now the European Union, EU);.roughly equal to 100,000 IT_Btu exact 4.184000 J thermochemical_calorie unit of heat energy defined as 4.184 Joules exactly (International Standard ISO 31-4: Quantities and units, Part 4: Heat); approximately the energy needed to increase the temperature of 1 gram of water by 1 C exact 4.1868 J IT_calorie calorie cal unit of heat energy used in thermochemistry, the International Steam Table (IT) calorie defined by the Fifth International Conference on the properties of Steam (1956) by definition 4.184 MJ/kg TNT unit of energy; approximately the energy released by the detonation of a given amount of mass of TNT by definition 4.184e9 J ton_TNT tons_TNT unit of energy; approximately the energy released by the detonation of a 1000 kilograms of TNT exact 1.054804e8 J US_therm therm thm unit of energy legally defined in the U.S. Federal Register of July 27, 1968, and the legal unit used by the U.S. natural gas industry exact watt.hour watthour unit of energy equal to the product of the power in watts and the time in hours (if the energy is being transmitted or used at a constant rate (power) over a period of time); one watt is equal to 1 Joule/second exact 1e9 eV bev unit of energy corresponding to 1 billion electron volts (eV) exact V.A voltampere VA unit of electric power equal to the product of one volt and one ampere, equivalent to one watt for direct current systems and a unit of apparent power for alternating current systems 9.80950e3 W boiler_horsepower unit of power equal to the power required to evaporate 34.5 lb of fresh water at 212 degrees F in one hour; describes a boiler's capacity to deliver steam to a steam engine shaft_horsepower is a unit of power as delivered by a drive shaft at its output (e.g., of a ship, aircraft engine, or helicopter rotor; typically not automobiles due to drive train losses) 7.456999e2 W shaft_horsepower horsepower hp unit of power originally corresponding to the estimated typical power of draft horses, calculated as lifting 33000 pounds one foot in one minute (550 foot-pounds/second) 7.35499e2 W metric_horsepower unit of power corresponding to a calculation of 75 kilogram-meters/second exact 7.460000e2 W electric_horsepower unit of power defined in the International System of Units as exactly 746 W; generally used for power used by electrical machines 7.46043e2 W water_horsepower unit of power used in the U.S. primarily in rating pumps; calculated as pump capacity Q (gallons per minute) times pump pressure ("head") of P (feet of head), divided by 3956 water horsepower; the calculation assumes water density is 8 1/3 pounds per U.S. gallon, which is not exact. 7.4570e2 W UK_horsepower unit of power originally corresponding to the estimated typical power of draft horses, calculated as lifting 33000 pounds one foot in one minute (550 foot-pounds/second), as calculated/specified in the United Kingdom 12000 Btu/hr refrigeration_ton ton_of_refrigeration tons_of_refrigeration unit of power describing the heat-extraction capacity of cooling equipment; defined as the heat absorbed by melting 1 short ton of pure ice at 0 degrees C in 24 hours lg(re 1 W) BW unit of power in decibel scale, referenced to 1 watt; the power in bel-watts is equal to 100 times the base 10 logarithm of the power in watts (making decibel-watt, the more common term, 10 times the base 10 log of the power in watts) lg(re 1 mW) Bm unit of power in decibel scale, referenced to 1 milliwatt; the power in bel-milliwatts is equal to 100 times the base 10 logarithm of the power in milliwatts (making decibel-milliwatt, the more common term, 10 times the base 10 log of the power in watts) 1.55e-1 K.m^2/W clo unit of thermal resistance used in describing the insulating value of clothing; the amount of thermal resistance needed to maintain in comfort a resting subject in a normally ventilated room (air movement 10 cm/sec) at a temperature of 20 degrees C and a humidity less than 50% 10 A abampere basic unit of electricity in the electromagnetic CGS system of units 7.957747e-1 A gilbert unit of electricity/magnetism 3.335640e-10 A statampere unit of electricity/magnetism 10 A biot basic unit of electricity in the electromagnetic CGS system of units (same as abampere), named after Jean-Baptiste Biot exact 1e9 F abfarad unit of electricity/magnetism exact 1e-9 H abhenry unit of electricity/magnetism exact 1e9 S abmho unit of electricity/magnetism exact 1e-9 ohm abohm unit of electricity/magnetism exact 1e-8 V abvolt unit of electricity/magnetism 1.602176487e-19 C e unit of electricity/magnetism 9.64957e4 C chemical_faraday unit of electricity/magnetism 9.65219e4 C physical_faraday unit of electricity/magnetism 9.648531e4 C C12_faraday faraday unit of electricity/magnetism exact 1e-9 T gamma unit of electricity/magnetism exact 1e-4 T gauss unit of electricity/magnetism exact 1e-8 Wb maxwell unit of electricity/magnetism 7.957747e1 A/m oersted Oe unit of electricity/magnetism 3.335640e-10 C statcoulomb unit of electricity/magnetism 1.112650e-12 F statfarad unit of electricity/magnetism 8.987554e11 H stathenry unit of electricity/magnetism 1.112650e-12 S statmho unit of electricity/magnetism 8.987554e11 ohm statohm unit of electricity/magnetism 2.997925e2 V statvolt unit of electricity/magnetism 1.256637e-7 Wb unit_pole unit of electricity/magnetism lg(re 1 V) BV unit of electricity/magnetism rms voltage lg(re 0.775 V) Bv unit of electricity/magnetism lg(re 1e-6 V) BµV unit of electricity/magnetism K/1.8 °R degree_rankine degrees_rankine degreeR degreesR degree_R degrees_R degR degsR deg_R degs_R unit of thermodynamic temperature °R @ 459.67 °F fahrenheit degree_fahrenheit degrees_fahrenheit degreeF degreesF degree_F degrees_F degF degsF deg_F degs_F unit of thermodynamic temperature 1.076391e-1 lx footcandle unit of illumination exact 3.426259 cd/m^2 footlambert unit of illumination exact (1e4/pi) cd/m^2 lambert unit of illumination exact 1e4 cd/m^2 stilb sb unit of illumination exact 1e4 lm/m^2 phot ph unit of illumination exact 1 cd/m^2 nit nt unit of illumination exact 4.184000e4 J/m^2 langley unit of illumination exact cd/(pi m^2) blondel apostilb unit of illumination exact 100/m kayser exact gravity geopotential dynamic gp exact 2056 hours work_year exact work_year/12 work_month exact 1e-6 m^2 s^-1 K kg^-1 potential_vorticity_unit PVU 1 count 1 bit 8 octet byte 446.2 micromoles/meter^2 dobson DU 1/avogadro_constant molecule molec nucleon nuc units/inst/share/udunits/udunits2-base.xml0000644000176200001440000000532413306730152020401 0ustar liggesusers meter m metre The meter is the length of the path travelled by light in vacuum during a time interval of 1/299 792 458 of a second. kilogram kg The kilogram is the unit of mass; it is equal to the mass of the international prototype of the kilogram. second s The second is the duration of 9 192 631 770 periods of the radiation corresponding to the transition between the two hyperfine levels of the ground state of the cesium 133 atom. ampere A The ampere is that constant current which, if maintained in two straight parallel conductors of infinite length, of negligible circular cross-section, and placed 1 meter apart in vacuum, would produce between these conductors a force equal to 2e-7 newton per meter of length. kelvin K The kelvin, unit of thermodynamic temperature, is the fraction 1/273.16 of the thermodynamic temperature of the triple point of water. mole mol The mole is the amount of substance of a system which contains as many elementary entities as there are atoms in 0.012 kilogram of carbon 12. When the mole is used, the elementary entities must be specified and may be atoms, molecules, ions, electrons, other particles, or specified groups of such particles. candela cd The candela is the luminous intensity, in a given direction, of a source that emits monochromatic radiation of frequency 540e12 hertz and that has a radiant intensity in that direction of 1/683 watt per steradian. units/cleanup0000755000176200001440000000004413547030302012764 0ustar liggesusersrm -f src/Makevars src/*.o src/*.so units/configure0000755000176200001440000043601413547030302013330 0ustar liggesusers#! /bin/sh # Guess values for system-dependent variables and create Makefiles. # Generated by GNU Autoconf 2.69 for units 0.6-4. # # Report bugs to . # # # Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc. # # # This configure script is free software; the Free Software Foundation # gives unlimited permission to copy, distribute and modify it. ## -------------------- ## ## M4sh Initialization. ## ## -------------------- ## # Be more Bourne compatible DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi as_nl=' ' export as_nl # Printing a long string crashes Solaris 7 /usr/bin/printf. as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo # Prefer a ksh shell builtin over an external printf program on Solaris, # but without wasting forks for bash or zsh. if test -z "$BASH_VERSION$ZSH_VERSION" \ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='print -r --' as_echo_n='print -rn --' elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='printf %s\n' as_echo_n='printf %s' else if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' as_echo_n='/usr/ucb/echo -n' else as_echo_body='eval expr "X$1" : "X\\(.*\\)"' as_echo_n_body='eval arg=$1; case $arg in #( *"$as_nl"*) expr "X$arg" : "X\\(.*\\)$as_nl"; arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; esac; expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" ' export as_echo_n_body as_echo_n='sh -c $as_echo_n_body as_echo' fi export as_echo_body as_echo='sh -c $as_echo_body as_echo' fi # The user is always right. if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi # IFS # We need space, tab and new line, in precisely that order. Quoting is # there to prevent editors from complaining about space-tab. # (If _AS_PATH_WALK were called with IFS unset, it would disable word # splitting by setting IFS to empty value.) IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break done IFS=$as_save_IFS ;; esac # We did not find ourselves, most probably we were run as `sh COMMAND' # in which case we are not to be found in the path. if test "x$as_myself" = x; then as_myself=$0 fi if test ! -f "$as_myself"; then $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 exit 1 fi # Unset variables that we do not need and which cause bugs (e.g. in # pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" # suppresses any "Segmentation fault" message there. '((' could # trigger a bug in pdksh 5.2.14. for as_var in BASH_ENV ENV MAIL MAILPATH do eval test x\${$as_var+set} = xset \ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : done PS1='$ ' PS2='> ' PS4='+ ' # NLS nuisances. LC_ALL=C export LC_ALL LANGUAGE=C export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # Use a proper internal environment variable to ensure we don't fall # into an infinite loop, continuously re-executing ourselves. if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then _as_can_reexec=no; export _as_can_reexec; # We cannot yet assume a decent shell, so we have to provide a # neutralization value for shells without unset; and this also # works around shells that cannot unset nonexistent variables. # Preserve -v and -x to the replacement shell. BASH_ENV=/dev/null ENV=/dev/null (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV case $- in # (((( *v*x* | *x*v* ) as_opts=-vx ;; *v* ) as_opts=-v ;; *x* ) as_opts=-x ;; * ) as_opts= ;; esac exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} # Admittedly, this is quite paranoid, since all the known shells bail # out after a failed `exec'. $as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 as_fn_exit 255 fi # We don't want this to propagate to other subprocesses. { _as_can_reexec=; unset _as_can_reexec;} if test "x$CONFIG_SHELL" = x; then as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which # is contrary to our usage. Disable this feature. alias -g '\${1+\"\$@\"}'='\"\$@\"' setopt NO_GLOB_SUBST else case \`(set -o) 2>/dev/null\` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi " as_required="as_fn_return () { (exit \$1); } as_fn_success () { as_fn_return 0; } as_fn_failure () { as_fn_return 1; } as_fn_ret_success () { return 0; } as_fn_ret_failure () { return 1; } exitcode=0 as_fn_success || { exitcode=1; echo as_fn_success failed.; } as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; } as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; } as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; } if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then : else exitcode=1; echo positional parameters were not saved. fi test x\$exitcode = x0 || exit 1 test -x / || exit 1" as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" && test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1 test \$(( 1 + 1 )) = 2 || exit 1" if (eval "$as_required") 2>/dev/null; then : as_have_required=yes else as_have_required=no fi if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then : else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR as_found=false for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. as_found=: case $as_dir in #( /*) for as_base in sh bash ksh sh5; do # Try only shells that exist, to save several forks. as_shell=$as_dir/$as_base if { test -f "$as_shell" || test -f "$as_shell.exe"; } && { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then : CONFIG_SHELL=$as_shell as_have_required=yes if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then : break 2 fi fi done;; esac as_found=false done $as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } && { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then : CONFIG_SHELL=$SHELL as_have_required=yes fi; } IFS=$as_save_IFS if test "x$CONFIG_SHELL" != x; then : export CONFIG_SHELL # We cannot yet assume a decent shell, so we have to provide a # neutralization value for shells without unset; and this also # works around shells that cannot unset nonexistent variables. # Preserve -v and -x to the replacement shell. BASH_ENV=/dev/null ENV=/dev/null (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV case $- in # (((( *v*x* | *x*v* ) as_opts=-vx ;; *v* ) as_opts=-v ;; *x* ) as_opts=-x ;; * ) as_opts= ;; esac exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} # Admittedly, this is quite paranoid, since all the known shells bail # out after a failed `exec'. $as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 exit 255 fi if test x$as_have_required = xno; then : $as_echo "$0: This script requires a shell more modern than all" $as_echo "$0: the shells that I found on your system." if test x${ZSH_VERSION+set} = xset ; then $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should" $as_echo "$0: be upgraded to zsh 4.3.4 or later." else $as_echo "$0: Please tell bug-autoconf@gnu.org and $0: edzer.pebesma@uni-muenster.de about your system, $0: including any error possibly output before this $0: message. Then install a modern shell, or manually run $0: the script under such a shell if you do have one." fi exit 1 fi fi fi SHELL=${CONFIG_SHELL-/bin/sh} export SHELL # Unset more variables known to interfere with behavior of common tools. CLICOLOR_FORCE= GREP_OPTIONS= unset CLICOLOR_FORCE GREP_OPTIONS ## --------------------- ## ## M4sh Shell Functions. ## ## --------------------- ## # as_fn_unset VAR # --------------- # Portably unset VAR. as_fn_unset () { { eval $1=; unset $1;} } as_unset=as_fn_unset # as_fn_set_status STATUS # ----------------------- # Set $? to STATUS, without forking. as_fn_set_status () { return $1 } # as_fn_set_status # as_fn_exit STATUS # ----------------- # Exit the shell with STATUS, even in a "trap 0" or "set -e" context. as_fn_exit () { set +e as_fn_set_status $1 exit $1 } # as_fn_exit # as_fn_mkdir_p # ------------- # Create "$as_dir" as a directory, including parents if necessary. as_fn_mkdir_p () { case $as_dir in #( -*) as_dir=./$as_dir;; esac test -d "$as_dir" || eval $as_mkdir_p || { as_dirs= while :; do case $as_dir in #( *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( *) as_qdir=$as_dir;; esac as_dirs="'$as_qdir' $as_dirs" as_dir=`$as_dirname -- "$as_dir" || $as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_dir" : 'X\(//\)[^/]' \| \ X"$as_dir" : 'X\(//\)$' \| \ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_dir" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` test -d "$as_dir" && break done test -z "$as_dirs" || eval "mkdir $as_dirs" } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" } # as_fn_mkdir_p # as_fn_executable_p FILE # ----------------------- # Test if FILE is an executable regular file. as_fn_executable_p () { test -f "$1" && test -x "$1" } # as_fn_executable_p # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take # advantage of any shell optimizations that allow amortized linear growth over # repeated appends, instead of the typical quadratic growth present in naive # implementations. if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : eval 'as_fn_append () { eval $1+=\$2 }' else as_fn_append () { eval $1=\$$1\$2 } fi # as_fn_append # as_fn_arith ARG... # ------------------ # Perform arithmetic evaluation on the ARGs, and store the result in the # global $as_val. Take advantage of shells that can avoid forks. The arguments # must be portable across $(()) and expr. if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : eval 'as_fn_arith () { as_val=$(( $* )) }' else as_fn_arith () { as_val=`expr "$@" || test $? -eq 1` } fi # as_fn_arith # as_fn_error STATUS ERROR [LINENO LOG_FD] # ---------------------------------------- # Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are # provided, also output the error to LOG_FD, referencing LINENO. Then exit the # script with STATUS, using 1 if that was 0. as_fn_error () { as_status=$1; test $as_status -eq 0 && as_status=1 if test "$4"; then as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 fi $as_echo "$as_me: error: $2" >&2 as_fn_exit $as_status } # as_fn_error if expr a : '\(a\)' >/dev/null 2>&1 && test "X`expr 00001 : '.*\(...\)'`" = X001; then as_expr=expr else as_expr=false fi if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then as_basename=basename else as_basename=false fi if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then as_dirname=dirname else as_dirname=false fi as_me=`$as_basename -- "$0" || $as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ X"$0" : 'X\(//\)$' \| \ X"$0" : 'X\(/\)' \| . 2>/dev/null || $as_echo X/"$0" | sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/ q } /^X\/\(\/\/\)$/{ s//\1/ q } /^X\/\(\/\).*/{ s//\1/ q } s/.*/./; q'` # Avoid depending upon Character Ranges. as_cr_letters='abcdefghijklmnopqrstuvwxyz' as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' as_cr_Letters=$as_cr_letters$as_cr_LETTERS as_cr_digits='0123456789' as_cr_alnum=$as_cr_Letters$as_cr_digits as_lineno_1=$LINENO as_lineno_1a=$LINENO as_lineno_2=$LINENO as_lineno_2a=$LINENO eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" && test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || { # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-) sed -n ' p /[$]LINENO/= ' <$as_myself | sed ' s/[$]LINENO.*/&-/ t lineno b :lineno N :loop s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/ t loop s/-\n.*// ' >$as_me.lineno && chmod +x "$as_me.lineno" || { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; } # If we had to re-execute with $CONFIG_SHELL, we're ensured to have # already done that, so ensure we don't try to do so again and fall # in an infinite loop. This has already happened in practice. _as_can_reexec=no; export _as_can_reexec # Don't try to exec as it changes $[0], causing all sort of problems # (the dirname of $[0] is not the place where we might find the # original and so on. Autoconf is especially sensitive to this). . "./$as_me.lineno" # Exit status is that of the last command. exit } ECHO_C= ECHO_N= ECHO_T= case `echo -n x` in #((((( -n*) case `echo 'xy\c'` in *c*) ECHO_T=' ';; # ECHO_T is single tab character. xy) ECHO_C='\c';; *) echo `echo ksh88 bug on AIX 6.1` > /dev/null ECHO_T=' ';; esac;; *) ECHO_N='-n';; esac rm -f conf$$ conf$$.exe conf$$.file if test -d conf$$.dir; then rm -f conf$$.dir/conf$$.file else rm -f conf$$.dir mkdir conf$$.dir 2>/dev/null fi if (echo >conf$$.file) 2>/dev/null; then if ln -s conf$$.file conf$$ 2>/dev/null; then as_ln_s='ln -s' # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else as_ln_s='cp -pR' fi else as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null if mkdir -p . 2>/dev/null; then as_mkdir_p='mkdir -p "$as_dir"' else test -d ./-p && rmdir ./-p as_mkdir_p=false fi as_test_x='test -x' as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" test -n "$DJDIR" || exec 7<&0 &1 # Name of the host. # hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status, # so uname gets run too. ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q` # # Initializations. # ac_default_prefix=/usr/local ac_clean_files= ac_config_libobj_dir=. LIBOBJS= cross_compiling=no subdirs= MFLAGS= MAKEFLAGS= # Identity of this package. PACKAGE_NAME='units' PACKAGE_TARNAME='units' PACKAGE_VERSION='0.6-4' PACKAGE_STRING='units 0.6-4' PACKAGE_BUGREPORT='edzer.pebesma@uni-muenster.de' PACKAGE_URL='' # Factoring default headers for most tests. ac_includes_default="\ #include #ifdef HAVE_SYS_TYPES_H # include #endif #ifdef HAVE_SYS_STAT_H # include #endif #ifdef STDC_HEADERS # include # include #else # ifdef HAVE_STDLIB_H # include # endif #endif #ifdef HAVE_STRING_H # if !defined STDC_HEADERS && defined HAVE_MEMORY_H # include # endif # include #endif #ifdef HAVE_STRINGS_H # include #endif #ifdef HAVE_INTTYPES_H # include #endif #ifdef HAVE_STDINT_H # include #endif #ifdef HAVE_UNISTD_H # include #endif" ac_subst_vars='LTLIBOBJS UDUNITS2_DIR UD_CPPFLAGS ac_ct_CC CFLAGS CC LIBOBJS EGREP GREP CXXCPP OBJEXT EXEEXT ac_ct_CXX CPPFLAGS LDFLAGS CXXFLAGS CXX target_alias host_alias build_alias LIBS ECHO_T ECHO_N ECHO_C DEFS mandir localedir libdir psdir pdfdir dvidir htmldir infodir docdir oldincludedir includedir localstatedir sharedstatedir sysconfdir datadir datarootdir libexecdir sbindir bindir program_transform_name prefix exec_prefix PACKAGE_URL PACKAGE_BUGREPORT PACKAGE_STRING PACKAGE_VERSION PACKAGE_TARNAME PACKAGE_NAME PATH_SEPARATOR SHELL' ac_subst_files='' ac_user_opts=' enable_option_checking with_udunits2_include with_udunits2_lib ' ac_precious_vars='build_alias host_alias target_alias CXX CXXFLAGS LDFLAGS LIBS CPPFLAGS CCC CXXCPP CC CFLAGS' # Initialize some variables set by options. ac_init_help= ac_init_version=false ac_unrecognized_opts= ac_unrecognized_sep= # The variables have the same names as the options, with # dashes changed to underlines. cache_file=/dev/null exec_prefix=NONE no_create= no_recursion= prefix=NONE program_prefix=NONE program_suffix=NONE program_transform_name=s,x,x, silent= site= srcdir= verbose= x_includes=NONE x_libraries=NONE # Installation directory options. # These are left unexpanded so users can "make install exec_prefix=/foo" # and all the variables that are supposed to be based on exec_prefix # by default will actually change. # Use braces instead of parens because sh, perl, etc. also accept them. # (The list follows the same order as the GNU Coding Standards.) bindir='${exec_prefix}/bin' sbindir='${exec_prefix}/sbin' libexecdir='${exec_prefix}/libexec' datarootdir='${prefix}/share' datadir='${datarootdir}' sysconfdir='${prefix}/etc' sharedstatedir='${prefix}/com' localstatedir='${prefix}/var' includedir='${prefix}/include' oldincludedir='/usr/include' docdir='${datarootdir}/doc/${PACKAGE_TARNAME}' infodir='${datarootdir}/info' htmldir='${docdir}' dvidir='${docdir}' pdfdir='${docdir}' psdir='${docdir}' libdir='${exec_prefix}/lib' localedir='${datarootdir}/locale' mandir='${datarootdir}/man' ac_prev= ac_dashdash= for ac_option do # If the previous option needs an argument, assign it. if test -n "$ac_prev"; then eval $ac_prev=\$ac_option ac_prev= continue fi case $ac_option in *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;; *=) ac_optarg= ;; *) ac_optarg=yes ;; esac # Accept the important Cygnus configure options, so we can diagnose typos. case $ac_dashdash$ac_option in --) ac_dashdash=yes ;; -bindir | --bindir | --bindi | --bind | --bin | --bi) ac_prev=bindir ;; -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) bindir=$ac_optarg ;; -build | --build | --buil | --bui | --bu) ac_prev=build_alias ;; -build=* | --build=* | --buil=* | --bui=* | --bu=*) build_alias=$ac_optarg ;; -cache-file | --cache-file | --cache-fil | --cache-fi \ | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) ac_prev=cache_file ;; -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) cache_file=$ac_optarg ;; --config-cache | -C) cache_file=config.cache ;; -datadir | --datadir | --datadi | --datad) ac_prev=datadir ;; -datadir=* | --datadir=* | --datadi=* | --datad=*) datadir=$ac_optarg ;; -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \ | --dataroo | --dataro | --datar) ac_prev=datarootdir ;; -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \ | --dataroot=* | --dataroo=* | --dataro=* | --datar=*) datarootdir=$ac_optarg ;; -disable-* | --disable-*) ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid feature name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "enable_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval enable_$ac_useropt=no ;; -docdir | --docdir | --docdi | --doc | --do) ac_prev=docdir ;; -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*) docdir=$ac_optarg ;; -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv) ac_prev=dvidir ;; -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*) dvidir=$ac_optarg ;; -enable-* | --enable-*) ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid feature name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "enable_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval enable_$ac_useropt=\$ac_optarg ;; -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ | --exec | --exe | --ex) ac_prev=exec_prefix ;; -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ | --exec=* | --exe=* | --ex=*) exec_prefix=$ac_optarg ;; -gas | --gas | --ga | --g) # Obsolete; use --with-gas. with_gas=yes ;; -help | --help | --hel | --he | -h) ac_init_help=long ;; -help=r* | --help=r* | --hel=r* | --he=r* | -hr*) ac_init_help=recursive ;; -help=s* | --help=s* | --hel=s* | --he=s* | -hs*) ac_init_help=short ;; -host | --host | --hos | --ho) ac_prev=host_alias ;; -host=* | --host=* | --hos=* | --ho=*) host_alias=$ac_optarg ;; -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht) ac_prev=htmldir ;; -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \ | --ht=*) htmldir=$ac_optarg ;; -includedir | --includedir | --includedi | --included | --include \ | --includ | --inclu | --incl | --inc) ac_prev=includedir ;; -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ | --includ=* | --inclu=* | --incl=* | --inc=*) includedir=$ac_optarg ;; -infodir | --infodir | --infodi | --infod | --info | --inf) ac_prev=infodir ;; -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) infodir=$ac_optarg ;; -libdir | --libdir | --libdi | --libd) ac_prev=libdir ;; -libdir=* | --libdir=* | --libdi=* | --libd=*) libdir=$ac_optarg ;; -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ | --libexe | --libex | --libe) ac_prev=libexecdir ;; -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ | --libexe=* | --libex=* | --libe=*) libexecdir=$ac_optarg ;; -localedir | --localedir | --localedi | --localed | --locale) ac_prev=localedir ;; -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*) localedir=$ac_optarg ;; -localstatedir | --localstatedir | --localstatedi | --localstated \ | --localstate | --localstat | --localsta | --localst | --locals) ac_prev=localstatedir ;; -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*) localstatedir=$ac_optarg ;; -mandir | --mandir | --mandi | --mand | --man | --ma | --m) ac_prev=mandir ;; -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) mandir=$ac_optarg ;; -nfp | --nfp | --nf) # Obsolete; use --without-fp. with_fp=no ;; -no-create | --no-create | --no-creat | --no-crea | --no-cre \ | --no-cr | --no-c | -n) no_create=yes ;; -no-recursion | --no-recursion | --no-recursio | --no-recursi \ | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) no_recursion=yes ;; -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ | --oldin | --oldi | --old | --ol | --o) ac_prev=oldincludedir ;; -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) oldincludedir=$ac_optarg ;; -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) ac_prev=prefix ;; -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) prefix=$ac_optarg ;; -program-prefix | --program-prefix | --program-prefi | --program-pref \ | --program-pre | --program-pr | --program-p) ac_prev=program_prefix ;; -program-prefix=* | --program-prefix=* | --program-prefi=* \ | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) program_prefix=$ac_optarg ;; -program-suffix | --program-suffix | --program-suffi | --program-suff \ | --program-suf | --program-su | --program-s) ac_prev=program_suffix ;; -program-suffix=* | --program-suffix=* | --program-suffi=* \ | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) program_suffix=$ac_optarg ;; -program-transform-name | --program-transform-name \ | --program-transform-nam | --program-transform-na \ | --program-transform-n | --program-transform- \ | --program-transform | --program-transfor \ | --program-transfo | --program-transf \ | --program-trans | --program-tran \ | --progr-tra | --program-tr | --program-t) ac_prev=program_transform_name ;; -program-transform-name=* | --program-transform-name=* \ | --program-transform-nam=* | --program-transform-na=* \ | --program-transform-n=* | --program-transform-=* \ | --program-transform=* | --program-transfor=* \ | --program-transfo=* | --program-transf=* \ | --program-trans=* | --program-tran=* \ | --progr-tra=* | --program-tr=* | --program-t=*) program_transform_name=$ac_optarg ;; -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd) ac_prev=pdfdir ;; -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*) pdfdir=$ac_optarg ;; -psdir | --psdir | --psdi | --psd | --ps) ac_prev=psdir ;; -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*) psdir=$ac_optarg ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil) silent=yes ;; -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) ac_prev=sbindir ;; -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ | --sbi=* | --sb=*) sbindir=$ac_optarg ;; -sharedstatedir | --sharedstatedir | --sharedstatedi \ | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ | --sharedst | --shareds | --shared | --share | --shar \ | --sha | --sh) ac_prev=sharedstatedir ;; -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ | --sha=* | --sh=*) sharedstatedir=$ac_optarg ;; -site | --site | --sit) ac_prev=site ;; -site=* | --site=* | --sit=*) site=$ac_optarg ;; -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) ac_prev=srcdir ;; -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) srcdir=$ac_optarg ;; -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ | --syscon | --sysco | --sysc | --sys | --sy) ac_prev=sysconfdir ;; -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) sysconfdir=$ac_optarg ;; -target | --target | --targe | --targ | --tar | --ta | --t) ac_prev=target_alias ;; -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) target_alias=$ac_optarg ;; -v | -verbose | --verbose | --verbos | --verbo | --verb) verbose=yes ;; -version | --version | --versio | --versi | --vers | -V) ac_init_version=: ;; -with-* | --with-*) ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid package name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "with_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval with_$ac_useropt=\$ac_optarg ;; -without-* | --without-*) ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'` # Reject names that are not valid shell variable names. expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && as_fn_error $? "invalid package name: $ac_useropt" ac_useropt_orig=$ac_useropt ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` case $ac_user_opts in *" "with_$ac_useropt" "*) ;; *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig" ac_unrecognized_sep=', ';; esac eval with_$ac_useropt=no ;; --x) # Obsolete; use --with-x. with_x=yes ;; -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ | --x-incl | --x-inc | --x-in | --x-i) ac_prev=x_includes ;; -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) x_includes=$ac_optarg ;; -x-libraries | --x-libraries | --x-librarie | --x-librari \ | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) ac_prev=x_libraries ;; -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) x_libraries=$ac_optarg ;; -*) as_fn_error $? "unrecognized option: \`$ac_option' Try \`$0 --help' for more information" ;; *=*) ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='` # Reject names that are not valid shell variable names. case $ac_envvar in #( '' | [0-9]* | *[!_$as_cr_alnum]* ) as_fn_error $? "invalid variable name: \`$ac_envvar'" ;; esac eval $ac_envvar=\$ac_optarg export $ac_envvar ;; *) # FIXME: should be removed in autoconf 3.0. $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2 expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2 : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}" ;; esac done if test -n "$ac_prev"; then ac_option=--`echo $ac_prev | sed 's/_/-/g'` as_fn_error $? "missing argument to $ac_option" fi if test -n "$ac_unrecognized_opts"; then case $enable_option_checking in no) ;; fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;; *) $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;; esac fi # Check all directory arguments for consistency. for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \ datadir sysconfdir sharedstatedir localstatedir includedir \ oldincludedir docdir infodir htmldir dvidir pdfdir psdir \ libdir localedir mandir do eval ac_val=\$$ac_var # Remove trailing slashes. case $ac_val in */ ) ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'` eval $ac_var=\$ac_val;; esac # Be sure to have absolute directory names. case $ac_val in [\\/$]* | ?:[\\/]* ) continue;; NONE | '' ) case $ac_var in *prefix ) continue;; esac;; esac as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val" done # There might be people who depend on the old broken behavior: `$host' # used to hold the argument of --host etc. # FIXME: To remove some day. build=$build_alias host=$host_alias target=$target_alias # FIXME: To remove some day. if test "x$host_alias" != x; then if test "x$build_alias" = x; then cross_compiling=maybe elif test "x$build_alias" != "x$host_alias"; then cross_compiling=yes fi fi ac_tool_prefix= test -n "$host_alias" && ac_tool_prefix=$host_alias- test "$silent" = yes && exec 6>/dev/null ac_pwd=`pwd` && test -n "$ac_pwd" && ac_ls_di=`ls -di .` && ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` || as_fn_error $? "working directory cannot be determined" test "X$ac_ls_di" = "X$ac_pwd_ls_di" || as_fn_error $? "pwd does not report name of working directory" # Find the source files, if location was not specified. if test -z "$srcdir"; then ac_srcdir_defaulted=yes # Try the directory containing this script, then the parent directory. ac_confdir=`$as_dirname -- "$as_myself" || $as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_myself" : 'X\(//\)[^/]' \| \ X"$as_myself" : 'X\(//\)$' \| \ X"$as_myself" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_myself" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` srcdir=$ac_confdir if test ! -r "$srcdir/$ac_unique_file"; then srcdir=.. fi else ac_srcdir_defaulted=no fi if test ! -r "$srcdir/$ac_unique_file"; then test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .." as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir" fi ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work" ac_abs_confdir=`( cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg" pwd)` # When building in place, set srcdir=. if test "$ac_abs_confdir" = "$ac_pwd"; then srcdir=. fi # Remove unnecessary trailing slashes from srcdir. # Double slashes in file names in object file debugging info # mess up M-x gdb in Emacs. case $srcdir in */) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;; esac for ac_var in $ac_precious_vars; do eval ac_env_${ac_var}_set=\${${ac_var}+set} eval ac_env_${ac_var}_value=\$${ac_var} eval ac_cv_env_${ac_var}_set=\${${ac_var}+set} eval ac_cv_env_${ac_var}_value=\$${ac_var} done # # Report the --help message. # if test "$ac_init_help" = "long"; then # Omit some internal or obsolete options to make the list less imposing. # This message is too long to be a string in the A/UX 3.1 sh. cat <<_ACEOF \`configure' configures units 0.6-4 to adapt to many kinds of systems. Usage: $0 [OPTION]... [VAR=VALUE]... To assign environment variables (e.g., CC, CFLAGS...), specify them as VAR=VALUE. See below for descriptions of some of the useful variables. Defaults for the options are specified in brackets. Configuration: -h, --help display this help and exit --help=short display options specific to this package --help=recursive display the short help of all the included packages -V, --version display version information and exit -q, --quiet, --silent do not print \`checking ...' messages --cache-file=FILE cache test results in FILE [disabled] -C, --config-cache alias for \`--cache-file=config.cache' -n, --no-create do not create output files --srcdir=DIR find the sources in DIR [configure dir or \`..'] Installation directories: --prefix=PREFIX install architecture-independent files in PREFIX [$ac_default_prefix] --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX [PREFIX] By default, \`make install' will install all the files in \`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify an installation prefix other than \`$ac_default_prefix' using \`--prefix', for instance \`--prefix=\$HOME'. For better control, use the options below. Fine tuning of the installation directories: --bindir=DIR user executables [EPREFIX/bin] --sbindir=DIR system admin executables [EPREFIX/sbin] --libexecdir=DIR program executables [EPREFIX/libexec] --sysconfdir=DIR read-only single-machine data [PREFIX/etc] --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] --localstatedir=DIR modifiable single-machine data [PREFIX/var] --libdir=DIR object code libraries [EPREFIX/lib] --includedir=DIR C header files [PREFIX/include] --oldincludedir=DIR C header files for non-gcc [/usr/include] --datarootdir=DIR read-only arch.-independent data root [PREFIX/share] --datadir=DIR read-only architecture-independent data [DATAROOTDIR] --infodir=DIR info documentation [DATAROOTDIR/info] --localedir=DIR locale-dependent data [DATAROOTDIR/locale] --mandir=DIR man documentation [DATAROOTDIR/man] --docdir=DIR documentation root [DATAROOTDIR/doc/units] --htmldir=DIR html documentation [DOCDIR] --dvidir=DIR dvi documentation [DOCDIR] --pdfdir=DIR pdf documentation [DOCDIR] --psdir=DIR ps documentation [DOCDIR] _ACEOF cat <<\_ACEOF _ACEOF fi if test -n "$ac_init_help"; then case $ac_init_help in short | recursive ) echo "Configuration of units 0.6-4:";; esac cat <<\_ACEOF Optional Packages: --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) --with-udunits2-include=DIR location of the udunits2 header files --with-udunits2-lib=DIR location of the udunits2 libraries Some influential environment variables: CXX C++ compiler command CXXFLAGS C++ compiler flags LDFLAGS linker flags, e.g. -L if you have libraries in a nonstandard directory LIBS libraries to pass to the linker, e.g. -l CPPFLAGS (Objective) C/C++ preprocessor flags, e.g. -I if you have headers in a nonstandard directory CXXCPP C++ preprocessor CC C compiler command CFLAGS C compiler flags Use these variables to override the choices made by `configure' or to help it to find libraries and programs with nonstandard names/locations. Report bugs to . _ACEOF ac_status=$? fi if test "$ac_init_help" = "recursive"; then # If there are subdirs, report their specific --help. for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue test -d "$ac_dir" || { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } || continue ac_builddir=. case "$ac_dir" in .) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` # A ".." for each directory in $ac_dir_suffix. ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` case $ac_top_builddir_sub in "") ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; esac ;; esac ac_abs_top_builddir=$ac_pwd ac_abs_builddir=$ac_pwd$ac_dir_suffix # for backward compatibility: ac_top_builddir=$ac_top_build_prefix case $srcdir in .) # We are building in place. ac_srcdir=. ac_top_srcdir=$ac_top_builddir_sub ac_abs_top_srcdir=$ac_pwd ;; [\\/]* | ?:[\\/]* ) # Absolute name. ac_srcdir=$srcdir$ac_dir_suffix; ac_top_srcdir=$srcdir ac_abs_top_srcdir=$srcdir ;; *) # Relative name. ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix ac_top_srcdir=$ac_top_build_prefix$srcdir ac_abs_top_srcdir=$ac_pwd/$srcdir ;; esac ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix cd "$ac_dir" || { ac_status=$?; continue; } # Check for guested configure. if test -f "$ac_srcdir/configure.gnu"; then echo && $SHELL "$ac_srcdir/configure.gnu" --help=recursive elif test -f "$ac_srcdir/configure"; then echo && $SHELL "$ac_srcdir/configure" --help=recursive else $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2 fi || ac_status=$? cd "$ac_pwd" || { ac_status=$?; break; } done fi test -n "$ac_init_help" && exit $ac_status if $ac_init_version; then cat <<\_ACEOF units configure 0.6-4 generated by GNU Autoconf 2.69 Copyright (C) 2012 Free Software Foundation, Inc. This configure script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it. _ACEOF exit fi ## ------------------------ ## ## Autoconf initialization. ## ## ------------------------ ## # ac_fn_cxx_try_compile LINENO # ---------------------------- # Try to compile conftest.$ac_ext, and return whether this succeeded. ac_fn_cxx_try_compile () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack rm -f conftest.$ac_objext if { { ac_try="$ac_compile" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compile") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { test -z "$ac_cxx_werror_flag" || test ! -s conftest.err } && test -s conftest.$ac_objext; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_compile # ac_fn_cxx_check_type LINENO TYPE VAR INCLUDES # --------------------------------------------- # Tests whether TYPE exists after having included INCLUDES, setting cache # variable VAR accordingly. ac_fn_cxx_check_type () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else eval "$3=no" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { if (sizeof ($2)) return 0; ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 int main () { if (sizeof (($2))) return 0; ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : else eval "$3=yes" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_cxx_check_type # ac_fn_cxx_try_cpp LINENO # ------------------------ # Try to preprocess conftest.$ac_ext, and return whether this succeeded. ac_fn_cxx_try_cpp () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if { { ac_try="$ac_cpp conftest.$ac_ext" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_cpp conftest.$ac_ext") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } > conftest.i && { test -z "$ac_cxx_preproc_warn_flag$ac_cxx_werror_flag" || test ! -s conftest.err }; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_cpp # ac_fn_cxx_try_run LINENO # ------------------------ # Try to link conftest.$ac_ext, and return whether this succeeded. Assumes # that executables *can* be run. ac_fn_cxx_try_run () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { ac_try='./conftest$ac_exeext' { { case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_try") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; }; then : ac_retval=0 else $as_echo "$as_me: program exited with status $ac_status" >&5 $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=$ac_status fi rm -rf conftest.dSYM conftest_ipa8_conftest.oo eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_run # ac_fn_cxx_check_header_compile LINENO HEADER VAR INCLUDES # --------------------------------------------------------- # Tests whether HEADER exists and can be compiled using the include files in # INCLUDES, setting the cache variable VAR accordingly. ac_fn_cxx_check_header_compile () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 #include <$2> _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : eval "$3=yes" else eval "$3=no" fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_cxx_check_header_compile # ac_fn_cxx_try_link LINENO # ------------------------- # Try to link conftest.$ac_ext, and return whether this succeeded. ac_fn_cxx_try_link () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack rm -f conftest.$ac_objext conftest$ac_exeext if { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { test -z "$ac_cxx_werror_flag" || test ! -s conftest.err } && test -s conftest$ac_exeext && { test "$cross_compiling" = yes || test -x conftest$ac_exeext }; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi # Delete the IPA/IPO (Inter Procedural Analysis/Optimization) information # created by the PGI compiler (conftest_ipa8_conftest.oo), as it would # interfere with the next link command; also delete a directory that is # left behind by Apple's compiler. We do this before executing the actions. rm -rf conftest.dSYM conftest_ipa8_conftest.oo eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_cxx_try_link # ac_fn_c_try_compile LINENO # -------------------------- # Try to compile conftest.$ac_ext, and return whether this succeeded. ac_fn_c_try_compile () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack rm -f conftest.$ac_objext if { { ac_try="$ac_compile" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compile") 2>conftest.err ac_status=$? if test -s conftest.err; then grep -v '^ *+' conftest.err >conftest.er1 cat conftest.er1 >&5 mv -f conftest.er1 conftest.err fi $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } && { test -z "$ac_c_werror_flag" || test ! -s conftest.err } && test -s conftest.$ac_objext; then : ac_retval=0 else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 ac_retval=1 fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno as_fn_set_status $ac_retval } # ac_fn_c_try_compile # ac_fn_cxx_check_header_mongrel LINENO HEADER VAR INCLUDES # --------------------------------------------------------- # Tests whether HEADER exists, giving a warning if it cannot be compiled using # the include files in INCLUDES and setting the cache variable VAR # accordingly. ac_fn_cxx_check_header_mongrel () { as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack if eval \${$3+:} false; then : { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } else # Is the header compilable? { $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 usability" >&5 $as_echo_n "checking $2 usability... " >&6; } cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ $4 #include <$2> _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : ac_header_compiler=yes else ac_header_compiler=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_compiler" >&5 $as_echo "$ac_header_compiler" >&6; } # Is the header present? { $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 presence" >&5 $as_echo_n "checking $2 presence... " >&6; } cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include <$2> _ACEOF if ac_fn_cxx_try_cpp "$LINENO"; then : ac_header_preproc=yes else ac_header_preproc=no fi rm -f conftest.err conftest.i conftest.$ac_ext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_preproc" >&5 $as_echo "$ac_header_preproc" >&6; } # So? What about this header? case $ac_header_compiler:$ac_header_preproc:$ac_cxx_preproc_warn_flag in #(( yes:no: ) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&5 $as_echo "$as_me: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5 $as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;} ;; no:yes:* ) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: present but cannot be compiled" >&5 $as_echo "$as_me: WARNING: $2: present but cannot be compiled" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: check for missing prerequisite headers?" >&5 $as_echo "$as_me: WARNING: $2: check for missing prerequisite headers?" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: see the Autoconf documentation" >&5 $as_echo "$as_me: WARNING: $2: see the Autoconf documentation" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: section \"Present But Cannot Be Compiled\"" >&5 $as_echo "$as_me: WARNING: $2: section \"Present But Cannot Be Compiled\"" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5 $as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;} ( $as_echo "## -------------------------------------------- ## ## Report this to edzer.pebesma@uni-muenster.de ## ## -------------------------------------------- ##" ) | sed "s/^/$as_me: WARNING: /" >&2 ;; esac { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5 $as_echo_n "checking for $2... " >&6; } if eval \${$3+:} false; then : $as_echo_n "(cached) " >&6 else eval "$3=\$ac_header_compiler" fi eval ac_res=\$$3 { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5 $as_echo "$ac_res" >&6; } fi eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno } # ac_fn_cxx_check_header_mongrel cat >config.log <<_ACEOF This file contains any messages produced by compilers while running configure, to aid debugging if configure makes a mistake. It was created by units $as_me 0.6-4, which was generated by GNU Autoconf 2.69. Invocation command line was $ $0 $@ _ACEOF exec 5>>config.log { cat <<_ASUNAME ## --------- ## ## Platform. ## ## --------- ## hostname = `(hostname || uname -n) 2>/dev/null | sed 1q` uname -m = `(uname -m) 2>/dev/null || echo unknown` uname -r = `(uname -r) 2>/dev/null || echo unknown` uname -s = `(uname -s) 2>/dev/null || echo unknown` uname -v = `(uname -v) 2>/dev/null || echo unknown` /usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown` /bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown` /bin/arch = `(/bin/arch) 2>/dev/null || echo unknown` /usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown` /usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown` /usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown` /bin/machine = `(/bin/machine) 2>/dev/null || echo unknown` /usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown` /bin/universe = `(/bin/universe) 2>/dev/null || echo unknown` _ASUNAME as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. $as_echo "PATH: $as_dir" done IFS=$as_save_IFS } >&5 cat >&5 <<_ACEOF ## ----------- ## ## Core tests. ## ## ----------- ## _ACEOF # Keep a trace of the command line. # Strip out --no-create and --no-recursion so they do not pile up. # Strip out --silent because we don't want to record it for future runs. # Also quote any args containing shell meta-characters. # Make two passes to allow for proper duplicate-argument suppression. ac_configure_args= ac_configure_args0= ac_configure_args1= ac_must_keep_next=false for ac_pass in 1 2 do for ac_arg do case $ac_arg in -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil) continue ;; *\'*) ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; esac case $ac_pass in 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;; 2) as_fn_append ac_configure_args1 " '$ac_arg'" if test $ac_must_keep_next = true; then ac_must_keep_next=false # Got value, back to normal. else case $ac_arg in *=* | --config-cache | -C | -disable-* | --disable-* \ | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \ | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \ | -with-* | --with-* | -without-* | --without-* | --x) case "$ac_configure_args0 " in "$ac_configure_args1"*" '$ac_arg' "* ) continue ;; esac ;; -* ) ac_must_keep_next=true ;; esac fi as_fn_append ac_configure_args " '$ac_arg'" ;; esac done done { ac_configure_args0=; unset ac_configure_args0;} { ac_configure_args1=; unset ac_configure_args1;} # When interrupted or exit'd, cleanup temporary files, and complete # config.log. We remove comments because anyway the quotes in there # would cause problems or look ugly. # WARNING: Use '\'' to represent an apostrophe within the trap. # WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug. trap 'exit_status=$? # Save into config.log some information that might help in debugging. { echo $as_echo "## ---------------- ## ## Cache variables. ## ## ---------------- ##" echo # The following way of writing the cache mishandles newlines in values, ( for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do eval ac_val=\$$ac_var case $ac_val in #( *${as_nl}*) case $ac_var in #( *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; esac case $ac_var in #( _ | IFS | as_nl) ;; #( BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( *) { eval $ac_var=; unset $ac_var;} ;; esac ;; esac done (set) 2>&1 | case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #( *${as_nl}ac_space=\ *) sed -n \ "s/'\''/'\''\\\\'\'''\''/g; s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p" ;; #( *) sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" ;; esac | sort ) echo $as_echo "## ----------------- ## ## Output variables. ## ## ----------------- ##" echo for ac_var in $ac_subst_vars do eval ac_val=\$$ac_var case $ac_val in *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; esac $as_echo "$ac_var='\''$ac_val'\''" done | sort echo if test -n "$ac_subst_files"; then $as_echo "## ------------------- ## ## File substitutions. ## ## ------------------- ##" echo for ac_var in $ac_subst_files do eval ac_val=\$$ac_var case $ac_val in *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; esac $as_echo "$ac_var='\''$ac_val'\''" done | sort echo fi if test -s confdefs.h; then $as_echo "## ----------- ## ## confdefs.h. ## ## ----------- ##" echo cat confdefs.h echo fi test "$ac_signal" != 0 && $as_echo "$as_me: caught signal $ac_signal" $as_echo "$as_me: exit $exit_status" } >&5 rm -f core *.core core.conftest.* && rm -f -r conftest* confdefs* conf$$* $ac_clean_files && exit $exit_status ' 0 for ac_signal in 1 2 13 15; do trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal done ac_signal=0 # confdefs.h avoids OS command line length limits that DEFS can exceed. rm -f -r conftest* confdefs.h $as_echo "/* confdefs.h */" > confdefs.h # Predefined preprocessor variables. cat >>confdefs.h <<_ACEOF #define PACKAGE_NAME "$PACKAGE_NAME" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_TARNAME "$PACKAGE_TARNAME" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_VERSION "$PACKAGE_VERSION" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_STRING "$PACKAGE_STRING" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT" _ACEOF cat >>confdefs.h <<_ACEOF #define PACKAGE_URL "$PACKAGE_URL" _ACEOF # Let the site file select an alternate cache file if it wants to. # Prefer an explicitly selected file to automatically selected ones. ac_site_file1=NONE ac_site_file2=NONE if test -n "$CONFIG_SITE"; then # We do not want a PATH search for config.site. case $CONFIG_SITE in #(( -*) ac_site_file1=./$CONFIG_SITE;; */*) ac_site_file1=$CONFIG_SITE;; *) ac_site_file1=./$CONFIG_SITE;; esac elif test "x$prefix" != xNONE; then ac_site_file1=$prefix/share/config.site ac_site_file2=$prefix/etc/config.site else ac_site_file1=$ac_default_prefix/share/config.site ac_site_file2=$ac_default_prefix/etc/config.site fi for ac_site_file in "$ac_site_file1" "$ac_site_file2" do test "x$ac_site_file" = xNONE && continue if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5 $as_echo "$as_me: loading site script $ac_site_file" >&6;} sed 's/^/| /' "$ac_site_file" >&5 . "$ac_site_file" \ || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "failed to load site script $ac_site_file See \`config.log' for more details" "$LINENO" 5; } fi done if test -r "$cache_file"; then # Some versions of bash will fail to source /dev/null (special files # actually), so we avoid doing that. DJGPP emulates it as a regular file. if test /dev/null != "$cache_file" && test -f "$cache_file"; then { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5 $as_echo "$as_me: loading cache $cache_file" >&6;} case $cache_file in [\\/]* | ?:[\\/]* ) . "$cache_file";; *) . "./$cache_file";; esac fi else { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5 $as_echo "$as_me: creating cache $cache_file" >&6;} >$cache_file fi # Check that the precious variables saved in the cache have kept the same # value. ac_cache_corrupted=false for ac_var in $ac_precious_vars; do eval ac_old_set=\$ac_cv_env_${ac_var}_set eval ac_new_set=\$ac_env_${ac_var}_set eval ac_old_val=\$ac_cv_env_${ac_var}_value eval ac_new_val=\$ac_env_${ac_var}_value case $ac_old_set,$ac_new_set in set,) { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5 $as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;} ac_cache_corrupted=: ;; ,set) { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5 $as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;} ac_cache_corrupted=: ;; ,);; *) if test "x$ac_old_val" != "x$ac_new_val"; then # differences in whitespace do not lead to failure. ac_old_val_w=`echo x $ac_old_val` ac_new_val_w=`echo x $ac_new_val` if test "$ac_old_val_w" != "$ac_new_val_w"; then { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5 $as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;} ac_cache_corrupted=: else { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5 $as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;} eval $ac_var=\$ac_old_val fi { $as_echo "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5 $as_echo "$as_me: former value: \`$ac_old_val'" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5 $as_echo "$as_me: current value: \`$ac_new_val'" >&2;} fi;; esac # Pass precious variables to config.status. if test "$ac_new_set" = set; then case $ac_new_val in *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;; *) ac_arg=$ac_var=$ac_new_val ;; esac case " $ac_configure_args " in *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy. *) as_fn_append ac_configure_args " '$ac_arg'" ;; esac fi done if $ac_cache_corrupted; then { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5 $as_echo "$as_me: error: changes in the environment can compromise the build" >&2;} as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5 fi ## -------------------- ## ## Main body of script. ## ## -------------------- ## ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: ${PACKAGE_NAME}: ${PACKAGE_VERSION}" >&5 $as_echo "$as_me: ${PACKAGE_NAME}: ${PACKAGE_VERSION}" >&6;} : ${R_HOME=`R RHOME`} if test -z "${R_HOME}"; then echo "could not determine R_HOME" exit 1 fi CC=`"${R_HOME}/bin/R" CMD config CC` CFLAGS=`"${R_HOME}/bin/R" CMD config CFLAGS` CPPFLAGS=`"${R_HOME}/bin/R" CMD config CPPFLAGS` LDFLAGS=`"${R_HOME}/bin/R" CMD config LDFLAGS` CXX=`"${R_HOME}/bin/R" CMD config CXX` CXXFLAGS=`"${R_HOME}/bin/R" CMD config CXXFLAGS` ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_cxx_compiler_gnu ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_cxx_compiler_gnu if test -z "$CXX"; then if test -n "$CCC"; then CXX=$CCC else if test -n "$ac_tool_prefix"; then for ac_prog in g++ c++ gpp aCC CC cxx cc++ cl.exe FCC KCC RCC xlC_r xlC do # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CXX"; then ac_cv_prog_CXX="$CXX" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CXX="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CXX=$ac_cv_prog_CXX if test -n "$CXX"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CXX" >&5 $as_echo "$CXX" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$CXX" && break done fi if test -z "$CXX"; then ac_ct_CXX=$CXX for ac_prog in g++ c++ gpp aCC CC cxx cc++ cl.exe FCC KCC RCC xlC_r xlC do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_CXX+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CXX"; then ac_cv_prog_ac_ct_CXX="$ac_ct_CXX" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CXX="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_CXX=$ac_cv_prog_ac_ct_CXX if test -n "$ac_ct_CXX"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CXX" >&5 $as_echo "$ac_ct_CXX" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$ac_ct_CXX" && break done if test "x$ac_ct_CXX" = x; then CXX="g++" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac CXX=$ac_ct_CXX fi fi fi fi # Provide some information about the compiler. $as_echo "$as_me:${as_lineno-$LINENO}: checking for C++ compiler version" >&5 set X $ac_compile ac_compiler=$2 for ac_option in --version -v -V -qversion; do { { ac_try="$ac_compiler $ac_option >&5" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compiler $ac_option >&5") 2>conftest.err ac_status=$? if test -s conftest.err; then sed '10a\ ... rest of stderr output deleted ... 10q' conftest.err >conftest.er1 cat conftest.er1 >&5 fi rm -f conftest.er1 conftest.err $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } done cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF ac_clean_files_save=$ac_clean_files ac_clean_files="$ac_clean_files a.out a.out.dSYM a.exe b.out" # Try to create an executable without -o first, disregard a.out. # It will help us diagnose broken compilers, and finding out an intuition # of exeext. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C++ compiler works" >&5 $as_echo_n "checking whether the C++ compiler works... " >&6; } ac_link_default=`$as_echo "$ac_link" | sed 's/ -o *conftest[^ ]*//'` # The possible output files: ac_files="a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*" ac_rmfiles= for ac_file in $ac_files do case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; * ) ac_rmfiles="$ac_rmfiles $ac_file";; esac done rm -f $ac_rmfiles if { { ac_try="$ac_link_default" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link_default") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then : # Autoconf-2.13 could set the ac_cv_exeext variable to `no'. # So ignore a value of `no', otherwise this would lead to `EXEEXT = no' # in a Makefile. We should not override ac_cv_exeext if it was cached, # so that the user can short-circuit this test for compilers unknown to # Autoconf. for ac_file in $ac_files '' do test -f "$ac_file" || continue case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; [ab].out ) # We found the default executable, but exeext='' is most # certainly right. break;; *.* ) if test "${ac_cv_exeext+set}" = set && test "$ac_cv_exeext" != no; then :; else ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` fi # We set ac_cv_exeext here because the later test for it is not # safe: cross compilers may not add the suffix if given an `-o' # argument, so we may need to know it at that point already. # Even if this section looks crufty: it has the advantage of # actually working. break;; * ) break;; esac done test "$ac_cv_exeext" = no && ac_cv_exeext= else ac_file='' fi if test -z "$ac_file"; then : { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error 77 "C++ compiler cannot create executables See \`config.log' for more details" "$LINENO" 5; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 $as_echo "yes" >&6; } fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for C++ compiler default output file name" >&5 $as_echo_n "checking for C++ compiler default output file name... " >&6; } { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_file" >&5 $as_echo "$ac_file" >&6; } ac_exeext=$ac_cv_exeext rm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out ac_clean_files=$ac_clean_files_save { $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of executables" >&5 $as_echo_n "checking for suffix of executables... " >&6; } if { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then : # If both `conftest.exe' and `conftest' are `present' (well, observable) # catch `conftest.exe'. For instance with Cygwin, `ls conftest' will # work properly (i.e., refer to `conftest.exe'), while it won't with # `rm'. for ac_file in conftest.exe conftest conftest.*; do test -f "$ac_file" || continue case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` break;; * ) break;; esac done else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot compute suffix of executables: cannot compile and link See \`config.log' for more details" "$LINENO" 5; } fi rm -f conftest conftest$ac_cv_exeext { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5 $as_echo "$ac_cv_exeext" >&6; } rm -f conftest.$ac_ext EXEEXT=$ac_cv_exeext ac_exeext=$EXEEXT cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include int main () { FILE *f = fopen ("conftest.out", "w"); return ferror (f) || fclose (f) != 0; ; return 0; } _ACEOF ac_clean_files="$ac_clean_files conftest.out" # Check that the compiler produces executables we can run. If not, either # the compiler is broken, or we cross compile. { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling" >&5 $as_echo_n "checking whether we are cross compiling... " >&6; } if test "$cross_compiling" != yes; then { { ac_try="$ac_link" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_link") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } if { ac_try='./conftest$ac_cv_exeext' { { case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_try") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; }; then cross_compiling=no else if test "$cross_compiling" = maybe; then cross_compiling=yes else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot run C++ compiled programs. If you meant to cross compile, use \`--host'. See \`config.log' for more details" "$LINENO" 5; } fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $cross_compiling" >&5 $as_echo "$cross_compiling" >&6; } rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out ac_clean_files=$ac_clean_files_save { $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5 $as_echo_n "checking for suffix of object files... " >&6; } if ${ac_cv_objext+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF rm -f conftest.o conftest.obj if { { ac_try="$ac_compile" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compile") 2>&5 ac_status=$? $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; }; then : for ac_file in conftest.o conftest.obj conftest.*; do test -f "$ac_file" || continue; case $ac_file in *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;; *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'` break;; esac done else $as_echo "$as_me: failed program was:" >&5 sed 's/^/| /' conftest.$ac_ext >&5 { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "cannot compute suffix of object files: cannot compile See \`config.log' for more details" "$LINENO" 5; } fi rm -f conftest.$ac_cv_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext" >&5 $as_echo "$ac_cv_objext" >&6; } OBJEXT=$ac_cv_objext ac_objext=$OBJEXT { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C++ compiler" >&5 $as_echo_n "checking whether we are using the GNU C++ compiler... " >&6; } if ${ac_cv_cxx_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { #ifndef __GNUC__ choke me #endif ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : ac_compiler_gnu=yes else ac_compiler_gnu=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ac_cv_cxx_compiler_gnu=$ac_compiler_gnu fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_cxx_compiler_gnu" >&5 $as_echo "$ac_cv_cxx_compiler_gnu" >&6; } if test $ac_compiler_gnu = yes; then GXX=yes else GXX= fi ac_test_CXXFLAGS=${CXXFLAGS+set} ac_save_CXXFLAGS=$CXXFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CXX accepts -g" >&5 $as_echo_n "checking whether $CXX accepts -g... " >&6; } if ${ac_cv_prog_cxx_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_cxx_werror_flag=$ac_cxx_werror_flag ac_cxx_werror_flag=yes ac_cv_prog_cxx_g=no CXXFLAGS="-g" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : ac_cv_prog_cxx_g=yes else CXXFLAGS="" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : else ac_cxx_werror_flag=$ac_save_cxx_werror_flag CXXFLAGS="-g" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : ac_cv_prog_cxx_g=yes fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ac_cxx_werror_flag=$ac_save_cxx_werror_flag fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cxx_g" >&5 $as_echo "$ac_cv_prog_cxx_g" >&6; } if test "$ac_test_CXXFLAGS" = set; then CXXFLAGS=$ac_save_CXXFLAGS elif test $ac_cv_prog_cxx_g = yes; then if test "$GXX" = yes; then CXXFLAGS="-g -O2" else CXXFLAGS="-g" fi else if test "$GXX" = yes; then CXXFLAGS="-O2" else CXXFLAGS= fi fi ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_cxx_compiler_gnu ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_cxx_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking how to run the C++ preprocessor" >&5 $as_echo_n "checking how to run the C++ preprocessor... " >&6; } if test -z "$CXXCPP"; then if ${ac_cv_prog_CXXCPP+:} false; then : $as_echo_n "(cached) " >&6 else # Double quotes because CXXCPP needs to be expanded for CXXCPP in "$CXX -E" "/lib/cpp" do ac_preproc_ok=false for ac_cxx_preproc_warn_flag in '' yes do # Use a header file that comes with gcc, so configuring glibc # with a fresh cross-compiler works. # Prefer to if __STDC__ is defined, since # exists even on freestanding compilers. # On the NeXT, cc -E runs the code through the compiler's parser, # not just through cpp. "Syntax error" is here to catch this case. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifdef __STDC__ # include #else # include #endif Syntax error _ACEOF if ac_fn_cxx_try_cpp "$LINENO"; then : else # Broken: fails on valid input. continue fi rm -f conftest.err conftest.i conftest.$ac_ext # OK, works on sane cases. Now check whether nonexistent headers # can be detected and how. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if ac_fn_cxx_try_cpp "$LINENO"; then : # Broken: success on invalid input. continue else # Passes both tests. ac_preproc_ok=: break fi rm -f conftest.err conftest.i conftest.$ac_ext done # Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. rm -f conftest.i conftest.err conftest.$ac_ext if $ac_preproc_ok; then : break fi done ac_cv_prog_CXXCPP=$CXXCPP fi CXXCPP=$ac_cv_prog_CXXCPP else ac_cv_prog_CXXCPP=$CXXCPP fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CXXCPP" >&5 $as_echo "$CXXCPP" >&6; } ac_preproc_ok=false for ac_cxx_preproc_warn_flag in '' yes do # Use a header file that comes with gcc, so configuring glibc # with a fresh cross-compiler works. # Prefer to if __STDC__ is defined, since # exists even on freestanding compilers. # On the NeXT, cc -E runs the code through the compiler's parser, # not just through cpp. "Syntax error" is here to catch this case. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #ifdef __STDC__ # include #else # include #endif Syntax error _ACEOF if ac_fn_cxx_try_cpp "$LINENO"; then : else # Broken: fails on valid input. continue fi rm -f conftest.err conftest.i conftest.$ac_ext # OK, works on sane cases. Now check whether nonexistent headers # can be detected and how. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if ac_fn_cxx_try_cpp "$LINENO"; then : # Broken: success on invalid input. continue else # Passes both tests. ac_preproc_ok=: break fi rm -f conftest.err conftest.i conftest.$ac_ext done # Because of `break', _AC_PREPROC_IFELSE's cleaning code was skipped. rm -f conftest.i conftest.err conftest.$ac_ext if $ac_preproc_ok; then : else { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "C++ preprocessor \"$CXXCPP\" fails sanity check See \`config.log' for more details" "$LINENO" 5; } fi ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_cxx_compiler_gnu { $as_echo "$as_me:${as_lineno-$LINENO}: checking for grep that handles long lines and -e" >&5 $as_echo_n "checking for grep that handles long lines and -e... " >&6; } if ${ac_cv_path_GREP+:} false; then : $as_echo_n "(cached) " >&6 else if test -z "$GREP"; then ac_path_GREP_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in grep ggrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_GREP="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_GREP" || continue # Check for GNU ac_path_GREP and select it if it is found. # Check for GNU $ac_path_GREP case `"$ac_path_GREP" --version 2>&1` in *GNU*) ac_cv_path_GREP="$ac_path_GREP" ac_path_GREP_found=:;; *) ac_count=0 $as_echo_n 0123456789 >"conftest.in" while : do cat "conftest.in" "conftest.in" >"conftest.tmp" mv "conftest.tmp" "conftest.in" cp "conftest.in" "conftest.nl" $as_echo 'GREP' >> "conftest.nl" "$ac_path_GREP" -e 'GREP$' -e '-(cannot match)-' < "conftest.nl" >"conftest.out" 2>/dev/null || break diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break as_fn_arith $ac_count + 1 && ac_count=$as_val if test $ac_count -gt ${ac_path_GREP_max-0}; then # Best one so far, save it but keep looking for a better one ac_cv_path_GREP="$ac_path_GREP" ac_path_GREP_max=$ac_count fi # 10*(2^10) chars as input seems more than enough test $ac_count -gt 10 && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out;; esac $ac_path_GREP_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_GREP"; then as_fn_error $? "no acceptable grep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 fi else ac_cv_path_GREP=$GREP fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_GREP" >&5 $as_echo "$ac_cv_path_GREP" >&6; } GREP="$ac_cv_path_GREP" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for egrep" >&5 $as_echo_n "checking for egrep... " >&6; } if ${ac_cv_path_EGREP+:} false; then : $as_echo_n "(cached) " >&6 else if echo a | $GREP -E '(a|b)' >/dev/null 2>&1 then ac_cv_path_EGREP="$GREP -E" else if test -z "$EGREP"; then ac_path_EGREP_found=false # Loop through the user's path and test for each of PROGNAME-LIST as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_prog in egrep; do for ac_exec_ext in '' $ac_executable_extensions; do ac_path_EGREP="$as_dir/$ac_prog$ac_exec_ext" as_fn_executable_p "$ac_path_EGREP" || continue # Check for GNU ac_path_EGREP and select it if it is found. # Check for GNU $ac_path_EGREP case `"$ac_path_EGREP" --version 2>&1` in *GNU*) ac_cv_path_EGREP="$ac_path_EGREP" ac_path_EGREP_found=:;; *) ac_count=0 $as_echo_n 0123456789 >"conftest.in" while : do cat "conftest.in" "conftest.in" >"conftest.tmp" mv "conftest.tmp" "conftest.in" cp "conftest.in" "conftest.nl" $as_echo 'EGREP' >> "conftest.nl" "$ac_path_EGREP" 'EGREP$' < "conftest.nl" >"conftest.out" 2>/dev/null || break diff "conftest.out" "conftest.nl" >/dev/null 2>&1 || break as_fn_arith $ac_count + 1 && ac_count=$as_val if test $ac_count -gt ${ac_path_EGREP_max-0}; then # Best one so far, save it but keep looking for a better one ac_cv_path_EGREP="$ac_path_EGREP" ac_path_EGREP_max=$ac_count fi # 10*(2^10) chars as input seems more than enough test $ac_count -gt 10 && break done rm -f conftest.in conftest.tmp conftest.nl conftest.out;; esac $ac_path_EGREP_found && break 3 done done done IFS=$as_save_IFS if test -z "$ac_cv_path_EGREP"; then as_fn_error $? "no acceptable egrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin" "$LINENO" 5 fi else ac_cv_path_EGREP=$EGREP fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_EGREP" >&5 $as_echo "$ac_cv_path_EGREP" >&6; } EGREP="$ac_cv_path_EGREP" { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ANSI C header files" >&5 $as_echo_n "checking for ANSI C header files... " >&6; } if ${ac_cv_header_stdc+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #include #include int main () { ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : ac_cv_header_stdc=yes else ac_cv_header_stdc=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext if test $ac_cv_header_stdc = yes; then # SunOS 4.x string.h does not declare mem*, contrary to ANSI. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "memchr" >/dev/null 2>&1; then : else ac_cv_header_stdc=no fi rm -f conftest* fi if test $ac_cv_header_stdc = yes; then # ISC 2.0.2 stdlib.h does not declare free, contrary to ANSI. cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include _ACEOF if (eval "$ac_cpp conftest.$ac_ext") 2>&5 | $EGREP "free" >/dev/null 2>&1; then : else ac_cv_header_stdc=no fi rm -f conftest* fi if test $ac_cv_header_stdc = yes; then # /bin/cc in Irix-4.0.5 gets non-ANSI ctype macros unless using -ansi. if test "$cross_compiling" = yes; then : : else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include #if ((' ' & 0x0FF) == 0x020) # define ISLOWER(c) ('a' <= (c) && (c) <= 'z') # define TOUPPER(c) (ISLOWER(c) ? 'A' + ((c) - 'a') : (c)) #else # define ISLOWER(c) \ (('a' <= (c) && (c) <= 'i') \ || ('j' <= (c) && (c) <= 'r') \ || ('s' <= (c) && (c) <= 'z')) # define TOUPPER(c) (ISLOWER(c) ? ((c) | 0x40) : (c)) #endif #define XOR(e, f) (((e) && !(f)) || (!(e) && (f))) int main () { int i; for (i = 0; i < 256; i++) if (XOR (islower (i), ISLOWER (i)) || toupper (i) != TOUPPER (i)) return 2; return 0; } _ACEOF if ac_fn_cxx_try_run "$LINENO"; then : else ac_cv_header_stdc=no fi rm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \ conftest.$ac_objext conftest.beam conftest.$ac_ext fi fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdc" >&5 $as_echo "$ac_cv_header_stdc" >&6; } if test $ac_cv_header_stdc = yes; then $as_echo "#define STDC_HEADERS 1" >>confdefs.h fi # On IRIX 5.3, sys/types and inttypes.h are conflicting. for ac_header in sys/types.h sys/stat.h stdlib.h string.h memory.h strings.h \ inttypes.h stdint.h unistd.h do : as_ac_Header=`$as_echo "ac_cv_header_$ac_header" | $as_tr_sh` ac_fn_cxx_check_header_compile "$LINENO" "$ac_header" "$as_ac_Header" "$ac_includes_default " if eval test \"x\$"$as_ac_Header"\" = x"yes"; then : cat >>confdefs.h <<_ACEOF #define `$as_echo "HAVE_$ac_header" | $as_tr_cpp` 1 _ACEOF fi done { $as_echo "$as_me:${as_lineno-$LINENO}: checking for stdbool.h that conforms to C99" >&5 $as_echo_n "checking for stdbool.h that conforms to C99... " >&6; } if ${ac_cv_header_stdbool_h+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #ifndef bool "error: bool is not defined" #endif #ifndef false "error: false is not defined" #endif #if false "error: false is not 0" #endif #ifndef true "error: true is not defined" #endif #if true != 1 "error: true is not 1" #endif #ifndef __bool_true_false_are_defined "error: __bool_true_false_are_defined is not defined" #endif struct s { _Bool s: 1; _Bool t; } s; char a[true == 1 ? 1 : -1]; char b[false == 0 ? 1 : -1]; char c[__bool_true_false_are_defined == 1 ? 1 : -1]; char d[(bool) 0.5 == true ? 1 : -1]; /* See body of main program for 'e'. */ char f[(_Bool) 0.0 == false ? 1 : -1]; char g[true]; char h[sizeof (_Bool)]; char i[sizeof s.t]; enum { j = false, k = true, l = false * true, m = true * 256 }; /* The following fails for HP aC++/ANSI C B3910B A.05.55 [Dec 04 2003]. */ _Bool n[m]; char o[sizeof n == m * sizeof n[0] ? 1 : -1]; char p[-1 - (_Bool) 0 < 0 && -1 - (bool) 0 < 0 ? 1 : -1]; /* Catch a bug in an HP-UX C compiler. See http://gcc.gnu.org/ml/gcc-patches/2003-12/msg02303.html http://lists.gnu.org/archive/html/bug-coreutils/2005-11/msg00161.html */ _Bool q = true; _Bool *pq = &q; int main () { bool e = &s; *pq |= q; *pq |= ! q; /* Refer to every declared value, to avoid compiler optimizations. */ return (!a + !b + !c + !d + !e + !f + !g + !h + !i + !!j + !k + !!l + !m + !n + !o + !p + !q + !pq); ; return 0; } _ACEOF if ac_fn_cxx_try_compile "$LINENO"; then : ac_cv_header_stdbool_h=yes else ac_cv_header_stdbool_h=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdbool_h" >&5 $as_echo "$ac_cv_header_stdbool_h" >&6; } ac_fn_cxx_check_type "$LINENO" "_Bool" "ac_cv_type__Bool" "$ac_includes_default" if test "x$ac_cv_type__Bool" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE__BOOL 1 _ACEOF fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for error_at_line" >&5 $as_echo_n "checking for error_at_line... " >&6; } if ${ac_cv_lib_error_at_line+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include int main () { error_at_line (0, 0, "", 0, "an error occurred"); ; return 0; } _ACEOF if ac_fn_cxx_try_link "$LINENO"; then : ac_cv_lib_error_at_line=yes else ac_cv_lib_error_at_line=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_error_at_line" >&5 $as_echo "$ac_cv_lib_error_at_line" >&6; } if test $ac_cv_lib_error_at_line = no; then case " $LIBOBJS " in *" error.$ac_objext "* ) ;; *) LIBOBJS="$LIBOBJS error.$ac_objext" ;; esac fi ac_ext=c ac_cpp='$CPP $CPPFLAGS' ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_c_compiler_gnu if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args. set dummy ${ac_tool_prefix}gcc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="${ac_tool_prefix}gcc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$ac_cv_prog_CC"; then ac_ct_CC=$CC # Extract the first word of "gcc", so it can be a program name with args. set dummy gcc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CC"; then ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CC="gcc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_CC=$ac_cv_prog_ac_ct_CC if test -n "$ac_ct_CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 $as_echo "$ac_ct_CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi if test "x$ac_ct_CC" = x; then CC="" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac CC=$ac_ct_CC fi else CC="$ac_cv_prog_CC" fi if test -z "$CC"; then if test -n "$ac_tool_prefix"; then # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args. set dummy ${ac_tool_prefix}cc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="${ac_tool_prefix}cc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi fi if test -z "$CC"; then # Extract the first word of "cc", so it can be a program name with args. set dummy cc; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else ac_prog_rejected=no as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then ac_prog_rejected=yes continue fi ac_cv_prog_CC="cc" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS if test $ac_prog_rejected = yes; then # We found a bogon in the path, so make sure we never use it. set dummy $ac_cv_prog_CC shift if test $# != 0; then # We chose a different compiler from the bogus one. # However, it has the same basename, so the bogon will be chosen # first if we set CC to just the basename; use the full file name. shift ac_cv_prog_CC="$as_dir/$ac_word${1+' '}$@" fi fi fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi fi if test -z "$CC"; then if test -n "$ac_tool_prefix"; then for ac_prog in cl.exe do # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. set dummy $ac_tool_prefix$ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$CC"; then ac_cv_prog_CC="$CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_CC="$ac_tool_prefix$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi CC=$ac_cv_prog_CC if test -n "$CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 $as_echo "$CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$CC" && break done fi if test -z "$CC"; then ac_ct_CC=$CC for ac_prog in cl.exe do # Extract the first word of "$ac_prog", so it can be a program name with args. set dummy $ac_prog; ac_word=$2 { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 $as_echo_n "checking for $ac_word... " >&6; } if ${ac_cv_prog_ac_ct_CC+:} false; then : $as_echo_n "(cached) " >&6 else if test -n "$ac_ct_CC"; then ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. else as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. for ac_exec_ext in '' $ac_executable_extensions; do if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then ac_cv_prog_ac_ct_CC="$ac_prog" $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 break 2 fi done done IFS=$as_save_IFS fi fi ac_ct_CC=$ac_cv_prog_ac_ct_CC if test -n "$ac_ct_CC"; then { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 $as_echo "$ac_ct_CC" >&6; } else { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 $as_echo "no" >&6; } fi test -n "$ac_ct_CC" && break done if test "x$ac_ct_CC" = x; then CC="" else case $cross_compiling:$ac_tool_warned in yes:) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 $as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} ac_tool_warned=yes ;; esac CC=$ac_ct_CC fi fi fi test -z "$CC" && { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? "no acceptable C compiler found in \$PATH See \`config.log' for more details" "$LINENO" 5; } # Provide some information about the compiler. $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5 set X $ac_compile ac_compiler=$2 for ac_option in --version -v -V -qversion; do { { ac_try="$ac_compiler $ac_option >&5" case "(($ac_try" in *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; *) ac_try_echo=$ac_try;; esac eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" $as_echo "$ac_try_echo"; } >&5 (eval "$ac_compiler $ac_option >&5") 2>conftest.err ac_status=$? if test -s conftest.err; then sed '10a\ ... rest of stderr output deleted ... 10q' conftest.err >conftest.er1 cat conftest.er1 >&5 fi rm -f conftest.er1 conftest.err $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 test $ac_status = 0; } done { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C compiler" >&5 $as_echo_n "checking whether we are using the GNU C compiler... " >&6; } if ${ac_cv_c_compiler_gnu+:} false; then : $as_echo_n "(cached) " >&6 else cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { #ifndef __GNUC__ choke me #endif ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_compiler_gnu=yes else ac_compiler_gnu=no fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ac_cv_c_compiler_gnu=$ac_compiler_gnu fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu" >&5 $as_echo "$ac_cv_c_compiler_gnu" >&6; } if test $ac_compiler_gnu = yes; then GCC=yes else GCC= fi ac_test_CFLAGS=${CFLAGS+set} ac_save_CFLAGS=$CFLAGS { $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5 $as_echo_n "checking whether $CC accepts -g... " >&6; } if ${ac_cv_prog_cc_g+:} false; then : $as_echo_n "(cached) " >&6 else ac_save_c_werror_flag=$ac_c_werror_flag ac_c_werror_flag=yes ac_cv_prog_cc_g=no CFLAGS="-g" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_prog_cc_g=yes else CFLAGS="" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : else ac_c_werror_flag=$ac_save_c_werror_flag CFLAGS="-g" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ int main () { ; return 0; } _ACEOF if ac_fn_c_try_compile "$LINENO"; then : ac_cv_prog_cc_g=yes fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext fi rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext ac_c_werror_flag=$ac_save_c_werror_flag fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g" >&5 $as_echo "$ac_cv_prog_cc_g" >&6; } if test "$ac_test_CFLAGS" = set; then CFLAGS=$ac_save_CFLAGS elif test $ac_cv_prog_cc_g = yes; then if test "$GCC" = yes; then CFLAGS="-g -O2" else CFLAGS="-g" fi else if test "$GCC" = yes; then CFLAGS="-O2" else CFLAGS= fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C89" >&5 $as_echo_n "checking for $CC option to accept ISO C89... " >&6; } if ${ac_cv_prog_cc_c89+:} false; then : $as_echo_n "(cached) " >&6 else ac_cv_prog_cc_c89=no ac_save_CC=$CC cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ #include #include struct stat; /* Most of the following tests are stolen from RCS 5.7's src/conf.sh. */ struct buf { int x; }; FILE * (*rcsopen) (struct buf *, struct stat *, int); static char *e (p, i) char **p; int i; { return p[i]; } static char *f (char * (*g) (char **, int), char **p, ...) { char *s; va_list v; va_start (v,p); s = g (p, va_arg (v,int)); va_end (v); return s; } /* OSF 4.0 Compaq cc is some sort of almost-ANSI by default. It has function prototypes and stuff, but not '\xHH' hex character constants. These don't provoke an error unfortunately, instead are silently treated as 'x'. The following induces an error, until -std is added to get proper ANSI mode. Curiously '\x00'!='x' always comes out true, for an array size at least. It's necessary to write '\x00'==0 to get something that's true only with -std. */ int osf4_cc_array ['\x00' == 0 ? 1 : -1]; /* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters inside strings and character constants. */ #define FOO(x) 'x' int xlc6_cc_array[FOO(a) == 'x' ? 1 : -1]; int test (int i, double x); struct s1 {int (*f) (int a);}; struct s2 {int (*f) (double a);}; int pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int); int argc; char **argv; int main () { return f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1]; ; return 0; } _ACEOF for ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std \ -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__" do CC="$ac_save_CC $ac_arg" if ac_fn_c_try_compile "$LINENO"; then : ac_cv_prog_cc_c89=$ac_arg fi rm -f core conftest.err conftest.$ac_objext test "x$ac_cv_prog_cc_c89" != "xno" && break done rm -f conftest.$ac_ext CC=$ac_save_CC fi # AC_CACHE_VAL case "x$ac_cv_prog_cc_c89" in x) { $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5 $as_echo "none needed" >&6; } ;; xno) { $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5 $as_echo "unsupported" >&6; } ;; *) CC="$CC $ac_cv_prog_cc_c89" { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89" >&5 $as_echo "$ac_cv_prog_cc_c89" >&6; } ;; esac if test "x$ac_cv_prog_cc_c89" != xno; then : fi ac_ext=cpp ac_cpp='$CXXCPP $CPPFLAGS' ac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5' ac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' ac_compiler_gnu=$ac_cv_cxx_compiler_gnu # Check whether --with-udunits2-include was given. if test "${with_udunits2_include+set}" = set; then : withval=$with_udunits2_include; udunits2_include_path=$withval fi if test -n "$udunits2_include_path" ; then UD_CPPFLAGS="-I${udunits2_include_path}" else if test -n "${UDUNITS2_INCLUDE}" ; then UD_CPPFLAGS="-I${UDUNITS2_INCLUDE}" fi fi # Check whether --with-udunits2-lib was given. if test "${with_udunits2_lib+set}" = set; then : withval=$with_udunits2_lib; udunits2_lib_path=$withval fi if test -n "$udunits2_lib_path" ; then LIBS="-L${udunits2_lib_path} ${LIBS}" else if test -n "${UDUNITS2_LIBS}" ; then LIBS="-L${UDUNITS2_LIBS} ${LIBS}" fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for XML_ParserCreate in -lexpat" >&5 $as_echo_n "checking for XML_ParserCreate in -lexpat... " >&6; } if ${ac_cv_lib_expat_XML_ParserCreate+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-lexpat ${LIBS} $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char XML_ParserCreate (); int main () { return XML_ParserCreate (); ; return 0; } _ACEOF if ac_fn_cxx_try_link "$LINENO"; then : ac_cv_lib_expat_XML_ParserCreate=yes else ac_cv_lib_expat_XML_ParserCreate=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_expat_XML_ParserCreate" >&5 $as_echo "$ac_cv_lib_expat_XML_ParserCreate" >&6; } if test "x$ac_cv_lib_expat_XML_ParserCreate" = xyes; then : cat >>confdefs.h <<_ACEOF #define HAVE_LIBEXPAT 1 _ACEOF LIBS="-lexpat $LIBS" fi if test "${ac_cv_lib_expat_XML_ParserCreate}" == yes; then LIBS="${LIBS} -lexpat" fi CPPFLAGS="${UD_CPPFLAGS} ${CPPFLAGS}" ac_fn_cxx_check_header_mongrel "$LINENO" "udunits2.h" "ac_cv_header_udunits2_h" "$ac_includes_default" if test "x$ac_cv_header_udunits2_h" = xyes; then : UDUNITS2_DIR=0 else ac_fn_cxx_check_header_mongrel "$LINENO" "udunits2/udunits2.h" "ac_cv_header_udunits2_udunits2_h" "$ac_includes_default" if test "x$ac_cv_header_udunits2_udunits2_h" = xyes; then : UDUNITS2_DIR=1 else UD_ERROR="udunits2.h was not found" fi fi { $as_echo "$as_me:${as_lineno-$LINENO}: checking for ut_read_xml in -ludunits2" >&5 $as_echo_n "checking for ut_read_xml in -ludunits2... " >&6; } if ${ac_cv_lib_udunits2_ut_read_xml+:} false; then : $as_echo_n "(cached) " >&6 else ac_check_lib_save_LIBS=$LIBS LIBS="-ludunits2 $LIBS" cat confdefs.h - <<_ACEOF >conftest.$ac_ext /* end confdefs.h. */ /* Override any GCC internal prototype to avoid an error. Use char because int might match the return type of a GCC builtin and then its argument prototype would still apply. */ #ifdef __cplusplus extern "C" #endif char ut_read_xml (); int main () { return ut_read_xml (); ; return 0; } _ACEOF if ac_fn_cxx_try_link "$LINENO"; then : ac_cv_lib_udunits2_ut_read_xml=yes else ac_cv_lib_udunits2_ut_read_xml=no fi rm -f core conftest.err conftest.$ac_objext \ conftest$ac_exeext conftest.$ac_ext LIBS=$ac_check_lib_save_LIBS fi { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_udunits2_ut_read_xml" >&5 $as_echo "$ac_cv_lib_udunits2_ut_read_xml" >&6; } if test "x$ac_cv_lib_udunits2_ut_read_xml" = xyes; then : LIBS="${LIBS} -ludunits2" else UD_ERROR="libudunits2.so was not found" fi if test "${UD_ERROR}" != "" ; then { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 $as_echo "$as_me: error: in \`$ac_pwd':" >&2;} as_fn_error $? " -------------------------------------------------------------------------------- Configuration failed because ${UD_ERROR}. Try installing: * deb: libudunits2-dev (Debian, Ubuntu, ...) * rpm: udunits2-devel (Fedora, EPEL, ...) * brew: udunits (OSX) If udunits2 is already installed in a non-standard location, use: --configure-args='--with-udunits2-lib=/usr/local/lib' if the library was not found, and/or: --configure-args='--with-udunits2-include=/usr/include/udunits2' if the header was not found, replacing paths with appropriate values. You can alternatively set UDUNITS2_INCLUDE and UDUNITS2_LIBS manually. -------------------------------------------------------------------------------- See \`config.log' for more details" "$LINENO" 5; } fi UD_CPPFLAGS="${UD_CPPFLAGS} ${CPPFLAGS}" ac_config_files="$ac_config_files src/Makevars" cat >confcache <<\_ACEOF # This file is a shell script that caches the results of configure # tests run on this system so they can be shared between configure # scripts and configure runs, see configure's option --config-cache. # It is not useful on other systems. If it contains results you don't # want to keep, you may remove or edit it. # # config.status only pays attention to the cache file if you give it # the --recheck option to rerun configure. # # `ac_cv_env_foo' variables (set or unset) will be overridden when # loading this file, other *unset* `ac_cv_foo' will be assigned the # following values. _ACEOF # The following way of writing the cache mishandles newlines in values, # but we know of no workaround that is simple, portable, and efficient. # So, we kill variables containing newlines. # Ultrix sh set writes to stderr and can't be redirected directly, # and sets the high bit in the cache file unless we assign to the vars. ( for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do eval ac_val=\$$ac_var case $ac_val in #( *${as_nl}*) case $ac_var in #( *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 $as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; esac case $ac_var in #( _ | IFS | as_nl) ;; #( BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( *) { eval $ac_var=; unset $ac_var;} ;; esac ;; esac done (set) 2>&1 | case $as_nl`(ac_space=' '; set) 2>&1` in #( *${as_nl}ac_space=\ *) # `set' does not quote correctly, so add quotes: double-quote # substitution turns \\\\ into \\, and sed turns \\ into \. sed -n \ "s/'/'\\\\''/g; s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p" ;; #( *) # `set' quotes correctly as required by POSIX, so do not add quotes. sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" ;; esac | sort ) | sed ' /^ac_cv_env_/b end t clear :clear s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/ t end s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/ :end' >>confcache if diff "$cache_file" confcache >/dev/null 2>&1; then :; else if test -w "$cache_file"; then if test "x$cache_file" != "x/dev/null"; then { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5 $as_echo "$as_me: updating cache $cache_file" >&6;} if test ! -f "$cache_file" || test -h "$cache_file"; then cat confcache >"$cache_file" else case $cache_file in #( */* | ?:*) mv -f confcache "$cache_file"$$ && mv -f "$cache_file"$$ "$cache_file" ;; #( *) mv -f confcache "$cache_file" ;; esac fi fi else { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5 $as_echo "$as_me: not updating unwritable cache $cache_file" >&6;} fi fi rm -f confcache test "x$prefix" = xNONE && prefix=$ac_default_prefix # Let make expand exec_prefix. test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' # Transform confdefs.h into DEFS. # Protect against shell expansion while executing Makefile rules. # Protect against Makefile macro expansion. # # If the first sed substitution is executed (which looks for macros that # take arguments), then branch to the quote section. Otherwise, # look for a macro that doesn't take arguments. ac_script=' :mline /\\$/{ N s,\\\n,, b mline } t clear :clear s/^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*([^)]*)\)[ ]*\(.*\)/-D\1=\2/g t quote s/^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\)/-D\1=\2/g t quote b any :quote s/[ `~#$^&*(){}\\|;'\''"<>?]/\\&/g s/\[/\\&/g s/\]/\\&/g s/\$/$$/g H :any ${ g s/^\n// s/\n/ /g p } ' DEFS=`sed -n "$ac_script" confdefs.h` ac_libobjs= ac_ltlibobjs= U= for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue # 1. Remove the extension, and $U if already installed. ac_script='s/\$U\././;s/\.o$//;s/\.obj$//' ac_i=`$as_echo "$ac_i" | sed "$ac_script"` # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR # will be set to the directory where LIBOBJS objects are built. as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext" as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo' done LIBOBJS=$ac_libobjs LTLIBOBJS=$ac_ltlibobjs : "${CONFIG_STATUS=./config.status}" ac_write_fail=0 ac_clean_files_save=$ac_clean_files ac_clean_files="$ac_clean_files $CONFIG_STATUS" { $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5 $as_echo "$as_me: creating $CONFIG_STATUS" >&6;} as_write_fail=0 cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1 #! $SHELL # Generated by $as_me. # Run this file to recreate the current configuration. # Compiler output produced by configure, useful for debugging # configure, is in config.log if it exists. debug=false ac_cs_recheck=false ac_cs_silent=false SHELL=\${CONFIG_SHELL-$SHELL} export SHELL _ASEOF cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1 ## -------------------- ## ## M4sh Initialization. ## ## -------------------- ## # Be more Bourne compatible DUALCASE=1; export DUALCASE # for MKS sh if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : emulate sh NULLCMD=: # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which # is contrary to our usage. Disable this feature. alias -g '${1+"$@"}'='"$@"' setopt NO_GLOB_SUBST else case `(set -o) 2>/dev/null` in #( *posix*) : set -o posix ;; #( *) : ;; esac fi as_nl=' ' export as_nl # Printing a long string crashes Solaris 7 /usr/bin/printf. as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo # Prefer a ksh shell builtin over an external printf program on Solaris, # but without wasting forks for bash or zsh. if test -z "$BASH_VERSION$ZSH_VERSION" \ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='print -r --' as_echo_n='print -rn --' elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then as_echo='printf %s\n' as_echo_n='printf %s' else if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' as_echo_n='/usr/ucb/echo -n' else as_echo_body='eval expr "X$1" : "X\\(.*\\)"' as_echo_n_body='eval arg=$1; case $arg in #( *"$as_nl"*) expr "X$arg" : "X\\(.*\\)$as_nl"; arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; esac; expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" ' export as_echo_n_body as_echo_n='sh -c $as_echo_n_body as_echo' fi export as_echo_body as_echo='sh -c $as_echo_body as_echo' fi # The user is always right. if test "${PATH_SEPARATOR+set}" != set; then PATH_SEPARATOR=: (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || PATH_SEPARATOR=';' } fi # IFS # We need space, tab and new line, in precisely that order. Quoting is # there to prevent editors from complaining about space-tab. # (If _AS_PATH_WALK were called with IFS unset, it would disable word # splitting by setting IFS to empty value.) IFS=" "" $as_nl" # Find who we are. Look in the path if we contain no directory separator. as_myself= case $0 in #(( *[\\/]* ) as_myself=$0 ;; *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR for as_dir in $PATH do IFS=$as_save_IFS test -z "$as_dir" && as_dir=. test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break done IFS=$as_save_IFS ;; esac # We did not find ourselves, most probably we were run as `sh COMMAND' # in which case we are not to be found in the path. if test "x$as_myself" = x; then as_myself=$0 fi if test ! -f "$as_myself"; then $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 exit 1 fi # Unset variables that we do not need and which cause bugs (e.g. in # pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" # suppresses any "Segmentation fault" message there. '((' could # trigger a bug in pdksh 5.2.14. for as_var in BASH_ENV ENV MAIL MAILPATH do eval test x\${$as_var+set} = xset \ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : done PS1='$ ' PS2='> ' PS4='+ ' # NLS nuisances. LC_ALL=C export LC_ALL LANGUAGE=C export LANGUAGE # CDPATH. (unset CDPATH) >/dev/null 2>&1 && unset CDPATH # as_fn_error STATUS ERROR [LINENO LOG_FD] # ---------------------------------------- # Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are # provided, also output the error to LOG_FD, referencing LINENO. Then exit the # script with STATUS, using 1 if that was 0. as_fn_error () { as_status=$1; test $as_status -eq 0 && as_status=1 if test "$4"; then as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 fi $as_echo "$as_me: error: $2" >&2 as_fn_exit $as_status } # as_fn_error # as_fn_set_status STATUS # ----------------------- # Set $? to STATUS, without forking. as_fn_set_status () { return $1 } # as_fn_set_status # as_fn_exit STATUS # ----------------- # Exit the shell with STATUS, even in a "trap 0" or "set -e" context. as_fn_exit () { set +e as_fn_set_status $1 exit $1 } # as_fn_exit # as_fn_unset VAR # --------------- # Portably unset VAR. as_fn_unset () { { eval $1=; unset $1;} } as_unset=as_fn_unset # as_fn_append VAR VALUE # ---------------------- # Append the text in VALUE to the end of the definition contained in VAR. Take # advantage of any shell optimizations that allow amortized linear growth over # repeated appends, instead of the typical quadratic growth present in naive # implementations. if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : eval 'as_fn_append () { eval $1+=\$2 }' else as_fn_append () { eval $1=\$$1\$2 } fi # as_fn_append # as_fn_arith ARG... # ------------------ # Perform arithmetic evaluation on the ARGs, and store the result in the # global $as_val. Take advantage of shells that can avoid forks. The arguments # must be portable across $(()) and expr. if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : eval 'as_fn_arith () { as_val=$(( $* )) }' else as_fn_arith () { as_val=`expr "$@" || test $? -eq 1` } fi # as_fn_arith if expr a : '\(a\)' >/dev/null 2>&1 && test "X`expr 00001 : '.*\(...\)'`" = X001; then as_expr=expr else as_expr=false fi if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then as_basename=basename else as_basename=false fi if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then as_dirname=dirname else as_dirname=false fi as_me=`$as_basename -- "$0" || $as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ X"$0" : 'X\(//\)$' \| \ X"$0" : 'X\(/\)' \| . 2>/dev/null || $as_echo X/"$0" | sed '/^.*\/\([^/][^/]*\)\/*$/{ s//\1/ q } /^X\/\(\/\/\)$/{ s//\1/ q } /^X\/\(\/\).*/{ s//\1/ q } s/.*/./; q'` # Avoid depending upon Character Ranges. as_cr_letters='abcdefghijklmnopqrstuvwxyz' as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' as_cr_Letters=$as_cr_letters$as_cr_LETTERS as_cr_digits='0123456789' as_cr_alnum=$as_cr_Letters$as_cr_digits ECHO_C= ECHO_N= ECHO_T= case `echo -n x` in #((((( -n*) case `echo 'xy\c'` in *c*) ECHO_T=' ';; # ECHO_T is single tab character. xy) ECHO_C='\c';; *) echo `echo ksh88 bug on AIX 6.1` > /dev/null ECHO_T=' ';; esac;; *) ECHO_N='-n';; esac rm -f conf$$ conf$$.exe conf$$.file if test -d conf$$.dir; then rm -f conf$$.dir/conf$$.file else rm -f conf$$.dir mkdir conf$$.dir 2>/dev/null fi if (echo >conf$$.file) 2>/dev/null; then if ln -s conf$$.file conf$$ 2>/dev/null; then as_ln_s='ln -s' # ... but there are two gotchas: # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. # In both cases, we have to default to `cp -pR'. ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || as_ln_s='cp -pR' elif ln conf$$.file conf$$ 2>/dev/null; then as_ln_s=ln else as_ln_s='cp -pR' fi else as_ln_s='cp -pR' fi rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file rmdir conf$$.dir 2>/dev/null # as_fn_mkdir_p # ------------- # Create "$as_dir" as a directory, including parents if necessary. as_fn_mkdir_p () { case $as_dir in #( -*) as_dir=./$as_dir;; esac test -d "$as_dir" || eval $as_mkdir_p || { as_dirs= while :; do case $as_dir in #( *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( *) as_qdir=$as_dir;; esac as_dirs="'$as_qdir' $as_dirs" as_dir=`$as_dirname -- "$as_dir" || $as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$as_dir" : 'X\(//\)[^/]' \| \ X"$as_dir" : 'X\(//\)$' \| \ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$as_dir" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` test -d "$as_dir" && break done test -z "$as_dirs" || eval "mkdir $as_dirs" } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" } # as_fn_mkdir_p if mkdir -p . 2>/dev/null; then as_mkdir_p='mkdir -p "$as_dir"' else test -d ./-p && rmdir ./-p as_mkdir_p=false fi # as_fn_executable_p FILE # ----------------------- # Test if FILE is an executable regular file. as_fn_executable_p () { test -f "$1" && test -x "$1" } # as_fn_executable_p as_test_x='test -x' as_executable_p=as_fn_executable_p # Sed expression to map a string onto a valid CPP name. as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" # Sed expression to map a string onto a valid variable name. as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" exec 6>&1 ## ----------------------------------- ## ## Main body of $CONFIG_STATUS script. ## ## ----------------------------------- ## _ASEOF test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1 cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Save the log message, to keep $0 and so on meaningful, and to # report actual input values of CONFIG_FILES etc. instead of their # values after options handling. ac_log=" This file was extended by units $as_me 0.6-4, which was generated by GNU Autoconf 2.69. Invocation command line was CONFIG_FILES = $CONFIG_FILES CONFIG_HEADERS = $CONFIG_HEADERS CONFIG_LINKS = $CONFIG_LINKS CONFIG_COMMANDS = $CONFIG_COMMANDS $ $0 $@ on `(hostname || uname -n) 2>/dev/null | sed 1q` " _ACEOF case $ac_config_files in *" "*) set x $ac_config_files; shift; ac_config_files=$*;; esac cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 # Files that config.status was made for. config_files="$ac_config_files" _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 ac_cs_usage="\ \`$as_me' instantiates files and other configuration actions from templates according to the current configuration. Unless the files and actions are specified as TAGs, all are instantiated by default. Usage: $0 [OPTION]... [TAG]... -h, --help print this help, then exit -V, --version print version number and configuration settings, then exit --config print configuration, then exit -q, --quiet, --silent do not print progress messages -d, --debug don't remove temporary files --recheck update $as_me by reconfiguring in the same conditions --file=FILE[:TEMPLATE] instantiate the configuration file FILE Configuration files: $config_files Report bugs to ." _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" ac_cs_version="\\ units config.status 0.6-4 configured by $0, generated by GNU Autoconf 2.69, with options \\"\$ac_cs_config\\" Copyright (C) 2012 Free Software Foundation, Inc. This config.status script is free software; the Free Software Foundation gives unlimited permission to copy, distribute and modify it." ac_pwd='$ac_pwd' srcdir='$srcdir' test -n "\$AWK" || AWK=awk _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # The default lists apply if the user does not specify any file. ac_need_defaults=: while test $# != 0 do case $1 in --*=?*) ac_option=`expr "X$1" : 'X\([^=]*\)='` ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'` ac_shift=: ;; --*=) ac_option=`expr "X$1" : 'X\([^=]*\)='` ac_optarg= ac_shift=: ;; *) ac_option=$1 ac_optarg=$2 ac_shift=shift ;; esac case $ac_option in # Handling of the options. -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) ac_cs_recheck=: ;; --version | --versio | --versi | --vers | --ver | --ve | --v | -V ) $as_echo "$ac_cs_version"; exit ;; --config | --confi | --conf | --con | --co | --c ) $as_echo "$ac_cs_config"; exit ;; --debug | --debu | --deb | --de | --d | -d ) debug=: ;; --file | --fil | --fi | --f ) $ac_shift case $ac_optarg in *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; '') as_fn_error $? "missing file argument" ;; esac as_fn_append CONFIG_FILES " '$ac_optarg'" ac_need_defaults=false;; --he | --h | --help | --hel | -h ) $as_echo "$ac_cs_usage"; exit ;; -q | -quiet | --quiet | --quie | --qui | --qu | --q \ | -silent | --silent | --silen | --sile | --sil | --si | --s) ac_cs_silent=: ;; # This is an error. -*) as_fn_error $? "unrecognized option: \`$1' Try \`$0 --help' for more information." ;; *) as_fn_append ac_config_targets " $1" ac_need_defaults=false ;; esac shift done ac_configure_extra_args= if $ac_cs_silent; then exec 6>/dev/null ac_configure_extra_args="$ac_configure_extra_args --silent" fi _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 if \$ac_cs_recheck; then set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion shift \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6 CONFIG_SHELL='$SHELL' export CONFIG_SHELL exec "\$@" fi _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 exec 5>>config.log { echo sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX ## Running $as_me. ## _ASBOX $as_echo "$ac_log" } >&5 _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # Handling of arguments. for ac_config_target in $ac_config_targets do case $ac_config_target in "src/Makevars") CONFIG_FILES="$CONFIG_FILES src/Makevars" ;; *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;; esac done # If the user did not use the arguments to specify the items to instantiate, # then the envvar interface is used. Set only those that are not. # We use the long form for the default assignment because of an extremely # bizarre bug on SunOS 4.1.3. if $ac_need_defaults; then test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files fi # Have a temporary directory for convenience. Make it in the build tree # simply because there is no reason against having it here, and in addition, # creating and moving files from /tmp can sometimes cause problems. # Hook for its removal unless debugging. # Note that there is a small window in which the directory will not be cleaned: # after its creation but before its name has been assigned to `$tmp'. $debug || { tmp= ac_tmp= trap 'exit_status=$? : "${ac_tmp:=$tmp}" { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status ' 0 trap 'as_fn_exit 1' 1 2 13 15 } # Create a (secure) tmp directory for tmp files. { tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` && test -d "$tmp" } || { tmp=./conf$$-$RANDOM (umask 077 && mkdir "$tmp") } || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5 ac_tmp=$tmp # Set up the scripts for CONFIG_FILES section. # No need to generate them if there are no CONFIG_FILES. # This happens for instance with `./config.status config.h'. if test -n "$CONFIG_FILES"; then ac_cr=`echo X | tr X '\015'` # On cygwin, bash can eat \r inside `` if the user requested igncr. # But we know of no other shell where ac_cr would be empty at this # point, so we can use a bashism as a fallback. if test "x$ac_cr" = x; then eval ac_cr=\$\'\\r\' fi ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' /dev/null` if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then ac_cs_awk_cr='\\r' else ac_cs_awk_cr=$ac_cr fi echo 'BEGIN {' >"$ac_tmp/subs1.awk" && _ACEOF { echo "cat >conf$$subs.awk <<_ACEOF" && echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' && echo "_ACEOF" } >conf$$subs.sh || as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'` ac_delim='%!_!# ' for ac_last_try in false false false false false :; do . ./conf$$subs.sh || as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X` if test $ac_delim_n = $ac_delim_num; then break elif $ac_last_try; then as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 else ac_delim="$ac_delim!$ac_delim _$ac_delim!! " fi done rm -f conf$$subs.sh cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK && _ACEOF sed -n ' h s/^/S["/; s/!.*/"]=/ p g s/^[^!]*!// :repl t repl s/'"$ac_delim"'$// t delim :nl h s/\(.\{148\}\)..*/\1/ t more1 s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/ p n b repl :more1 s/["\\]/\\&/g; s/^/"/; s/$/"\\/ p g s/.\{148\}// t nl :delim h s/\(.\{148\}\)..*/\1/ t more2 s/["\\]/\\&/g; s/^/"/; s/$/"/ p b :more2 s/["\\]/\\&/g; s/^/"/; s/$/"\\/ p g s/.\{148\}// t delim ' >$CONFIG_STATUS || ac_write_fail=1 rm -f conf$$subs.awk cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 _ACAWK cat >>"\$ac_tmp/subs1.awk" <<_ACAWK && for (key in S) S_is_set[key] = 1 FS = "" } { line = $ 0 nfields = split(line, field, "@") substed = 0 len = length(field[1]) for (i = 2; i < nfields; i++) { key = field[i] keylen = length(key) if (S_is_set[key]) { value = S[key] line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3) len += length(value) + length(field[++i]) substed = 1 } else len += 1 + keylen } print line } _ACAWK _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g" else cat fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \ || as_fn_error $? "could not setup config files machinery" "$LINENO" 5 _ACEOF # VPATH may cause trouble with some makes, so we remove sole $(srcdir), # ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and # trailing colons and then remove the whole line if VPATH becomes empty # (actually we leave an empty line to preserve line numbers). if test "x$srcdir" = x.; then ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{ h s/// s/^/:/ s/[ ]*$/:/ s/:\$(srcdir):/:/g s/:\${srcdir}:/:/g s/:@srcdir@:/:/g s/^:*// s/:*$// x s/\(=[ ]*\).*/\1/ G s/\n// s/^[^=]*=[ ]*$// }' fi cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 fi # test -n "$CONFIG_FILES" eval set X " :F $CONFIG_FILES " shift for ac_tag do case $ac_tag in :[FHLC]) ac_mode=$ac_tag; continue;; esac case $ac_mode$ac_tag in :[FHL]*:*);; :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;; :[FH]-) ac_tag=-:-;; :[FH]*) ac_tag=$ac_tag:$ac_tag.in;; esac ac_save_IFS=$IFS IFS=: set x $ac_tag IFS=$ac_save_IFS shift ac_file=$1 shift case $ac_mode in :L) ac_source=$1;; :[FH]) ac_file_inputs= for ac_f do case $ac_f in -) ac_f="$ac_tmp/stdin";; *) # Look for the file first in the build tree, then in the source tree # (if the path is not absolute). The absolute path cannot be DOS-style, # because $ac_f cannot contain `:'. test -f "$ac_f" || case $ac_f in [\\/$]*) false;; *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";; esac || as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;; esac case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac as_fn_append ac_file_inputs " '$ac_f'" done # Let's still pretend it is `configure' which instantiates (i.e., don't # use $as_me), people would be surprised to read: # /* config.h. Generated by config.status. */ configure_input='Generated from '` $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g' `' by configure.' if test x"$ac_file" != x-; then configure_input="$ac_file. $configure_input" { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5 $as_echo "$as_me: creating $ac_file" >&6;} fi # Neutralize special characters interpreted by sed in replacement strings. case $configure_input in #( *\&* | *\|* | *\\* ) ac_sed_conf_input=`$as_echo "$configure_input" | sed 's/[\\\\&|]/\\\\&/g'`;; #( *) ac_sed_conf_input=$configure_input;; esac case $ac_tag in *:-:* | *:-) cat >"$ac_tmp/stdin" \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; esac ;; esac ac_dir=`$as_dirname -- "$ac_file" || $as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ X"$ac_file" : 'X\(//\)[^/]' \| \ X"$ac_file" : 'X\(//\)$' \| \ X"$ac_file" : 'X\(/\)' \| . 2>/dev/null || $as_echo X"$ac_file" | sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ s//\1/ q } /^X\(\/\/\)[^/].*/{ s//\1/ q } /^X\(\/\/\)$/{ s//\1/ q } /^X\(\/\).*/{ s//\1/ q } s/.*/./; q'` as_dir="$ac_dir"; as_fn_mkdir_p ac_builddir=. case "$ac_dir" in .) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` # A ".." for each directory in $ac_dir_suffix. ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` case $ac_top_builddir_sub in "") ac_top_builddir_sub=. ac_top_build_prefix= ;; *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; esac ;; esac ac_abs_top_builddir=$ac_pwd ac_abs_builddir=$ac_pwd$ac_dir_suffix # for backward compatibility: ac_top_builddir=$ac_top_build_prefix case $srcdir in .) # We are building in place. ac_srcdir=. ac_top_srcdir=$ac_top_builddir_sub ac_abs_top_srcdir=$ac_pwd ;; [\\/]* | ?:[\\/]* ) # Absolute name. ac_srcdir=$srcdir$ac_dir_suffix; ac_top_srcdir=$srcdir ac_abs_top_srcdir=$srcdir ;; *) # Relative name. ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix ac_top_srcdir=$ac_top_build_prefix$srcdir ac_abs_top_srcdir=$ac_pwd/$srcdir ;; esac ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix case $ac_mode in :F) # # CONFIG_FILE # _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 # If the template does not know about datarootdir, expand it. # FIXME: This hack should be removed a few years after 2.60. ac_datarootdir_hack=; ac_datarootdir_seen= ac_sed_dataroot=' /datarootdir/ { p q } /@datadir@/p /@docdir@/p /@infodir@/p /@localedir@/p /@mandir@/p' case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in *datarootdir*) ac_datarootdir_seen=yes;; *@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5 $as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;} _ACEOF cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_datarootdir_hack=' s&@datadir@&$datadir&g s&@docdir@&$docdir&g s&@infodir@&$infodir&g s&@localedir@&$localedir&g s&@mandir@&$mandir&g s&\\\${datarootdir}&$datarootdir&g' ;; esac _ACEOF # Neutralize VPATH when `$srcdir' = `.'. # Shell code in configure.ac might set extrasub. # FIXME: do we really want to maintain this feature? cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 ac_sed_extra="$ac_vpsub $extrasub _ACEOF cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 :t /@[a-zA-Z_][a-zA-Z_0-9]*@/!b s|@configure_input@|$ac_sed_conf_input|;t t s&@top_builddir@&$ac_top_builddir_sub&;t t s&@top_build_prefix@&$ac_top_build_prefix&;t t s&@srcdir@&$ac_srcdir&;t t s&@abs_srcdir@&$ac_abs_srcdir&;t t s&@top_srcdir@&$ac_top_srcdir&;t t s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t s&@builddir@&$ac_builddir&;t t s&@abs_builddir@&$ac_abs_builddir&;t t s&@abs_top_builddir@&$ac_abs_top_builddir&;t t $ac_datarootdir_hack " eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \ >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5 test -z "$ac_datarootdir_hack$ac_datarootdir_seen" && { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } && { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \ "$ac_tmp/out"`; test -z "$ac_out"; } && { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&5 $as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir' which seems to be undefined. Please make sure it is defined" >&2;} rm -f "$ac_tmp/stdin" case $ac_file in -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";; *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";; esac \ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; esac done # for ac_tag as_fn_exit 0 _ACEOF ac_clean_files=$ac_clean_files_save test $ac_write_fail = 0 || as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5 # configure is writing to config.log, and then calls config.status. # config.status does its own redirection, appending to config.log. # Unfortunately, on DOS this fails, as config.log is still kept open # by configure, so config.status won't be able to write to it; its # output is simply discarded. So we exec the FD to /dev/null, # effectively closing config.log, so it can be properly (re)opened and # appended to by config.status. When coming back to configure, we # need to make the FD available again. if test "$no_create" != yes; then ac_cs_success=: ac_config_status_args= test "$silent" = yes && ac_config_status_args="$ac_config_status_args --quiet" exec 5>/dev/null $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false exec 5>>config.log # Use ||, not &&, to avoid exiting from the if with $? = 1, which # would make configure fail if this is the last instruction. $ac_cs_success || as_fn_exit 1 fi if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5 $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;} fi