I saw a discussion of this in
http://unix.stackexchange.com/questions/1906/direct-command-line-into-a-specified-directory
To get a list of commonly-used directories, put this in ~/.bashrc:
# track directories used. cd () { builtin cd "$@" /bin/pwd >> ~/.bashdir.new }
After a week or so, run this:
me% cd me% sort .bashdir.new | uniq -c | sort -n > .bashdir.common
The .bashdir.common file might look like this after you keep just the directories you use the most often:
20 /usr/local/src 20 /var/adm/sa/perflog 21 /backup/today 23 /tmp 24 /data01 24 /data02 24 /data03 24 /data04 24 /data05 24 /data06 24 /data07 24 /data08 27 /home/yourname/projects 28 /doc/templates 28 /doc/html 32 /var/log/samba 35 /usr/local/cron 35 /usr/local/lib 35 /usr/local/bin
Make your quick-change list:
me% mkcdlist .bashdir.common > .bashdir me% cat .bashdir 0 /usr/local/src 1 /var/adm/sa/perflog 2 /backup/today 3 /tmp 4 /data01 5 /data02 6 /data03 7 /data04 8 /data05 9 /data06 a /data07 b /data08 c /home/yourname/projects d /doc/templates e /doc/html f /var/log/samba g /usr/local/cron h /usr/local/lib i /usr/local/bin
#!/bin/ksh #<mkcdlist: read up to 36 common directories, write a list for g. t1=/tmp/cd1$$ t2=/tmp/cd2$$ num='0 1 2 3 4 5 6 7 8 9' let='a b c d e f g h i j k l m n o p q r s t u v w x y z' max=36 # Make sure we have a file to read... case "$#" in 1) file=$1 ;; *) echo no file; exit 0 ;; esac # ... and that it doesn't have more lines than we have letters. set X $(wc -l $file) lines=$2 test "$lines" -gt $max && { echo $file has more than $max lines, please trim it; exit 1 ; } # Write unique number/letter for each directory. echo "$num $let" | fmt -1 | head -$lines > $t1 expand $file | sed -e 's!^.* /!/!' > $t2 paste $t1 $t2 | expand -4 echo rm $t1 $t2 exit 0
g CR number-or-letter
You'll see your directory list. Press one letter or number and you immediately change to that directory.
You'll need a program called "grabchars", which you can find on a comp.sources.misc archive or by using http://www.filewatcher.com/. Grabchars lets you handle single-character feedback in a portable fashion via command line or shell-script. For example, running
grabchars -c 0123456789 -n2 -t10
interactively reads two numbers with a ten-second timeout, no need to press return after the numbers.
[ Section on installation of grabchars ]
g () { clear cat $HOME/.bashdir local prompt="dir: " local ans=`grabchars -d0 -L -c '[0-9a-zA-Z]' -q"$prompt"` set X `grep "^$ans" $HOME/.bashdir` case "$#" in (3) cd $3 ;; (*) echo no such entry ;; esac }
g () { clear cat $HOME/.bashdir2 local prompt="dir: " local ans=`grabchars -d- -c '[0-9a-zA-Z]' -q"$prompt"` case "$ans" in (-) return ;; (*) ;; esac set X `fmt -1 $HOME/.bashdir | fgrep "${ans}=" | tr "=" " "` case "$#" in (3) cd $3 && ( echo; echo; pwd; echo; ls -F --color=always -blptF --time-style='+%d-%b-%Y %T' | sed -e '/^total/d') ;; (*) echo no such entry ;; esac }
Popular directories 0=/etc l=/etc/hp G=/etc/reader.conf.d 1=/etc/X11 m=/etc/httpd H=/etc/rhgb 2=/etc/acpi n=/etc/logrotate.d I=/etc/rpm 3=/etc/bluetooth o=/etc/logwatch J=/etc/rwtab.d 4=/etc/cron.daily p=/etc/lvm K=/etc/sane.d 5=/etc/cron.hourly q=/etc/mail L=/etc/security 6=/etc/cron.monthly r=/etc/modprobe.d M=/etc/selinux 7=/etc/cron.weekly s=/etc/netplug N=/etc/setuptool.d 8=/etc/cups t=/etc/netplug.d O=/etc/skel 9=/etc/default u=/etc/ntp P=/etc/smrsh a=/etc/dev.d v=/etc/openldap Q=/etc/sound b=/etc/firmware w=/etc/opt R=/etc/squid c=/etc/fonts x=/etc/pam.d S=/etc/ssh d=/etc/foomatic y=/etc/pango T=/etc/stunnel e=/etc/gconf z=/etc/pcmcia U=/etc/subversion f=/etc/gdm A=/etc/pki V=/etc/sysconfig g=/etc/ghostscript B=/etc/pm W=/etc/udev h=/etc/gnome-vfs-2.0 C=/etc/ppp X=/etc/xdg i=/etc/gre.d D=/etc/profile.d Y=/etc/xinetd.d j=/etc/gtk-2.0 E=/etc/rc.d Z=/etc/yum k=/etc/hal F=/etc/readahead.d
If you have this many directories, it might be worth your while to use a file-manager like mc or vshnu.
$Revision: 1.5 $ $Date: 2010-10-13 14:31:07-04 $ $UUID: e58400c5-8a64-3d05-81c9-84d484c46ab1 $