met*_*ion 215 command-line shell bash
我发现自己重复了很多:
mkdir longtitleproject
cd longtitleproject
Run Code Online (Sandbox Code Playgroud)
有没有办法在一行中完成而不重复目录名称?我在这里狂欢。
Jes*_*era 211
这是您需要的单衬。不需要其他配置:
mkdir longtitleproject && cd $_
Run Code Online (Sandbox Code Playgroud)
$_bash 中的变量是给上一个命令的最后一个参数。在这种情况下,您刚刚创建的目录的名称。如中所述man bash:
_ At shell startup, set to the absolute pathname used to invoke
the shell or shell script being executed as passed in the envi?
ronment or argument list. Subsequently, expands to the last
argument to the previous command, after expansion. Also set to
the full pathname used to invoke each command executed and
placed in the environment exported to that command. When check?
ing mail, this parameter holds the name of the mail file cur?
rently being checked."$_" is the last argument of the previous command.
Run Code Online (Sandbox Code Playgroud)
使用cd $_检索前面的命令,而不是最后一个参数cd !$,因为cd !$给前一个命令的最后一个参数在shell的历史记录:
cd ~/
mkdir folder && cd !$
Run Code Online (Sandbox Code Playgroud)
你最终回家(或 ~/ )
cd ~/
mkdir newfolder && cd $_
Run Code Online (Sandbox Code Playgroud)
你最终会出现在 home 下的 newfolder 中!!(或 ~/newfolder )
Gil*_*il' 194
没有内置命令,但您可以轻松编写一个调用mkdirthen的函数cd:
mkcd () {
mkdir "$1"
cd "$1"
}
Run Code Online (Sandbox Code Playgroud)
将此代码放在您的~/.bashrc文件中(或~/.kshrc用于 ksh 用户,或~/.zshrc用于 zsh 用户)。它定义了一个名为mkcd. "$1"运行时将被函数的参数替换。
这个简单的版本有几个缺陷:
-p选项传递给mkdir. (这可能是也可能不是可取的,因为它增加了错误未被发现的风险,例如mkcd mydierctory/newsub会很高兴地创建mydierctory,mydierctory/newsub当您打算newsub在现有mydirectory. 中创建时。)-但不只是-,则mkdirandcd会将其解释为一个选项。如果只是-,cd则将其解释为意思$OLDPWD。如果+后面跟着 0 个或多个数字,则cd在 zsh 中会将其解释为目录堆栈中的索引。您可以通过--在参数之前传递来解决第一个问题,但不能解决其他两个问题。如果./参数是相对路径,您可以通过在参数前面添加来解决所有这些问题。mkdir不遵循CDPATH,但遵循,cd所以如果您设置CDPATH了一个不以开头的值.(公认的有点不寻常的配置),那么cd可能会将您带到与刚刚创建的目录不同的目录。前置./相对路径修复了这个¹(它会导致CDPATH被忽略)。mkdir失败,它会尝试执行cd。修复:用于&&分隔两个命令。还是比较简单的:
mkcd () {
mkdir "$1"
cd "$1"
}
Run Code Online (Sandbox Code Playgroud)
这个版本仍然有可能cd进入与mkdir刚刚在一种边缘情况下创建的目录不同的目录:如果参数mkcd包含..并通过符号链接。例如,如果当前目录是/tmp/here并且mylink是指向 的符号链接/somewhere/else,则mkdir mylink/../foo创建/somewhere/else/foo而cd mylink/../foo更改为foo。仅在参数中查找符号链接是不够的,因为 shell 还在其自己的当前目录中跟踪符号链接,因此cd /tmp/mylink; mkdir ../foo; cd ../foo不会更改为新目录 ( /somewhere/else/foo) 而是更改为/tmp/foo. 对此的解决方法是让cd内置..程序首先解析所有路径组件(foo/..如果foo不存在,所以mkdir永远不需要看到任何..)。
我们来到这个强大但有点血腥的版本:
mkcd () {
case "$1" in /*) :;; *) set -- "./$1";; esac
mkdir -p "$1" && cd "$1"
}
Run Code Online (Sandbox Code Playgroud)
(练习:为什么我在第一次cd调用时使用子shell ?)
如果 mkdir 失败,我想确保不要更改当前目录。如果 shell 没有更改到其当前目录的权限,用 cd - 或 $OLDPWD 改回来就不够好。此外,调用 cd 更新 OLDPWD,因此我们只想执行一次(或恢复 OLDPWD)。
还有一些不太专业的方法可以不必重新输入上一行中的单词:
cd ,然后Esc .(或Alt+ .)以插入上一个命令的最后一个参数。cd !$在cd上一个命令的最后一个参数上执行。mkdir为cd.¹ 但是请注意,它在 ksh93 中不起作用,因为u+版本已在 93u+m/1.0.0-alpha+d1483150 2021-01-05 中修复
Rob*_*Rob 32
我从来没有想过要编写这种行为,因为我几乎每小时都输入以下内容......
$ mkdir someDirectory<ENTER>
$ cd !$
Run Code Online (Sandbox Code Playgroud)
其中 bash 善意地!$用最后一行的最后一个字代替;即您输入的长目录名称。
此外,在这种情况下,文件名补全是您的朋友。如果您的新目录是文件夹中的唯一文件,则快速复制TAB将为您提供新目录,而无需重新输入。
尽管 bash 允许您编写其他答案所建议的此类常见任务很酷,但我认为最好学习 bash 必须提供的命令行编辑功能,这样当您在另一台机器上工作时,您就不会错过语法您的自定义脚本提供的糖。
小智 23
如果您使用 Oh My Zsh,则有一个名为take的命令可以执行此操作。它看起来像这样。
take myfolder
Run Code Online (Sandbox Code Playgroud)
我实际上是偶然发现了这个。我只是看着它的上市在此cheatsheat从噢,我的岩组GitHub的维基。这是一个非常有用的命令,而且显然很容易自己创建。
Mik*_*kel 17
根据您对 shell 配置文件进行了哪些自定义以提高生产力?,这就是我的做法:
# make a directory and cd to it
mcd()
{
test -d "$1" || mkdir "$1" && cd "$1"
}
Run Code Online (Sandbox Code Playgroud)
这意味着如果目录已经存在,它也可以工作。