Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

I would like to take the output of a which command, and cd to the parent directory. For example, say I have the following:

which someprogram

With output:

/home/me/somedirectory/someprogram

And I would like to cd to the directory that someprogram lives in:

cd /home/me/somedirectory

I'd like to accomplish this in one line. What is the most elegant, tricky, short way to do this?

share|improve this question
add comment

2 Answers

up vote 13 down vote accepted

Use dirname:

cd "`dirname $(which program)`"
share|improve this answer
6  
+1 but use $() instead of backticks: cd $(dirname $(which program)) –  glenn jackman Dec 1 '11 at 21:49
1  
@glennjackman It works fine with one pair of backticks (as shown in the answer, or the other way around with the $() on the outside and the backticks on the inside). It just wouldn't work with an inner pair of backticks nested inside a separate outer pair of backticks. –  Eliah Kagan Dec 2 '11 at 3:53
1  
@EliahKagan I think @glennjackman's point was not that backticks don't work, but that they should be gradually phased out in favor of $() due to the many advantages of $() over backticks. –  jw013 Dec 26 '11 at 17:57
add comment

In bash, I recommend type -p over which. which is an external command and it's tricky at times. You can use sed to remove everything after the final /, or use the special-purpose dirname utility.

cd "$(dirname -- "$(type -p program)")"
cd "$(type -p program | sed 's:[^/]*$::')"

On the command line, if you know that the directory doesn't contain any special characters (whitespace or \[?*), you can omit the quotes. You can also use backquotes instead of one of the $(…) (nesting backquotes is difficult, not worth it here).

cd `dirname $(type -p program)`
cd $(dirname `type -p program`)
cd `type -p program | sed 's:[^/]*$::'`

In zsh, there's a more compact syntax.

cd ${$(whence -p program):h}
cd ${$(echo =program):h}
cd ${${_+=program}:h}

(Yes, that last one is cryptic. It uses the ${VAR+TEXT} syntax on the _ variable, with the value being =program which is equivalent to $(whence -p program).)

share|improve this answer
add comment

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.