404

Is there a way in Bash to recall the argument of the previous command?

I usually do vi file.c followed by gcc file.c.

Is there a way in Bash to recall the argument of the previous command?

user2314737
  • 27,088
  • 20
  • 102
  • 114
The Coder
  • 4,043
  • 3
  • 16
  • 4
  • 2
    Possible duplicate : http://stackoverflow.com/questions/4009412/bash-first-argument-of-the-previous-command – eugenevd Jul 11 '13 at 14:25

7 Answers7

717

You can use $_ or !$ to recall the last argument of the previous command.

Also Alt + . can be used to recall the last argument of any of the previous commands.

Serge Stroobandt
  • 28,495
  • 9
  • 107
  • 102
codaddict
  • 445,704
  • 82
  • 492
  • 529
  • 155
    Also, if you want an arbitrary argument, you can use `!!:1`, `!!:2`, etc. (`!!:0` is the previous command itself.) See http://www.gnu.org/software/bash/manual/bashref.html#History-Interaction – janmoesen Jul 30 '10 at 12:21
  • 62
    Similar to `!$`, you use `!^` for the first argument. – Will Oct 26 '15 at 21:22
  • 23
    ahh... *nix... you are a thing of beauty... everyday I love you more – jx12345 May 26 '17 at 12:36
  • How can we refer to the second to last argument of the previous command? for example, If I gave `echo tiger rabbit`, how can I refer `tiger` at the following command? – Chan Kim Nov 02 '17 at 04:45
  • 10
    `Alt + .` doesn't work in vi mode. Just FYI, for others who were confused here. – Brian McCutchon Nov 01 '18 at 01:32
  • 4
    Note that `!$` print the full command in the first line when run, while `$_` doesn't. – 林果皞 Jun 17 '19 at 20:25
  • This is truly incredible. I love the `M-.` feature. Where is this documented? – young_souvlaki Jun 05 '20 at 23:03
  • 2
    @young_souvlaki see `man bash`, quite literally everything is in that, you just have to actually read it (which is the hard part, but look under 'HISTORY EXPANSION' and 'Commands for Manipulating the History' in particular. For GNU readline related stuff (which is most key binding related stuff outside of bash): https://tiswww.cwru.edu/php/chet/readline/rltop.html#TOCDocumentation – Chris Aug 19 '20 at 00:17
  • Is there a way I can make ` + .` work in vi mode? is there a similar workaround for zsh? – hundredrab Dec 08 '20 at 15:36
  • 2
    how does it work on mac? I use mac + iterm2, press Alt + . only shows "≥" – Chen Jan 07 '21 at 06:26
  • @Chen have to use osx at the moment, have not yet found a shortcut solution – Felix Oct 14 '21 at 07:32
  • @Chen Try using `ESC .` See the bash man page, under "Readline Notation": _"[...] Similarly, meta keys are denoted by M-key, so M-x means Meta-X. (On keyboards without a meta key, M-x means ESC x, i.e., press the Escape key then the x key. This makes ESC the meta prefix."_ – cilix May 26 '22 at 15:35
  • `$_` in the JavaScript console does a very similar thing! It returns the last result. E.g. `2+3` followed by _Enter_ gives `5` and then `$_` followed by _Enter_ also gives `5`. – Purplejacket Sep 18 '22 at 22:12
201

If the previous command had two arguments, like this

ls a.txt b.txt

and you wanted the first one, you could type

!:1

giving

a.txt

Or if you wanted both, you could type

!:1-2

giving

a.txt b.txt

You can extend this to any number of arguments, eg:

!:10-12
Robert Gowland
  • 7,677
  • 6
  • 40
  • 58
  • @RNA, I just tried it again to make sure I didn't include a typo, could you provide a little more detail (eg. ubuntu command line, cygwin for windows? error message? previous line?) – Robert Gowland Feb 14 '14 at 14:59
  • I am using GNU bash, version 3.2.51(1)-release (x86_64-apple-darwin13) Copyright (C) 2007 Free Software Foundation, Inc. The error message is `-bash: :1-2: bad word specifier` – RNA Feb 14 '14 at 18:21
  • 2
    I get the same thing if there weren't two arguments in the previous line. Eg. line 1 `ls a.txt` line 2 `ll !:1-2` – Robert Gowland Feb 15 '14 at 17:35
  • you're right. That is a stupid mistake I made. thanks! – RNA Feb 15 '14 at 21:04
  • Also to get all of the arguments, `!:^-$` can be used or of course similar code in combination with numbers. – 816-8055 Jun 26 '17 at 10:23
  • 1
    [sighs]... what a wonderful way to be distracted at work - just love this – user115014 May 22 '19 at 16:14
  • `!:-3` or `!:3-` works also (for all arguments until/from the 3rd argument) – Jonas Eberle May 22 '21 at 11:37
145

!!:n where n is the 0-based position of the argument you want.

For example:

echo 'one' 'two'
# "one two"

echo !!:2
# "two"

The ! prefix is used to access previous commands.

Other useful commands:

  • !$ - last argument from previous command
  • !^ - first argument (after the program/built-in/script) from previous command
  • !* - all arguments from previous command
  • !! - previous command (often pronounced "bang bang")
  • !n - command number n from history
  • !pattern - most recent command matching pattern
  • !!:s/find/replace - last command, substitute find with replace

More info on command history

Johntron
  • 2,443
  • 2
  • 24
  • 26
87

In the command-line, you can press alt+. or esc-.

It cycles through the last argument of your previous commands.

Sridhar Ratnakumar
  • 81,433
  • 63
  • 146
  • 187
Antonio Mano
  • 970
  • 5
  • 4
  • 1
    I've always found the `↑` and `↓` keys to work as well. – Bucket Nov 29 '18 at 14:44
  • 5
    @Bucket keys go though previous commands, while the solution provided by Antonio allows to go through previous arguments (last argument of each previous command only) – everyonesdesign Apr 18 '19 at 12:16
33

If you know the number given in the history for a particular command, you can pretty much take any argument in that command using following terms.

Use following to take the second argument from the third command in the history,

!3:2

Use following to take the third argument from the fifth last command in the history,

!-5:3

Using a minus sign, you ask it to traverse from the last command of the history.

Madisz
  • 433
  • 4
  • 4
  • For some reason, on MacOS 11.6.1 Terminal, zsh 5.8 (x86_64-apple-darwin20.0) This doesn't work. It looks like zsh ignores the '-' sign - and takes n simply from the start of list. What to do? which 'man' page to consult? – Motti Shneor Oct 29 '21 at 08:55
25

!* runs a new command with all previous arguments.

ls /tmp
cd !*
#you are now in /tmp
22

Yes, you can use !$ to recall the last argument of the preceding command.

Justin Ethier
  • 131,333
  • 52
  • 229
  • 284
  • 2
    Be aware of the key word "last," especially if your command contained multiple arguments. – Bucket Nov 29 '18 at 14:41