awk 명령을 사용하여 세 개의 열을 자르려고 합니다.
-rwxrwxr-x 1 rouser users 33 Oct 19 05:20 b.sh
다음 줄을 사용하여 19년 10월 33일 05:20 값을 잘라냅니다.
z=`ls -l b.sh | awk '{print $6,$7,$8 }'`
echo $z
z는 33 Oct 19 05:20 결과를 제공합니다.
내 문제는 2016년 19월 10일 날짜, 월, 연도를 이 형식으로 원한다는 것입니다.
어떻게 해야 합니까? ?
가능한 한 빨리 도와주세요.
답변1
출력 구문 분석에 대한 몇 가지 참고 사항 ls
:
- 형식은 로케일에 따라 다릅니다. 구문 분석이 필요한 경우 로케일을 알려진 것으로 수정해야 합니다. 일반적으로
C
- 출력 에서는
ls -l
사용자 이름과 그룹 이름이 날짜 앞에 나타나고 공백을 포함할 수 있으므로(실제로는 드물지만) 항상 6번째 필드에 있는 날짜에 의존할 수 없습니다.ls -n
대신 숫자 uids/gids를 사용하는 것이 더 좋습니다 (-o
또는-g
이를 포함하는 구현을 사용). - 파일 유형이 디렉토리인 경우
ls -l file
해당 내용이 나열됩니다. 이 옵션을 원합니다-d
(LC_ALL=C ls -nd -- "$file"
지금까지는). 파일 이름(또는 심볼릭 링크 유형 파일의 경우 심볼릭 링크 대상)에 개행 문자가 포함된 경우 출력의 첫 번째 줄만 고려되는지 확인해야 합니다.
LC_ALL=C ls -nd -- "$file" | awk '{print $6,$7,$8; exit}'
C 로케일에서는 파일이 지난 6개월 이내(또는 향후)에 마지막으로 수정되었는지 여부에 따라 수정 시간 형식이 달라집니다. 따라서 2016-11-09에 실행 중인 경우
Jun 14 09:18
또는Feb 4 2014
를 얻을 수 있습니다 .Jan 1 2017
연도가 지정되지 않으면 현재 연도라고 가정할 수 없습니다. 예를 들어 1월에 실행하여 하나를 얻으면Dec 24 23:59
작년 12월이 됩니다.
여전히 다음과 같이 해결할 수 있습니다.
LC_ALL=C ls -dn -- "$file" | awk -v now="$(date +%m:%Y)" '{
m=$6; d=$7; y=$8
m = index("--JanFebMarAprMayJunJulAugSepOctNov", m) / 3
if (y ~ /:/) {
split(now, a, ":")
y = a[2]
if (m > a[1]) y--
}
printf "%02d/%02d/%04d\n", d, m, y
exit}'
하지만 처음부터 올바른 형식으로 시간을 가져오는 것이 좋습니다. Pass 를 사용 하면 내장된 기능을 zsh
사용할 수 있습니다 .stat
zmodload zsh/stat
stat -LF %d/%m/%Y +mtime -- $file
GNU 시스템에서는 다음을 수행할 수 있습니다.
date -r "$file" +%d/%m/%Y
(심볼릭 링크의 경우 대상의 수정 시간을 제공하지만)
또는:
find -- "$file" -prune -printf '%Td/%Tm/%TY\n'
BSD에서:
stat -t %d/%m/%Y -f %Sm -- "$file"
또는 perl
이식성을 위해:
perl -MPOSIX -le '@s = lstat shift or die "lstat: $!";
print strftime "%d/%m/%Y", localtime $s[9]' -- "$file"
답변2
를 사용하려면 ls
다음과 같이 하세요. ls -l --time-style=+%d/%m/%Y