sed를 사용하여 파일 이름 바꾸기
객관적인
다음 파일 이름을 변경하십시오.
- F00001-0708-RG-biasliuyda
- F00001-0708-CS-akgdlaul
- F00001-0708-VF- 히 울기 글
다음 파일 이름에 :
- F0001-0708-RG-biasliuyda
- F0001-0708-CS-akgdlaul
- F0001-0708-VF- 히 울기 글
쉘 코드
테스트하려면 :
ls F00001-0708-*|sed 's/\(.\).\(.*\)/mv & \1\2/'
수행하려면 :
ls F00001-0708-*|sed 's/\(.\).\(.*\)/mv & \1\2/' | sh
내 질문
sed 코드를 이해하지 못합니다. 대체 명령이 무엇인지 이해합니다.
$ sed 's/something/mv'
방법. 그리고 정규 표현식을 다소 이해합니다. 하지만 여기서 무슨 일이 일어나고 있는지 이해할 수 없습니다.
\(.\).\(.*\)
또는 여기 :
& \1\2/
전자는 나에게 "단일 문자, 뒤에 단일 문자, 단일 문자의 길이 시퀀스"를 의미하는 것처럼 보이지만 확실히 그 이상의 의미가 있습니다. 후반부까지 :
& \1\2/
나는 모른다. 이 코드를 정말 이해하고 싶습니다. 여기 좀 도와주세요.
첫째,이를 수행하는 가장 쉬운 방법은 prename 또는 rename 명령을 사용하는 것입니다.
Ubuntu, OSX (Homebrew 패키지 rename
, MacPorts 패키지 p5-file-rename
) 또는 perl 이름 변경 (사전 이름)이있는 기타 시스템 :
rename s/0000/000/ F0000*
또는 RHEL과 같이 util-linux-ng에서 이름을 바꾸는 시스템 :
rename 0000 000 F0000*
동등한 sed 명령보다 훨씬 이해하기 쉽습니다.
그러나 sed 명령을 이해하려면 sed 맨 페이지가 도움이됩니다. man sed를 실행하고 &를 검색하면 (/ 명령을 사용하여 검색) s / foo / bar / 대체에서 특수 문자임을 알 수 있습니다.
s/regexp/replacement/
Attempt to match regexp against the pattern space. If success‐
ful, replace that portion matched with replacement. The
replacement may contain the special character & to refer to that
portion of the pattern space which matched, and the special
escapes \1 through \9 to refer to the corresponding matching
sub-expressions in the regexp.
따라서에서 \(.\)
참조 할 수있는 첫 번째 문자와 일치합니다 \1
. 그런 .
다음 항상 0 인 다음 문자 \(.*\)
와 일치 합니다. 그런 다음에서 참조 할 수있는 나머지 파일 이름과 일치합니다 \2
.
대체 문자열은 &
(원래 파일 이름)을 사용하여 모든 것을 모아 \1\2
두 번째 문자 인 0을 제외한 파일 이름의 모든 부분입니다.
이것은 IMHO를 수행하는 꽤 비밀스러운 방법입니다. 어떤 이유로 rename 명령을 사용할 수없고 sed를 사용하여 이름을 변경하려는 경우 (또는 이름 바꾸기에 너무 복잡한 작업을 수행 했습니까?) 정규식에서 더 명시 적으로 지정하면 훨씬 더 읽기 쉽습니다. 아마도 다음과 같습니다.
ls F00001-0708-*|sed 's/F0000\(.*\)/mv & F000\1/' | sh
s / search / replacement /에서 실제로 변경되는 내용을 볼 수 있으면 훨씬 더 읽기 쉽습니다. 또한 실수로 두 번 또는 무언가를 실행하면 파일 이름에서 문자를 계속 빨아 들이지 않습니다.
sed 설명을 마쳤습니다. 이제 셸만 사용할 수 있으며 외부 명령이 필요하지 않습니다.
for file in F0000*
do
echo mv "$file" "${file/#F0000/F000}"
# ${file/#F0000/F000} means replace the pattern that starts at beginning of string
done
sed
몇 년 전에 일괄 이름 변경에 대한 예제가 포함 된 작은 게시물을 작성했습니다 .
http://www.guyrutenberg.com/2009/01/12/batch-renaming-using-sed/
예를 들면 :
for i in *; do
mv "$i" "`echo $i | sed "s/regex/replace_text/"`";
done
정규식에 그룹 (예 :)이 포함 \(subregex\
된 경우 대체 텍스트 \1\
에서 \2
등 으로 사용할 수 있습니다 .
가장 쉬운 방법은 다음과 같습니다.
for i in F00001*; do mv "$i" "${i/F00001/F0001}"; done
또는 이식 가능하게
for i in F00001*; do mv "$i" "F0001${i#F00001}"; done
이렇게 F00001
하면 파일 이름 의 접두사가 F0001
. mahesh에 대한 크레딧 : http://www.debian-administration.org/articles/150
sed
명령
s/\(.\).\(.*\)/mv & \1\2/
대체하는 의미 :
\(.\).\(.*\)
와:
mv & \1\2
일반 sed
명령 과 같습니다 . 그러나 괄호 &
와 \n
마커는 약간 변경됩니다.
The search string matches (and remembers as pattern 1) the single character at the start, followed by a single character, follwed by the rest of the string (remembered as pattern 2).
In the replacement string, you can refer to these matched patterns to use them as part of the replacement. You can also refer to the whole matched portion as &
.
So what that sed
command is doing is creating a mv
command based on the original file (for the source) and character 1 and 3 onwards, effectively removing character 2 (for the destination). It will give you a series of lines along the following format:
mv F00001-0708-RG-biasliuyda F0001-0708-RG-biasliuyda
mv abcdef acdef
and so on.
The backslash-paren stuff means, "while matching the pattern, hold on to the stuff that matches in here." Later, on the replacement text side, you can get those remembered fragments back with "\1" (first parenthesized block), "\2" (second block), and so on.
The parentheses capture particular strings for use by the backslashed numbers.
If all you're really doing is removing the second character, regardless of what it is, you can do this:
s/.//2
but your command is building a mv
command and piping it to the shell for execution.
This is no more readable than your version:
find -type f | sed -n 'h;s/.//4;x;s/^/mv /;G;s/\n/ /g;p' | sh
The fourth character is removed because find
is prepending each filename with "./".
ls F00001-0708-*|sed 's|^F0000\(.*\)|mv & F000\1|' | bash
Here's what I would do:
for file in *.[Jj][Pp][Gg] ;do
echo mv -vi \"$file\" `jhead $file|
grep Date|
cut -b 16-|
sed -e 's/:/-/g' -e 's/ /_/g' -e 's/$/.jpg/g'` ;
done
Then if that looks ok, add | sh
to the end. So:
for file in *.[Jj][Pp][Gg] ;do
echo mv -vi \"$file\" `jhead $file|
grep Date|
cut -b 16-|
sed -e 's/:/-/g' -e 's/ /_/g' -e 's/$/.jpg/g'` ;
done | sh
참고URL : https://stackoverflow.com/questions/2372719/using-sed-to-mass-rename-files
'development' 카테고리의 다른 글
패턴이나 모든 n 요소를 포함하지 않을 때 Python에서 문자열을 어떻게 안정적으로 분할합니까? (0) | 2020.10.20 |
---|---|
날짜가 주어진 범위에 있는지 확인하는 방법은 무엇입니까? (0) | 2020.10.20 |
Magento 제품은 카테고리에 표시되지 않습니다. (0) | 2020.10.20 |
이스케이프 된 유니 코드로 문자열을 어떻게 디코딩합니까? (0) | 2020.10.20 |
ASP.NET MVC Razor : HTML의 조건부 속성 (0) | 2020.10.20 |