it-swarm-id.com

Bagaimana melakukan perhitungan integer & float, dalam bash atau bahasa / kerangka kerja lainnya?

Menggunakan echo "20+5" Secara harfiah menghasilkan teks "20+5".

Perintah apa yang dapat saya gunakan untuk mendapatkan jumlah numerik, 25 Dalam kasus ini?

Juga, apa cara termudah untuk melakukannya hanya menggunakan bash untuk floating point? Misalnya, echo $((3224/3807.0)) mencetak 0 :(.

Saya mencari jawaban baik menggunakan perintah dasar Shell ('command line') itu sendiri atau melalui menggunakan bahasa yang tersedia dari baris perintah.

316
Michael Durrant

Ada banyak pilihan!!!

Ringkasan

$ printf %.10f\\n "$((10**9 * 20/7))e-9"   # many shells. Not mksh.
$ echo "$((20.0/7))"                       # (ksh93/zsh/yash, not bash)
$ awk "BEGIN {print (20+5)/2}"
$ zcalc
$ bc <<< 20+5/2
$ bc <<< "scale=4; (20+5)/2"
$ dc <<< "4 k 20 5 + 2 / p"
$ expr 20 + 5
$ calc 2 + 4
$ node -pe 20+5/2  # Uses the power of JavaScript, e.g. : node -pe 20+5/Math.PI
$ echo 20 5 2 / + p | dc 
$ echo 4 k 20 5 2 / + p | dc 
$ Perl -E "say 20+5/2"
$ python -c "print(20+5/2)"
$ python -c "print(20+5/2.0)"
$ clisp -x "(+ 2 2)"
$ lua -e "print(20+5/2)"
$ php -r 'echo 20+5/2;'
$ Ruby -e 'p 20+5/2'
$ Ruby -e 'p 20+5/2.0'
$ guile -c '(display (+ 20 (/ 5 2)))'
$ guile -c '(display (+ 20 (/ 5 2.0)))'
$ slsh -e 'printf("%f",20+5/2)'
$ slsh -e 'printf("%f",20+5/2.0)'
$ tclsh <<< 'puts [expr 20+5/2]'
$ tclsh <<< 'puts [expr 20+5/2.0]'
$ sqlite3 <<< 'select 20+5/2;'
$ sqlite3 <<< 'select 20+5/2.0;'
$ echo 'select 1 + 1;' | sqlite3 
$ psql -tAc 'select 1+1'
$ R -q -e 'print(sd(rnorm(1000)))'
$ r -e 'cat(pi^2, "\n")'
$ r -e 'print(sum(1:100))'
$ smjs
$ jspl

Detail

Kerang

Anda dapat menggunakan ekspansi aritmatika POSIX untuk integer aritmatika echo "$((...))":

$ echo "$((20+5))"
25
$ echo "$((20+5/2))"
22

Cukup portabel (ash dash yash bash ksh93 lksh zsh):
Menggunakan kemampuan printf untuk mencetak floats, kami dapat memperluas sebagian besar shell untuk melakukan matematika titik mengambang walaupun dengan kisaran terbatas (tidak lebih dari 10 digit):

$ printf %.10f\\n "$((1000000000 *   20/7  ))e-9"
2.8571428570

ksh93, yash dan zsh mendukung float di sini:

$ echo "$((1.2 / 3))"
0.4

hanya ksh93 (langsung) dan zsh memuat fungsi perpustakaan perpustakaan di sini:

$ echo "$((4*atan(1)))"
3.14159265358979324

(zsh perlu memuat zmodload zsh/mathfunc untuk mendapatkan fungsi seperti atan).


Secara interaktif dengan zsh:

$ autoload zcalc
$ zcalc
1> PI/2
1.5708
2> cos($1)
6.12323e-17
3> :sci 12
6.12323399574e-17

Dengan (t) csh (hanya bilangan bulat):

% @ a=25 / 3; echo $a
8

Dalam rc keluarga Shell, akanga adalah keluarga dengan ekspansi aritmatika:

; echo $:25/3
8

Toolest POSIX

bc (lihat di bawah untuk mode interaktif), manual di sini

Mnemonik: best calculator (meskipun b sebenarnya untuk dasar).

$ echo 20+5/2 | bc
22
$ echo 'scale=4;20+5/2' | bc
22.5000

(mendukung angka presisi acak)


mode interaktif bc:

$ bc
bc 1.06.95
Copyright 1991-1994, 1997, 1998, 2000, 2004, 2006 Free Software Foundation, Inc.
This is free software with ABSOLUTELY NO WARRANTY.
For details type `warranty'. 
5+5
10

2.2+3.3
5.5

Rush solusi, expr (tidak ada mode interaktif):

$ expr 20 + 5
25
$ expr 20 + 5 / 2
22

solusi Joshua : awk (tidak ada mode interaktif):

$ calc() { awk "BEGIN{print $*}"; }
$ calc 1/3
0.333333

Alat portable lainnya yang kurang lebih

Arcege solusi, dc (mode interaktif: dc):

Yang bahkan lebih menyenangkan karena bekerja dengan notasi polish terbalik.

$ echo 20 5 2 / + p | dc 
22
$ echo 4 k 20 5 2 / + p | dc 
22.5000

Tapi tidak sepraktis kecuali Anda banyak bekerja dengan notasi polish terbalik.

Perhatikan bahwa dc mendahului bc dan bc telah secara historis diterapkan sebagai pembungkus sekitar dc tetapi dc tidak distandarisasi oleh POSIX


DQdims 's calc (wajib Sudo apt-get install apcalc):

$ calc 2 + 4
6

Penerjemah bahasa tujuan umum:

manatwork solusi, node (mode interaktif: node; fungsi output tidak dibutuhkan):

$ node -pe 20+5/2  # Uses the power of JavaScript, e.g. : node -pe 20+5/Math.PI
22.5

Perl (mode interaktif: Perl -de 1):

$ Perl -E "say 20+5/2"
22.5

Python (mode interaktif: python; fungsi output tidak diperlukan):

$ python -c "print(20+5/2)"
22 # 22.5 with python3
$ python -c "print(20+5/2.0)"
22.5

Juga mendukung angka presisi acak:

$ python -c 'print(2**1234)'
295811224608098629060044695716103590786339687135372992239556207050657350796238924261053837248378050186443647759070955993120820899330381760937027212482840944941362110665443775183495726811929203861182015218323892077355983393191208928867652655993602487903113708549402668624521100611794270340232766099317098048887493809023127398253860618772619035009883272941129544640111837184

Jika Anda telah menginstal clisp, Anda juga dapat menggunakan notasi semir:

$ clisp -x "(+ 2 2)"

Marco solusi, lua (mode interaktif: lua):

$ lua -e "print(20+5/2)"
22.5

[~ # ~] php [~ # ~] (mode interaktif: php -a):

$ php -r 'echo 20+5/2;'
22.5

Ruby (mode interaktif: irb; fungsi output tidak diperlukan):

$ Ruby -e 'p 20+5/2'
22
$ Ruby -e 'p 20+5/2.0'
22.5

Tipuan (mode interaktif: guile):

$ guile -c '(display (+ 20 (/ 5 2)))'
45/2
$ guile -c '(display (+ 20 (/ 5 2.0)))'
22.5

S-Lang (mode interaktif: slsh; fungsi output tidak diperlukan, hanya terminator ;):

$ slsh -e 'printf("%f",20+5/2)'
22.000000
$ slsh -e 'printf("%f",20+5/2.0)'
22.500000

Tcl (mode interaktif: tclsh; fungsi output tidak diperlukan, tetapi expr adalah):

$ tclsh <<< 'puts [expr 20+5/2]'
22
$ tclsh <<< 'puts [expr 20+5/2.0]'
22.5

Kerang Javascript :

$ smjs
js> 25/3
8.333333333333334
js>

$ jspl
JSC: 25/3

RP: 8.33333333333333
RJS: [object Number]
JSC:
Good bye...

$ node
> 25/3
8.333333333333334
>

Berbagai SQL:

SQLite (mode interaktif: sqlite3):

$ sqlite3 <<< 'select 20+5/2;'
22
$ sqlite3 <<< 'select 20+5/2.0;'
22.5

MySQL :

mysql -BNe 'select 1+1'

PostgreSQL :

psql -tAc 'select 1+1

_Pilihan pada mysql dan postgres menghentikan gambar 'ascii art'!

Bahasa berorientasi matematika khusus:

[~ # ~] r [~ # ~] dalam mode biasa - memungkinkan menghasilkan 1000 angka acak normal dan mendapatkan simpangan baku dan mencetaknya

$ R -q -e 'print(sd(rnorm(1000)))'
> print(sd(rnorm(1000)))
[1] 1.031997

[~ # ~] r [~ # ~] menggunakan littler skrip - memungkinkan pi cetak kuadrat

$ r -e 'cat(pi^2, "\n")'
9.869604
$  r -e 'print(sum(1:100))'
[1] 5050

PARI/GP , sistem aljabar komputer yang luas untuk teori bilangan, aljabar linier, dan banyak hal lainnya

$ echo "prime(1000)"|gp -q
7919                        // the 1000th prime
$ echo "factor(1000)" | gp -q
[2 3]
[5 3]                       // 2^3*5^3
$ echo "sum(x=1,5,x)" | gp -q
15                          // 1+2+3+4+5

GNU Octave (bahasa interpretasi tingkat tinggi, terutama ditujukan untuk perhitungan numerik)

Juga mendukung bilangan kompleks:

$ octave
>> 1.2 / 7
ans =  0.17143
>> sqrt(-1)
ans =  0 + 1i

Julia , bahasa kinerja tinggi dan juru bahasa untuk komputasi ilmiah dan numerik.

Opsi non-interaktif:

$ Julia -E '2.5+3.7'
6.2
431
lgarzo

Ada banyak cara untuk menghitung. Untuk ekspresi sederhana, Anda dapat menggunakan bash sendiri:

echo $((20+5))

atau expr:

expr 20 + 5

Dan untuk kasus rumit ada alat hebat bc:

echo "20+5" | bc

Btw, bc dapat menghitung bahkan ekspresi yang sangat kompleks dengan akar, logaritma, cos, dosa dan sebagainya.

37
rush

Solusi yang disebutkan baik untuk perhitungan yang sangat sederhana, tetapi sangat rawan kesalahan. Contoh:

# without spaces expr 20+5 produces literally 20+5
expr 20+5
→ 20+5

# bc's result doesn't give the fractional part by default
bc <<< 9.0/2.0
→ 4

# expr does only integer
expr 9 / 2
→ 4

# same for POSIX arithmetic expansion
echo $((9/2))
→ 4

# bash arithmetic expansion chokes on floats
echo $((9.0/2.0))
→ bash: 9/2.0: syntax error: invalid arithmetic operator (error token is ".0")

# Most `expr` implementations also have problems with floats
expr 9.0 / 2.0
→ expr: non-integer argument

Kesalahan sintaksis seperti yang terakhir mudah diketahui, tetapi respons bilangan bulat dengan bagian float yang dibuang dapat dengan mudah diketahui dan menyebabkan hasil yang salah.

Itu sebabnya saya selalu menggunakan bahasa scripting seperti Lua untuk itu. Tetapi Anda dapat memilih bahasa skrip apa pun yang Anda kenal. Saya hanya menggunakan Lua sebagai contoh. Keuntungannya adalah

  • sintaks yang akrab
  • fungsi yang biasa
  • peringatan akrab
  • input fleksibel
  • ruang biasanya tidak penting
  • output titik mengambang

Contoh:

lua -e "print(9/2)"
→ 4.5

lua -e "print(9 / 2)"
→ 4.5

lua -e "print(9.0/2)"
→ 4.5

lua -e "print (9 /2.)"
→ 4.5

lua -e "print(math.sqrt(9))"
→ 3
25
Marco

Belum ada yang menyebut awk?

Menggunakan fungsi POSIX Shell, dan kekuatan matematika awk, cukup tentukan fungsi (satu baris) ini:

calc(){ awk "BEGIN { print $*}"; }

Maka jalankan saja hal-hal seperti calc 1+1 atau calc 5/2

Catatan: Agar fungsi selalu tersedia, tambahkan ke ~/.bashrc (atau file startup Shell Anda yang sesuai)

Tentu saja, skrip kecil bernama "calc" dengan konten berikut:

#!/bin/sh -
awk "BEGIN { print $* }"

juga bisa bekerja.

25
Joshua

Anda dapat menggunakan bc. Misalnya.,

$ echo "25 + 5" | bc
30

Kalau tidak bc <<< 25+5 juga akan berfungsi.

Atau secara interaktif, jika Anda ingin melakukan lebih dari satu perhitungan sederhana:

$ bc
bc 1.06.95
Copyright 1991-1994, 1997, 1998, 2000, 2004, 2006 Free Software Foundation, Inc.
This is free software with ABSOLUTELY NO WARRANTY.
For details type `warranty'. 
25 + 5
30

The GNU implementasi bc mencetak informasi header/hak cipta saat start-up ketika stdin dan stdout pergi ke terminal. Anda dapat menekannya dengan (khusus GNU) ) -q pilihan. Untuk informasi lebih lanjut lihat bc halaman manual

