Bash/Arithmetische Substitution

Aus Foxwiki

Die Bash ist kein Taschenrechner. Dennoch besitzt sie ein erstaunliches Potenzial an eingebauten Rechenoperationen, die -- nach Prioritäten geordnet -- nachfolgende Tabelle zusammenfasst:

VAR++ and VAR-- variable post-increment and post-decrement
++VAR and --VAR variable pre-increment and pre-decrement
+ - Einstelliger Operator (Vorzeichen)
! ~ Logische und bitweise Negation
** Exponentialfunktion
* / % Multiplikation, Division und Modulo-Operator
+ - Addition, Subtraktion
<< >> Bitweise Links-/Rechtsverschiebung
<= >= < > Vergleiche
== != Gleichheit und Ungleichheit
& Bitweises UND
^ Bitweises Exclusive ODER
| Bitweises ODER
&& Logisches UND
'''|| ''' Logisches ODER
expr ? expr : expr Bedingte Zuweisung
=, *=, /=, %=, +=, -= <<=, >>=, &=, ^=, |= Zuweisungen
, separator between expressions

Als Operanden sind Konstanten und Shellvariablen (deren Inhalt als long integer betrachtet wird) erlaubt. Beginnt eine Konstante mit "0", dann wird sie als oktale Zahl verstanden; steht "0x" am Anfang, handelt es sich um eine hexadezimale Konstante.

Konstanten können zu jeder Basis zwischen 2 und 64 angegeben werden, so kann die Zahl 63 u.a. wie folgt dargestellt werden: * Zur Basis 10: 10#63

  • Zur Basis 8: 8#77
  • Zur Basis 16: 16#3f

Die so genannte arithmetische Substitution ist der gebräuchliche Weg, um Berechnungen durchzuführen: * Bash Versionen <2: Der zu berechnende Ausdruck wird in eckigen Klammern geschrieben: $[...]

  • Bash ab Version 2: Der zu berechnende Ausdruck wird in doppelte runde Klammern geschrieben: $((...)) (die alte Syntax wird weiterhin unterstützt)

Arithmetic expansion allows the evaluation of an arithmetic expression and the substitution of the result. The format for arithmetic expansion is:

$(( EXPRESSION ))

The expression is treated as if it were within double quotes, but a double quote inside the parentheses is not treated specially.

All tokens in the expression undergo parameter expansion, command substitution, and quote removal. Arithmetic substitutions may be nested.

Evaluation of arithmetic expressions is done in fixed-width integers with no check for overflow - although division by zero is trapped and recognized as an error.

The operators are roughly the same as in the C programming language. In order of decreasing precedence, the list looks like this:

Shell variables are allowed as operands; parameter expansion is performed before the expression is evaluated.

Within an expression, shell variables may also be referenced by name without using the parameter expansion syntax.

The value of a variable is evaluated as an arithmetic expression when it is referenced. A shell variable need not have its integer attribute turned on to be used in an expression.

Constants with a leading 0 (zero) are interpreted as octal numbers. A leading "0x" or "0X" denotes hexadecimal. Otherwise, numbers take the form "[BASE'#']N", where "BASE" is a decimal number between 2 and 64 representing the arithmetic base, and N is a number in that base.

If "BASE'#'" is omitted, then base 10 is used. The digits greater than 9 are represented by the lowercase letters, the uppercase letters, "@", and "_", in that order.

If "BASE" is less than or equal to 36, lowercase and uppercase letters may be used interchangably to represent numbers between 10 and 35.

Operators are evaluated in order of precedence. Sub-expressions in parentheses are evaluated first and may override the precedence rules above.

Wherever possible, Bash users should try to use the syntax with square brackets:

$[ EXPRESSION ] 

However, this will only calculate the result of EXPRESSION, and do no tests:

echo $[365*24]
8760

Übungen

b=5; b=$((b+1)); echo $b

6

a=$((b+=10)); echo $a

16

echo $((a>b?1:0))

1

echo $((8#17**2))

225

echo $((017**2))

225

echo $((-0x64*3#11%6))

-4

echo $((4<<1))

8

Wird als Operand eine Variable benutzt, so wird versucht, deren Inhalt in eine Ganzzahl zu konvertieren. Enthält die Variable keine Zahl, wird der Inhalt zu "0" konvertiert:

b="Ist b keine Zahl, wird b zu 0 konvertiert"

echo $b
Ist b keine Zahl, wird b zu 0 konvertiert

b=$(($b+1)); echo $b

1