명령줄을 사용하여 여러 파일의 이름을 바꾸는 방법에 대해 많은 질문을 발견했습니다. 하지만 이 파일 이름을 바꾸는 특정 문제는 해결할 수 없습니다.
something_4M_something_something_manyothersomethings.csv
다음을 입력하세요:
something_4_M_something_something_manyothersomethings.csv
나에게 필요한 것은 필드를 분할하는 것이지만 4M
그렇게 4_M
할 수는 없습니다(참고: 각무엇밑줄로 구분하면 작업에 중요하지 않은 다른 필드가 많이 있습니다.
내가 한 일은 다음과 같지만 예상대로 작동하지 않습니다. 정규 표현식에 문제가 있는 것 같지만 더 나은 방법을 찾을 수 없습니다.
rename -n 's/.4M/$&_4_M/' *
또한 이와 유사한 질문 중 하나의 댓글에서 비슷한 내용을 찾았지만 더 이상 찾을 수 없기 때문에 제가 작성한 내용이 정확히 어떻게 작동하는지 전혀 모릅니다.
답변1
정말로 원하는 것이 4M
로 바꾸는 것이라면 4_M
정규 표현식의 변형으로 다음을 수행할 수 있습니다.
$ ls
something_4M_something_something_manyothersomethings.csv
$ rename -n 's/4M/4_M/' *
'something_4M_something_something_manyothersomethings.csv' would be renamed to 'something_4_M_something_something_manyothersomethings.csv'
정규 표현식은 무엇이든 작동합니다.~에이름이므로 선행 "무언가"를 유지하기 위해 특정한 작업을 수행할 필요가 없습니다.
4M
첫 번째 "무언가"를 두 번째 "무언가"로 이동하거나 밑줄 다음의 첫 번째 항목 으로 제한하는 등 다른 작업을 수행하려면 질문을 편집하고 명확히 하십시오.
주석에서 볼 수 있듯이 -n
연습 실행이 수행되어 무슨 일이 일어나는지 보여주고 실제로 작업을 수행하지는 않습니다.
질문의 예는 이미 사용되었으므로 -n
질문자가 이것을 이해할 수 있다고 가정합니다.
답변2
Raku(이전 Perl_6) 사용
단일 파일의 경우:
~$ raku -e ' \
my $name = dir(test => /^ something_4M_somethingelse \. csv $/)[0]; \
my $modname = S/^ something_<(4M)>_somethingelse \. csv $/4_M/.IO given $name; \
($name,$modname).say; \
#rename($name,$modname, createonly => True);'
여러 파일의 경우:
~$ raku -e ' \
my @names = dir(test => /^ something_<digit><upper>_somethingelse \. csv $/); \
my @modnames = do for @names {S/^ something_<(<digit><upper>)>_somethingelse \. csv $/$<digit>_$<upper>/.IO given $_;}; \
for [Z] @names,@modnames -> ($x,$y) { ($x,$y).say }; \
#for [Z] @names,@modnames -> ($x,$y) { rename($x,$y, createonly => True) };'
디렉토리 입력:
~$ ls
something_4M_somethingelse.csv something_5N_somethingelse.csv something_6O_somethingelse.csv
디렉터리 출력(여러 파일 이름 바꾸기):
~$ ls
something_4_M_somethingelse.csv something_5_N_somethingelse.csv something_6_O_somethingelse.csv
경고하다:먼저 백업하세요! !
간략한 설명(단일 파일 이름 바꾸기): dir()
정규식 일치("부사") 옵션을 사용하여 관심 있는 파일 목록을 얻고 test => / ... /
하나의 요소(무엇이든 [0]
)만 가져와서 스칼라 변수에 저장합니다 $name
. 변수를 확인하면 해당 변수가 개체임을 알 수 있습니다 .IO
.
익숙한 관용구를 사용하여 변수를 S///
수정 given $name
하고 수정된 이름을 로 저장합니다 $modname
. 여기서는 S///
문자열화된 so .IO
메소드 호출이 추가되어 S///
that 도 $modname
객체 가 됩니다 .IO
.
정규식에서는 익숙하지 않은 기호가 <(…)>
표현일 수 있습니다. 하지만 그건 라쿠의 것일 뿐이야캡쳐마크이므로 의 왼쪽 절반에 있는 전체 일치 항목이 S///
인식되는 반면 의 오른쪽 절반에서는 4M
그 안에 있는 일치 항목 만 캡처되고 수정됩니다 .<(…)>
S///
.IO
필요한 시작/끝 개체를 얻은 경우 이 줄은 ($name,$modname).say;
다음과 유사한 출력을 생성해야 합니다.
("something_4M_somethingelse.csv".IO "something_4_M_somethingelse.csv".IO)
모든 것이 괜찮아 보이면 Raku 코드의 마지막 rename()
줄의 주석 처리를 제거하여 실제로 마지막에서 두 번째 줄에 나열된 파일 이름을 .say
.
참고: 위 코드 createonly => True
에 부사/옵션을 포함하면 기존 파일 이름이 삭제되지 않는다는 rename()
의미입니다 rename()
(짧은 형식이라도 :createonly
동일한 효과가 있음). 기본값( 예: 파괴)을 가져오고 기존 파일/파일 이름의 이름 바꾸기(덮어쓰기)를 허용 하려면 부사/옵션을 제거 createonly => True
하거나 제거하세요 .:createonly
False
https://docs.raku.org/syntax/S$SOLIDUS$SOLIDUS$SOLIDUS
https://docs.raku.org/routine/rename
https://raku.org