Why does this Java code print two arguments?

Computer Science Engineer :

The below Java code prints two arguments when I pass !clear as input as shown below.

class Test{

    public static void main(final String... arguments){
        for(String argument : arguments){
            System.out.println(argument);
        }
    }

}

Output:

$ java Test !clear
java Test clear
clear

UPDATE

Using any linux command in place of clear produces the same result.

$ java Test !pwd
java Test pwd
pwd

$ java Test !ls
java Test ls
ls

I am aware that this has got something to do with history expansion in bash and I can escape the ! character to solve this issue.

However, I am curious to know the exact reason why this code prints the above two lines as output. Could somebody please explain?

RealSkeptic :

You are working within a Unix/Linux shell, probably bash. The ! character is a special character in the Unix shell, and thus your command is considered a history expansion.

In history expansion, the usual thing that happens is that the shell shows you what the command expands to. The expansion of !clear will simply be clear provided that you had the command clear in your history, and the expanded command will therefore be java Test clear. The shell then runs the command. Java runs and only sees one argument - clear, and that's what it prints.

If instead, you run

java Test '!clear'

(With the single quotes!)

Java will get the argument !clear as is, without history expansion.

If you use a word that is not in the shell's history of commands, you'll get an "event not found error". If you use a word that, in your shell history, started a command with arguments, the entire command with all its arguments will be substituted. This is all part of bash and not Java.

Guess you like

Origin http://10.200.1.11:23101/article/api/json?id=471967&siteId=1