GNU/Linux >> Linux Esercitazione >  >> Linux

Arrotondamento dei numeri con bc in Bash

La funzione successiva arrotonda l'argomento 'x' a 'd' cifre:

define r(x, d) {
    auto r, s

    if(0 > x) {
        return -r(-x, d)
    }
    r = x + 0.5*10^-d
    s = scale
    scale = d
    r = r*10/10
    scale = s  
    return r
} 

Il tuo trucco per aggiungere 0.0005 non è una cattiva idea. Tuttavia, non funziona proprio in questo modo. scale è usato internamente quando bc esegue alcune operazioni (come le divisioni).

Nel tuo caso sarebbe meglio eseguire prima la divisione, magari utilizzando un scale grande o il -l passa a bc (se la tua versione lo supporta), quindi aggiungi 0.0005 e poi imposta scale=3 ed eseguire un'operazione che coinvolge scale internamente per eseguire il troncamento.

Qualcosa come:

`a=$sum/$n+0.0005; scale=3; a/1`

Naturalmente, vorrai procedere diversamente se sum è positivo o negativo. Fortunatamente, bc ha alcuni operatori condizionali.

`a=$sum/$n; if(a>0) a+=0.0005 else if (a<0) a-=0.0005; scale=3; a/1`

Dovrai quindi formattare questa risposta utilizzando printf .

Racchiuso in una funzione round (dove puoi facoltativamente selezionare il numero di cifre decimali):

round() {
    # $1 is expression to round (should be a valid bc expression)
    # $2 is number of decimal figures (optional). Defaults to three if none given
    local df=${2:-3}
    printf '%.*f\n' "$df" "$(bc -l <<< "a=$1; if(a>0) a+=5/10^($df+1) else if (a<0) a-=5/10^($df+1); scale=$df; a/1")"
}

Provalo:

gniourf$ round "(3+3+4)/3"
3.333
gniourf$ round "(3+3+5)/3"
3.667
gniourf$ round "-(3+3+5)/3"
-3.667
gniourf$ round 0
0.000
gniourf$ round 1/3 10
0.3333333333
gniourf$ round 0.0005
0.001
gniourf$ round 0.00049
0.000

con il -l interruttore, scale è impostato su 20 , che dovrebbe essere sufficiente.


Questa soluzione non è così flessibile (converte solo float in int), ma può gestire numeri negativi:

e=$( echo "scale=0; (${e}+0.5)/1" | bc -l )
if [[ "${e}" -lt 0 ]] ; then
    e=$(( e - 1 ))
fi

Linux
  1. Bash -c con parametri posizionali?

  2. Alias ​​con variabile in bash

  3. Aggiunta di timestamp a un nome file con mv in BASH

  4. Bash:aspetta con timeout

  5. Linux Bash XMLLINT con XPATH

Automatizza l'elaborazione delle immagini con questo script Bash

Cos'è Git Bash; Lavorare con i comandi Git Bash

Come scrivere uno script Bash con esempi

Bash HereDoc Tutorial con esempi

Come creare documenti con gli script Bash

Bash If Else Sintassi con esempi