如何在bash中使用if-not条件打印文件

如何在bash中使用if-not条件打印文件,bash,shell,if-statement,Bash,Shell,If Statement,假设我在一个目录中有三个文件dir touch a.ym b.ym a.job 如果没有相应的*.job文件,我需要打印所有*.ym。 这就是我所尝试的 for file in $(find ${dir} -name \*.ym);do filebase=$(basename $file) sample_id=$(echo "${filebase}"| awk -F'[.]' '{print $1}') if [[ $sample_id != *".job" ]];

假设我在一个目录中有三个文件
dir

touch a.ym b.ym a.job 
如果没有相应的
*.job
文件,我需要打印所有
*.ym
。 这就是我所尝试的

for file in $(find ${dir} -name \*.ym);do
    filebase=$(basename $file)
    sample_id=$(echo "${filebase}"| awk -F'[.]' '{print $1}')
    if  [[ $sample_id != *".job" ]]; then
          echo "${file}"
    fi
done
然而,上面的解决方案是同时打印这两种内容


a.ym b.ym
文件,其中我只需要打印出
b.ym
文件

我赞赏您在使用您熟悉的工具方面的足智多谋,但您在使用
find
awk
命令方面做了大量工作,这些命令只需使用
bash
即可轻松完成

试试这个:

答复
用于“${dir}”/*.ym中的ym_文件;做
job_file=“${ym_file/.ym/.job}”
如果[!-f“$job_file”];然后
echo“${ym_file}没有匹配的作业文件”
fi
完成
解释
  • “${dir}”/*.ym
    :可以直接在bash中使用全局匹配。如果您没有任何
    .ym
    文件,这将出错,但在这种情况下它不会做任何坏事
  • “${ym\u file/.ym/.job}”
    :这是一个
    bash
    模式替换。它将
    .ym
    的所有实例替换为
    .job
    。我假设这些模式不会出现在您的文件名中,除非在末尾
  • [!-f“$job_file”]
    -f
    标志测试是否存在常规文件,以及
    否定它(因此测试是否缺少常规文件)
c.f.和内置工具

for f in *.ym
do [[ -e "${f%.ym}.job" ]] || echo "$f"
done
在Bash中:

要确保使用
bash
解释器运行可执行脚本,必须确保脚本中的第一个字符是
#
,后跟一个将调用
bash
的命令。第一行示例如下:

#!/bin/bash
通常,对不匹配的全局模式的扩展将导致原始全局模式。这在我们的情况下是不可取的。为了使不匹配的glob计算为空文件列表,需要启用
nullglob
选项,如下所示:

shopt -s nullglob
以下表达式的计算结果为目录
$dir
中名称以
.ym
结尾的文件列表:

"$dir"/*.ym
以下计算结果为文件的文件名前缀,
$file

"${file%.*}"
检查文件是否不存在的条件是:

if [[ ! -f "${file}" ]]; then
  ... the file does not exist ...
fi
将这些点组合在一起将生成以下脚本:

#!/bin/bash

shopt -s nullglob

for file in "$dir"/*.ym; do
  if [[ ! -f "${file%.*}.job" ]]; then
    echo "$file"
  fi
done