Das Zeichen '#' kann nicht als Befehlszeilenargument übergeben werden

36

Ich kann keine Zeichenfolgen übergeben, die #als Befehlszeilenargumente beginnen .

Hier ist ein einfacher Test:

#include <stdio.h>

int main(int argc, char *argv[])
{
    for (int i = 1; i < argc; i++)
        printf("%s ", argv[i]);

    putchar('\n');

    return 0;
}

Wenn ich die Argumente wie folgt eingebe:

2 4 # 5 6

Der Wert von argcist 3und nicht 6. Es liest #und stoppt dort. Ich weiß nicht warum und kann die Antwort in meinen Kopien von The C Programming Language und C Primer Plus nicht finden .

cd-00
quelle
44
Die Syntaxhervorhebung auf StackOverflow veranschaulicht Ihr Problem gut :)
Brad Allred

Antworten:

47

#beginnt einen Kommentar in Unix-Shells, ähnlich wie //in C.

Dies bedeutet, dass die Shell, wenn sie die Argumente an das Programm übergibt, alles ignoriert, was auf das # folgt. Wenn Sie es mit einem Backslash oder Anführungszeichen versehen, wird es wie die anderen Parameter behandelt und das Programm sollte wie erwartet funktionieren.

2 4 \# 5 6

oder

2 4 '#' 5 6

oder

2 4 "#" 5 6

Beachten Sie, dass dies #nur am Anfang eines Wortes ein Kommentarzeichen ist. Dies sollte also auch funktionieren:

2 4#5 6
fanduin
quelle
2
Dies scheint eine ziemlich gute Liste zu sein unix.stackexchange.com/a/270979
fanduin
22
@ cd-00 Sie müssen lernen, wie die Shell funktioniert. Dies hat nichts mit Ihrem C-Code zu tun.
Chepner
3
Ah, Sie können also Kommentare in interaktiven Shell-Sitzungen eingeben, damit die Shell sie sofort nach Abschluss der Eingabe ignorieren kann. Was für eine nützliche Funktion.
Joker_vD
6
@Joker_vD Während Sie sich eine Shell als Befehlszeilenschnittstelle vorstellen, handelt es sich tatsächlich um einen Skriptinterpreter. Die Tatsache, dass Sie es wie eine interaktive CLI verwenden können, ist ein schöner Bonus. Warum sollte sich das Interpretierte erheblich anders verhalten, wenn Sie "ein Skript ausführen", als wenn Sie Befehle interaktiv eingeben? Was ist echo echo Hello, World | bash. Ist das interaktiv? Oder vielleicht bash <<END?
Christopher Schultz
6
@Joker_vD: Ich tippe häufig Kommentare in interaktiven Sitzungen ein, auf die ich in meinem Shell-Verlauf zurückgreifen kann. Manchmal dient dies dazu, einen Commit-Hash oder eine andere ID aufzuzeichnen, die an stdout ausgegeben wird. manchmal ist zu beachten, dass ein Befehl als Hinweis auf mein zukünftiges Selbst fehlgeschlagen ist; Manchmal werden Zeitdaten für das Ad-hoc-Benchmarking aufgezeichnet. Es ist eine nützliche Funktion.
Wchargin
12

Wenn Sie den Wert über Befehlszeilenargumente übergeben, müssen Sie die folgenden Anweisungen durchgehen. Die folgenden Zeichen haben in einigen Kontexten eine besondere Bedeutung für die Shell selbst und müssen möglicherweise in Argumenten maskiert werden:

` Backtick (U+0060 Grave Accent)
~ Tilde (U+007E)
! Exclamation mark (U+0021)
# Hash (U+0023 Number Sign)
$ Dollar sign (U+0024)
& Ampersand (U+0026)
* Asterisk (U+002A)
( Left Parenthesis (U+0028)
) Right parenthesis (U+0029)
 (⇥) Tab (U+0009)
{ Left brace (U+007B Left Curly Bracket)
[ Left square bracket (U+005B)
| Vertical bar (U+007C Vertical Line)
\ Backslash (U+005C Reverse Solidus)
; Semicolon (U+003B)
' Single quote / Apostrophe (U+0027)
" Double quote (U+0022)
↩ New line (U+000A)
< Less than (U+003C)
> Greater than (U+003E)
? Question mark (U+003F)
  Space (U+0020)1
VJAYSLN
quelle
3
Wie sollen sie dann entkommen?
Ilkkachu
3
\ - Escape mit Backslash .EX:2 4 \{#,$,&,*} 5 6
VJAYSLN
8

Das liegt daran, dass Sie eine shähnliche Shell verwenden. Zitieren Sie die# oder entkommen Sie es mit \und es wird funktionieren.

Dies wird als Kommentar in bezeichnetsh . Es bewirkt, dass der #(Leerzeichen-Hash) und alle Argumente danach verworfen werden. Es wird ähnlich wie Kommentare in C verwendet, wo es zum Dokumentieren von Code verwendet wird.

Zeichenfolgen, die mit beginnen, $werden als Variablen bezeichnet in sh. Wenn Sie keine Variable festgelegt haben, wird diese zu einer leeren Zeichenfolge erweitert.

All dies wären beispielsweise gültige Möglichkeiten, um das #an Ihre Anwendung weiterzuleiten :

2 4 '#' 5 6
2 4 "#" 5 6
2 4 \# 5 6

Und dies wären gültige Möglichkeiten, um eine Zeichenfolge zu übergeben, beginnend mit $:

2 4 '$var' 5 6
2 4 '$'var 5 6
2 4 \$var 5 6

Bitte beachten Sie, dass Variablen in "s noch erweitert sind.

SS Anne
quelle