A couple days ago I wrote a post about bash's history completion. It has since been brought to my attention that lesser programmers are in the habit of making "mistakes" when typing commands. This post is dedicated to those unfortunate souls.
If you're unsure what a history expansion will do, you can have bash print it out:
$ touch !-3*:p # recall that !-3* is the arguments of the third most recent command. # the new command is echoed but *not* run touch king of the world
The expanded line will be added to your history even though it wasn't run, so if it's what you wanted you can run it with !!. If it's close but not quite right, hit up or ^P to edit it.
This colon nonsense also lets you perform substitutions:
$ vin ordinaire bash: vin: command not found $ !!:s/n/m vim ordinaire
Note that only the first instance of the first string is substituted. Using gs instead of s will replace every match.
That's handy, but a little verbose. There's a short form that's equivalent to !!:s:
$ grep -lIr awesomeness ./* # whoops, I wanted that to be case insensitive $ ^l^il grep -ilIr awesomeness ./* ./todo:1005: (Note: this item should increase my AWESOMENESS by 2.7%.)
Finally, in the last post I forgot^H^H^H^H^H^Hwas too awesome to mention that !? will find a match anywhere in the command, not just the beginning:
$ !?dev vim /dev/null
This is not exhaustive, believe it or not, but we've covered all of the options that I use. If you think you need to know more about bash history expansion, I recommend seeking immediate psychiatric help. But while you're waiting you could read what Arabesque or Peteris Krumins have to say about the subject (spoiler: a lot).