resta - redondeo a tres cifras significativas calculadora
Cuente los ceros iniciales entre el punto decimal y el primer dÃgito distinto de cero (7)
Aquí hay otra posibilidad:
zeros_after_period <- function(x) {
if (isTRUE(all.equal(round(x),x))) return (0) # y would be -Inf for integer values
y <- log10(abs(x)-floor(abs(x)))
ifelse(isTRUE(all.equal(round(y),y)), -y-1, -ceiling(y))} # corrects case ending with ..01
Ejemplo:
x <- c(1.000633, 0.002, -10.01, 7.00010001, 62.01)
sapply(x,zeros_after_period)
#[1] 3 2 1 3 1
Supongamos que si tenemos un número 1.000633, quiero contar el número de ceros después del punto decimal hasta el primer dígito distinto de cero en la fracción, la respuesta debería ser 3. Para 0.002, la respuesta debería ser 2.
No hay tal función en R que pueda ayudar. He explorado la función Ndec en el paquete DescTools pero no hace el trabajo.
Otra forma de usar str_count
desde el paquete stringr
,
x <- as.character(1.000633)
str_count(gsub(".*[.]","",x), "0")
#[1] 3
EDITAR: Esto cuenta todos los ceros después del decimal y hasta el primer valor distinto de cero.
y <- c(1.00215, 1.010001, 50.000809058, 0.1)
str_count(gsub(".*[.]","",gsub("(?:(0+))[1-9].*","//1",as.character(y))),"0")
#[1] 2 1 3 0
Podemos usar sub
ifelse(grepl("//.0", str1),
nchar(sub("[^//.]+//.(0+)[^0]+.*", "//1", str1)), NA)
#[1] 3 2 3 3 2
O usando stringi
library(stringi)
r1 <- stri_extract(str1, regex="(?<=//.)0+")
ifelse(is.na(r1), NA, nchar(r1))
#[1] 3 2 3 3 2
Solo para comprobar si funciona con algún caso extraño.
str2 <- "0.00A-Z"
nchar(sub("[^//.]+//.(0+)[^0]+.*", "//1", str2))
#[1] 2
datos
str1 <- as.character(c(1.000633, 0.002, 0.000633,
10.000633, 3.0069006))
Puedes usar sub
ya que no necesitamos saltar. Por lo tanto no hay necesidad de gsub
nchar(sub(".*//.(0*).*","//1",str1))
[1] 3 2 3 3 2
dónde
str1 <- as.character(c(1.000633, 0.002, 0.000633,
10.000633, 3.0069006))
Usando la función rle
:
#test values
x <- c(0.000633,0.003,0.1,0.001,0.00633044,10.25,111.00012,-0.02)
#result
sapply(x, function(i){
myNum <- unlist(strsplit(as.character(i), ".", fixed = TRUE))[2]
myNumRle <- rle(unlist(strsplit(myNum, "")))
if(myNumRle$values[1] == 0) myNumRle$lengths[1] else 0
})
#output
# [1] 3 2 0 2 2 0 3 1
Usando regexpr
y su argumento match.length
attr(regexpr("(?<=//.)0+", x, perl = TRUE), "match.length")
floor( -log10( eps + abs(x) - floor( abs( x ) ) ) )