这是我的问题:我正在尝试解析系统上的很多文件以找到一些令牌。我的令牌存储在一个文件中,每行一个令牌(例如token.txt)。我的解析路径也存储在另一个文件中,每行一个路径(例如path.txt)。
我使用find
和grep
的组合来完成我的工作。这是一次尝试:
for path in $(cat path.txt)
do
for line in $(find $path -type f -print0 | xargs -0 grep -anf token.txt 2>/dev/null);
do
#some stuffs here
done
done
它似乎工作正常,但我真的不知道是否有其他方法可以让它更快(我是编程和shell的初学者)。
我的问题是:对于find
命令找到的每个文件,我想获取所有压缩的文件。为此,我想使用file
命令。问题是我需要为find
和grep
输出file
命令。
实现这一目标的最佳方法是什么?总结一下我的问题,我想要这样的事情:
for path in $(cat path.txt)
do
for line in $(find $path -type f);
do
#Use file command to test all the files, and do some stuff
#Use grep to find some tokens in all the files, and do some stuff
done
done
我不知道我的解释是否清楚,我尽力了。
编辑:我读过,执行for
循环读取文件很糟糕,但有些人声称执行while read
循环也很糟糕。说实话,我有点失落,我无法找到正确的方法来做我的事情。
答案 0 :(得分:1)
你这样做的方式很好,但这是另一种方法。使用此方法,您不必添加其他循环来迭代配置文件中的每个项目。有一些方法可以进一步简化这一点,但它不具备可读性。
测试一下: 在" $ {DIR} / path"我列出了两个目录(每行一个)。两个目录都包含在与此脚本相同的父目录中。在" $ {DIR} /令牌"文件,我有三个令牌(每行一个)来搜索。
#!/usr/bin/env bash
#
# Directory where this script is located
#
DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
#
# Loop through each file contained in our path list
#
for f in $(find $(cat "${DIR}/path") -type f); do
for c in $(cat "${f}" | grep "$(cat ${DIR}/token)"); do
echo "${f}"
echo "${c}"
# Do your file command here
done
done
答案 1 :(得分:0)
我认为你需要这样的东西:
find $(cat places.txt) -type f -exec bash -c 'file "$1" | grep -q compressed && echo $1 looks compressed' _ {} \;
示例输出
/Users/mark/tmp/a.tgz looks compressed
此脚本查找places.txt
中列出的所有位置,并为找到的每个文件运行新的bash
shell。在bash
shell内部,它正在测试文件是否被压缩并回显消息(如果是的话) - 我猜你会做其他事情,但你不说什么。
如果你还有很多工作要做,那就更详细地写下另一种写作方式:
#!/bin/bash
while read -r d; do
find "$d" -type f -exec bash -c '
file "$1" | grep -q "compressed"
if [ $? -eq 0 ]; then
echo "$1" is compressed
else
echo "$1" is not compressed
fi' _ {} \;
done < <(cat places.txt)