이 예에 표시된 것과 같이 기본 이름이 동일하고 확장자가 다르며 디렉터리가 여러 개 있는 파일이 여러 개 있습니다.
FileA.txt
FileA.html
FileA.directory/
FileB.txt
FileB.html
FileB.directory/
FileC.txt
FileC.html
FileC.directory/
기본 이름을 기반으로 모든 파일을 해당 디렉터리로 이동할 수 있는 for 루프를 만들고 싶습니다. 결과는 다음과 같습니다
FileA.directory/FileA.txt
FileA.directory/FileA.html
FileB.directory/FileB.txt
FileB.directory/FileB.html
FileC.directory/FileC.txt
FileC.directory/FileC.html
이 페이지에서 이 예제와 같이 내 문제와 유사한 몇 가지 제안을 찾으려고 노력했습니다. 하지만 정확히 비슷한 질문을 찾을 수 없습니다.
for dir in .*/
do
for f in "$dir"*
do
base=${f#$dir}
mv "$base.*" "$dir"
done
done
그러나 나는 그것을 작동시킬 수 없습니다.
답변1
파일과 디렉터리의 이름은 점이 뒤따르는 공통 그룹화 접두사를 공유하므로 동일한 명명 규칙을 따르고 파일이나 디렉터리의 파일 이름 접미사를 모른다고 가정합니다.
topdir=.
for dirname in "$topdir"/*/; do
prefix=$( basename "$dirname" ) # $topdir/FileC.directory/ --> FileC.directory
prefix=${prefix%%.*} # FileC.directory --> FileC
for filename in "$topdir/$prefix".*; do
if [ ! -d "$filename" ]; then
mv -i "$filename" "$dirname"
fi
done
done
외부 루프는 디렉터리의 모든 디렉터리를 반복합니다 $topdir
(여기서는 .
현재 디렉터리로 설정됨). 이는 $prefix
디렉터리 이름의 기본 이름이 되며 첫 번째 점 뒤의 비트가 제거됩니다.
접두사가 계산되면 $topdir
동일한 접두사를 공유하는 동일한 디렉터리의 디렉터리가 아닌 파일(파일)이 해당 디렉터리로 이동됩니다.
답변2
.html
모든 파일에 파일 이름 접미사가 있거나 .txt
모든 디렉터리에 접미사가 있다는 것을 알고 있다고 가정하면 .directory
다음을 사용할 수 있습니다.
for i in *.txt *.html
do
mv "$i" "${i%%.*}.directory/$i"
done
파일이 있는 동일한 디렉터리에서 이 명령을 실행합니다. 파일 이름에서 후행 .txt 및 .html을 제거한 다음 파일을 대상 디렉터리로 이동합니다.
답변3
dirs=$(ls | grep ".d")
for d in $dirs
do
filename=$(echo $d | awk -F"." '{print $1}')
ls | grep -P "$filename.(?!(d))" | xargs -I{} mv '{}' '$d'
done
너무 장황할 수도 있지만 작동합니다