18
Levon

Anda dapat menggunakan calc:

Jika Anda hanya memasukkan calc tanpa argumen lain, ia memasuki mode interaktif di mana Anda bisa terus melakukan matematika. Anda keluar dari ini dengan mengetikkan keluar:

C-style arbitrary precision calculator (version 2.12.3.3)
Calc is open software. For license details type:  help copyright
[Type "exit" to exit, or "help" for help.]

; 2+4
6
; 3+5
8
; 3.4+5
8.4
; 2^4
16
; exit

Atau Anda menggunakannya dengan ekspresi sebagai argumen dan itu akan memberikan jawaban dan kemudian keluar

$calc 2 + 4
    6
$

calc mirip dengan bc, saya hanya menyukai caranya berperilaku sebagai default yang lebih baik

17
DQdlM

Saya suka menjalankan Python dan menggunakannya sebagai kalkulator interaktif (tapi sekali lagi, saya seorang Python programmer).

10
asmeurer

Karena tidak ada orang lain yang menyebutkannya, dan meskipun ini bukan sepenuhnya kalkulator (tetapi tidak semua bahasa scripting untuk tujuan umum ini), saya ingin menyebutkan units:

$ units "1 + 1"
        Definition: 2
$ units "1 lb" "kg"
        * 0.45359237
         / 2.2046226

