Co dokładnie robi echo $ ((2 # $ 1))?


53

Poniższy skrypt bash wyświetla liczbę dziesiętną po podaniu liczby binarnej.

echo $((2#$1))

Dlaczego dokładnie

Rozumiem, że $1to jest wkład. Może 2jest bazą (binarną). Ale nie rozumiem zastosowanej składni.

Odpowiedzi:


72

uderzenie człowieka

   echo [-neE] [arg ...]
          Output  the  args,  separated  by spaces, followed by a newline.
          The return status is 0 unless a write error occurs.   If  -n  is
          specified, the trailing newline is suppressed.  If the -e option
          is given,  interpretation  of  the  following  backslash-escaped
          characters  is  enabled.

[...]

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

              $((expression))

[...]

   Constants with a leading 0 are interpreted as octal numbers.  A leading
   0x or  0X  denotes  hexadecimal.   Otherwise,  numbers  take  the  form
   [base#]n,  where the optional 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.  When specifying n, 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 interchangeably  to  repre‐
   sent numbers between 10 and 35.

66
-1 dla wyjaśnienia ZERO.
Max Ried

27
Myślę, że jest to dość dobrze wyjaśnione
NanoPish,

19
Pełne udzielenie odpowiedzi na pytanie, nawet jeśli „tylko” poprzez wybór istniejącej dokumentacji, nie zasługuje na -1 dla mnie. W szczególności, jeśli dokumentacja ta jest stroną podręcznika użytkownika bash.
YoungFrog,

31
man bash | wcwskazuje stronę podręcznika [GNU bash, wersja 3.2.57] na 4890 linii, 37094 słów , 329778 znaków. Ta odpowiedź usuwa tylko 7 wierszy, 176 słów i 1115 znaków. Myślę, że ta odpowiedź zasługuje na twoją opinię. (podobnie jak ten komentarz ;-)
Bruno Bronosky,

7
@MaxRied: -1 do komentarza za szukanie niepotrzebnego puchu
Mehrdad

30

Z dokumentu pod adresem : https://tiswww.case.edu/php/chet/bash/bashref.html#Shell-Arithmetic

Stałe z wiodącym 0 są interpretowane jako liczby ósemkowe. Wiodące „0x” lub „0X” oznacza liczbę szesnastkową. W przeciwnym razie liczby przyjmują postać [podstawa #] n, gdzie opcjonalna podstawa jest liczbą dziesiętną między 2 a 64 reprezentującą podstawę arytmetyczną, a n jest liczbą w tej podstawie. Jeśli baza nr zostanie pominięta, zostanie użyta baza 10. Przy określaniu n cyfry większe niż 9 są reprezentowane przez małe litery, wielkie litery „@” i „_” w tej kolejności. Jeśli podstawa jest mniejsza lub równa 36, ​​małe i wielkie litery mogą być używane zamiennie do reprezentowania liczb od 10 do 35.

Więc echo $((16#FF))wyjścia 255i echo $((2#0110))wyjścia6


25

Odpowiedź Iporta jest doskonała, ale bardzo nieznacznie niepełna. Cytowana część strony podręcznika bash mówi, że składnia działa tylko dla stałych i nie jest stała. Powinieneś zapytać, jak to naprawdę działa![base#]n2#$1

EKSPANSJA

    Rozwinięcie jest wykonywane w wierszu poleceń po podzieleniu go na słowa. Istnieje siedem rodzajów interpretacji: interpretacja nawiasów, interpretacja tyldy, interpretacja parametrów i zmiennych, podstawianie poleceń, interpretacja arytmetyczna, dzielenie słów i interpretacja nazw ścieżek.

    Kolejność rozszerzeń jest następująca: nawias klamrowy; interpretacja tyldy, interpretacja parametrów i zmiennych, interpretacja arytmetyczna i podstawianie poleceń (wykonywane od lewej do prawej); dzielenie słów; i rozszerzenie nazwy ścieżki.

Zasadniczo Bash najpierw wykonuje podstawienie zmiennych, aby $1najpierw zastąpić je swoją wartością. Dopiero wtedy dokonuje ekspansji arytmetycznej, która widzi tylko odpowiednią stałą.


To wydaje się niepotrzebne; OP mówi: „Rozumiem, że $1to jest wkład”.
Scott

8
+1, ponieważ zrozumienie kolejności rozwijania jest bardzo przydatne do zrozumienia wielu różnych wyrażeń Bash.
Anthony G - sprawiedliwość dla Moniki

1
To mógł być po prostu komentarz do odpowiedzi Iporta.
chepner

1
@chepner Spróbuj wycisnąć dobrze sformatowany cytat blokowy w komentarz :-)
Alexander

1
„Zauważ, że parametr $1jest rozszerzany, aby uzyskać stałą całkowitą przed obliczeniem wyrażenia arytmetycznego. Zobacz gnu.org/software/bash/manual/bash.txt , sekcja 3.5”
chepner
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.