bash程序将所有文件从一个位置复制到另一个位置
我试图编写一个简单的bash程序,在我的终端上执行,它将把一个目录中的所有文件复制到另一个目录。这是我的第一个bash程序。这就是我现在拥有的:bash程序将所有文件从一个位置复制到另一个位置,bash,file,terminal,Bash,File,Terminal,我试图编写一个简单的bash程序,在我的终端上执行,它将把一个目录中的所有文件复制到另一个目录。这是我的第一个bash程序。这就是我现在拥有的: #!/bin/bash cd /Users/georgi/Loopback_projects/ESPC/common/models for f in *.json do cp -v $f /Users/georgi/AndroidStudioProjects/ESPC_Retrofit/app/src/main/assets done 当我在终端中运
#!/bin/bash
cd /Users/georgi/Loopback_projects/ESPC/common/models
for f in *.json
do
cp -v $f /Users/georgi/AndroidStudioProjects/ESPC_Retrofit/app/src/main/assets
done
当我在终端中运行脚本时,如下所示:
Chriss-iMac:georgi$ exportToAndroid.sh
它显示-bash:exportToAndroid.sh:command not found
简短回答:
chmod +x exportToAndroid.sh
./exportToAndroid.sh
长答覆: 当您在终端中输入内容时,字符串被解析、切碎为单词,并且(除了重定向、环境变量或其他关键字)第一个单词被理解为要执行的命令。如果shell将这个词识别为一个函数或一个内置项(我在这里忽略别名),那么它将使用给定的参数运行这个函数或内置项;但我们不是在这种情况下:
exportToAndroid.sh
也不是。在这种情况下(因为这个单词不包含斜杠),shell将查看路径
变量,检查是否找到名为exportToAndroid.sh的文件(如果找到了,它会愉快地执行它);但在这里却找不到!(使用echo“$PATH”
检查PATH
变量包含的内容)
如果不是给出一个无斜杠的单词,而是给出一个带斜杠的路径,那么shell将不会查看path
变量,而是尝试直接执行给定的文件。这就是为什么
./exportToAndroid.sh
会有用的
如果您不想每次都在前面键入/
,下面是一个好办法:
在主文件夹中创建一个带有
mkdir ~/bin
将此目录添加到PATH
变量,如下所示:在.bashrc
文件的末尾,添加行PATH=~/bin:$PATH
(这不是将~/bin
预先添加到PATH
变量的可靠方法,但应该可以)
将脚本移动到~/bin
文件夹
重新启动Bash会话;您可以使用echo“$PATH”
检查~/bin
文件夹是否显示在路径
变量的第一个位置
几个月后,你会发现你的bin/
文件夹里有很多你完全忘记的无用的东西李>
这样做的好处是,您只需从任何目录中使用exportToAndroid.sh
调用脚本
关于代码的注释:
- 在脚本中,在
cd
之后,应始终检查cd
是否成功!一种可能性:
cd /Users/georgi/Loopback_projects/ESPC/common/models || { echo "Can't cd"; exit 1; }
- 在使用变量扩展时,除非您真的希望进行分词和文件名扩展(您很少希望这样做!事实上,这是一种非常罕见的做法,当我们希望发生这种情况时,我们总是写一行注释来解释我们的意图),您必须引用扩展名:您的
cp
行最好写为
cp -v "$f" /Users/georgi/AndroidStudioProjects/ESPC_Retrofit/app/src/main/assets
(见引文?)
- 当使用glob时,如*.json中f的
中,您应该确保启用了shopt-s nullglob
(或shopt-s failglob
)
此时,您的脚本应该如下所示:
#!/bin/bash
shopt -s nullglob
cd /Users/georgi/Loopback_projects/ESPC/common/models || { echo "Can't cd"; exit 1; }
for f in *.json; do
cp -v "$f" /Users/georgi/AndroidStudioProjects/ESPC_Retrofit/app/src/main/assets
done
但事实上,更简单、更有效的方法是:
#!/bin/bash
shopt -s failglob
sourcedir=/Users/georgi/Loopback_projects/ESPC/common/models
targetdir=/Users/georgi/AndroidStudioProjects/ESPC_Retrofit/app/src/main/assets
cp -v "$sourcedir"/*.json "$targetdir"
它的效率更高,因为我们只调用cp
一次,而不是每个文件复制一次
然而,如果有太多的文件要复制,这将失败。。。但它可以处理大小合理的目录。简短回答:
使用以下命令使脚本可执行:
chmod +x exportToAndroid.sh
使用以下命令运行它:
./exportToAndroid.sh
长答覆:
当您在终端中输入内容时,字符串被解析、切碎为单词,并且(除了重定向、环境变量或其他关键字)第一个单词被理解为要执行的命令。如果shell将这个词识别为一个函数或一个内置项(我在这里忽略别名),那么它将使用给定的参数运行这个函数或内置项;但我们不是在这种情况下:exportToAndroid.sh
也不是。在这种情况下(因为这个单词不包含斜杠),shell将查看路径
变量,检查是否找到名为exportToAndroid.sh的文件(如果找到了,它会愉快地执行它);但在这里却找不到!(使用echo“$PATH”
检查PATH
变量包含的内容)
如果不是给出一个无斜杠的单词,而是给出一个带斜杠的路径,那么shell将不会查看path
变量,而是尝试直接执行给定的文件。这就是为什么
./exportToAndroid.sh
会有用的
如果您不想每次都在前面键入/
,下面是一个好办法:
在主文件夹中创建一个带有
mkdir ~/bin
将此目录添加到PATH
变量,如下所示:在.bashrc
文件的末尾,添加行PATH=~/bin:$PATH
(这不是将~/bin
预先添加到PATH
变量的可靠方法,但应该可以)
将脚本移动到~/bin
文件夹
重新启动Bash会话;您可以使用echo“$PATH”
检查~/bin
文件夹是否显示在路径
变量的第一个位置
几个月后,你会发现你的bin/
文件夹里有很多你完全忘记的无用的东西李>
这样做的好处是,您只需从任何目录中使用exportToAndroid.sh
调用脚本
关于代码的注释:
- 在脚本中,在
cd
之后,应始终检查cd
是否成功!一种可能性:
cd /Users/georgi/Loopback_projects/ESPC/common/models || { echo "Can't cd"; exit 1; }
- 当使用变量扩展时,除非您真的希望进行分词和文件名扩展