Atau, untuk output yang lebih sedikit sehingga Anda bisa mendapatkan nomor yang digunakan di $() untuk menetapkan sesuatu:

$ units -t "1 + 1"
2
$ units -t "1 lb" "kg"
0.4539237

Dan bahkan konversi suhu

$ units -t "tempC(20)" "tempF"
68

Untuk mendapatkan konversi suhu dalam ekspresi untuk perhitungan lebih lanjut, lakukan ini:

$ units -t "~tempF(tempC(20))+1"
68.1
10
Random832

Untuk aritmatika Integer (di mana 3/2 = 1)

  • bashecho $(( 1+1 ))
  • fishmath 1+1
  • zsh*echo $((1+1))

*: dan ksh93, yash

Untuk aritmatika floating point (di mana 3/2 = 1.5)

  • bashawk "BEGIN {print 10/3}" (presisi rendah)
  • bashecho "10/3"|bc -l (presisi tinggi)
  • fishmath -s4 10/3
  • zsh*echo $((10./3))

*: dan ksh93, yash

Anda tentu saja dapat mengkonfigurasi Shell Anda untuk menggunakan awk dengan pengetikan minimum seperti calc 10/3 (Lihat catatan tentang bagaimana melakukannya untuk bash1 dan ikan2).

Alasan utama untuk menyarankan awk untuk bash adalah karena sudah diinstal pada hampir semua OS mirip Unix dan cukup ringan (tentu saja ada biaya memulai proses) dengan output yang kurang tepat tetapi lebih ramah manusia daripada bc -l yang mencetak 20 angka desimal (walaupun Anda tentu bisa Tweak awk untuk mendapatkan lebih banyak angka desimal ).


Catatan

(1) Cara menggunakan sintaks yang disederhanakan dalam bash

Tambahkan fungsi bash ini ke ~/.bashrc Anda:

calc(){ awk "BEGIN { print $*}"; }

(2) Cara menggunakan sintaks yang disederhanakan pada ikan

Buat fungsi calc fish (mis. File teks bernama /home/ndemou/.config/fish/functions/calc.fish):

function calc
    awk "BEGIN{ print $argv }" ;
end
6
ndemou
$> ghc -e '20 + 5'
25
it :: Integer

Juga ghci, yaitu Kompiler Glasgow-Haskell dalam mode interaktif (ghc --interactive, yang bertentangan dengan itu mengevaluasi ekspresi dengan -e ), membuat "kalkulator" yang menarik:

$>ghci
GHCi, version 7.8.3: http://www.haskell.org/ghc/  :? for help
Loading package ghc-prim ... linking ... done.
Loading package integer-gmp ... linking ... done.
Loading package base ... linking ... done.
Prelude> pi
3.141592653589793
Prelude> ceiling pi
4
Prelude> compare 1 2
LT

Saya menggunakan sedikit python script yang akan mengevaluasi ekspresi python dan mencetak hasilnya, maka saya dapat menjalankan sesuatu seperti

$ pc '[i ** 2 for i in range(10)]'
[0, 1, 4, 9, 16, 25, 36, 49, 64, 81]

skripnya adalah:

#!/usr/local/bin/python3

import sys
import traceback
from codeop import CommandCompiler

compile = CommandCompiler()
filename = "<input>"
source = ' '.join(sys.argv[1:]) + '\n'

try:
    code = compile(source, filename) 
except (OverflowError, SyntaxError, ValueError):
    type, value, sys.last_traceback = sys.exc_info()
    sys.last_type = type
    sys.last_value = value
    if filename and type is SyntaxError:
        # Work hard to stuff the correct filename in the exception
        try:
            msg, (dummy_filename, lineno, offset, line) = value.args
        except ValueError:
            # Not the format we expect; leave it alone
            pass
        else:
            # Stuff in the right filename
            value = SyntaxError(msg, (filename, lineno, offset, line))
            sys.last_value = value
    lines = traceback.format_exception_only(type, value)
    print(''.join(lines))
else:
    if code:
        exec(code)
    else:
        print('incomplete')

Sayangnya saya tidak ingat dari mana saya meminjam sebagian besar kode, jadi saya tidak bisa mengutipnya.

4
cobbal

Gnuplot

gnuplot - program perencanaan interaktif
Ikuti tautan di atas atau ketik gnuplot dari Prompt lalu help di dalam interpreter gnuplot .
Gnuplot adalah program yang lahir untuk memplot data, tetapi dapat digunakan untuk perhitungan juga. Ini menawarkan keuntungan bahwa Anda dapat mendefinisikan fungsi dan atau menggunakan yang built-in.

echo  "pr 20+5/2"  |  gnuplot          #  Lazy-note `pr` instead of print
22                                     #  Integer calculation & result
echo  "pr 20.+5/2"  |  gnuplot         #  Lazy-note `pr` instead of print
22.0                                   #  Floating point result
echo  "pr sin(2*pi/3.)"  |  gnuplot    #  Some functions ...
0.866025403784439

Root (atau lainnya penerjemah C )

(sistem ROOT menyediakan satu set kerangka kerja OO dengan semua fungsionalitas yang diperlukan untuk menangani dan menganalisis sejumlah besar data dalam cara efisien ...

Anda dapat menggunakannya sebagai penerjemah C , [~ # ~] cint [~ # ~] , atau Anda dapat menggunakan salah satu dari banyak banyak juru bahasa C lainnya . IMHO, itu besar, kompleks, kuat, dan tidak selalu ramah tetapi dapat memberikan kepuasan besar juga.

Jika Anda benar-benar tidak ingin mendengarkan suara kecil di dalam diri Anda yang mengutip Confucio dan Anda siap untuk mematahkan (mentega) terbang di atas kemudi Anda dapat menggunakan root . Pada kasus ini -l wajib untuk menghindari menampilkan layar splash ...

echo  "20+5/2"   | root -l
(const int)22
echo  "20+5/2."  | root -l
(const double)2.25000000000000000e+01

echo  "cout<< 20+5/2 << endl;"   | root -l
22
4
Hastur

Saya tidak percaya untuk membaca "kekuatan JavaScript" (tapi saya harus menghapuskan jawaban untuk bagian lain, kecuali Perl tentu saja.

Secara praktis, untuk kasus-kasus sederhana di mana aritmatika integer cukup, saya menggunakan $ buildin ((...)) dan merekomendasikannya. Lain, dalam hampir semua kasus gema "..." | bc sudah cukup.

Untuk beberapa operasi aritmatika seperti statistik, operasi matriks, dan banyak lagi R adalah alat yang lebih baik:

echo 25 + 5 | R --Vanilla

dan untuk dataset kecil dan hasil grafik, oocalc adalah utilitas yang bagus.

4
user unknown

Untuk perhitungan konsol, saya menggunakan concalc. (Sudo aptitude install concalc)

Setelah itu, cukup ketik concalc dan tekan enter. Ini tidak akan memberikan Prompt, tetapi cukup ketik perhitungan Anda (tanpa spasi) dan tekan enter, dan pada baris berikutnya, itu akan memberi Anda nilai numerik.

3
killermist

SQLite:

echo 'select 1 + 1;' | sqlite3 

MySQL:

mysql -e 'select 1 + 1 from dual;'

PostgreSQL:

psql -c 'select 1 + 1 as sum;'
3
Vidul

Gunakan --- Perpustakaan Aritmatika Presisi Ganda GNU melalui program run-expr Yang disediakan:

  • Unduh dan ekstrak (Anda perlu lzip): tar -xvf gmp-5.1.3.tar.lz
  • Di direktori teratas, ./configure Dan make (tidak perlu menginstal)
  • Dalam demo/expr, make run-expr
  • Saya suka membuat tautan simbolis ke direktori ~/bin Saya: ln -s /path/to/gmp/demos/expr/run-expr ~/bin/run-expr
  • Tambahkan alias untuk mudah digunakan; misalnya alias calcf='run-expr -f' untuk evaluasi floating point

Keluaran:

# calcf '2/3'
"2/3" base 0: result 0.666666666666666666667e0

Dari file run-expr.c:

Usage: ./run-expr [-z] [-q] [-f] [-p prec] [-b base] expression...

   Evaluate each argument as a simple expression.  By default this is in mpz
   integers, but -q selects mpq or -f selects mpf.  For mpf the float
   precision can be set with -p.  In all cases the input base can be set
   with -b, or the default is "0" meaning decimal with "0x" allowed.

Lihat manual untuk perbedaan dan detail kelas fungsi.

2
user44370

Sisa solusi di sini semuanya memiliki kelemahan yang menonjol.

Jadi saya telah membuat perintah baru untuk dapat melakukan ini dengan cara yang paling sederhana dan paling dapat diandalkan.

Sampel:

$ solve 1/5
0.2
$ solve 1.5+3.1
4.6
$ solve 1/1000000
1e-06
$ solve 7+2^3
15
$ solve "sqrt(8)"
2.82842712474619
$ solve 1/0
non solvable ????: 1/0