ls 정렬이 영숫자가 아닌 문자를 무시하는 이유는 무엇입니까? 정렬 할

파일 이름을 정렬 할 때 ls와 같은 문자는 무시합니다 -,_. 나는 그것들을 정렬 할 때도 사용할 것으로 기대했다.

예를 들면 :

touch a1 a2 a-1 a-2 a_1 a_2 a.1 a.2 a,1 a,2

이제이 파일들을 ls -1다음 과 같이 표시하십시오 :

a1
a_1
a-1
a,1
a.1
a2
a_2
a-2
a,2
a.2

내가 기대 한 것은 다음과 같습니다.

a1
a2
a,1
a,2
a.1
a.2
a_1
a_2
a-1
a-2

즉, 정렬 할 때 영숫자가 아닌 문자가 고려 될 것으로 예상했습니다.

누구든지이 행동을 설명 할 수 있습니까? 이 행동은 표준에 의해 규정되어 있습니까? 아니면 인코딩이 UTF-8이기 때문입니까?

업데이트 : 이것은 UTF-8 정렬과 관련이있는 것 같습니다.

$ LC_COLLATE=C ls -1
a,1
a,2
a-1
a-2
a.1
a.2
a1
a2
a_1
a_2


답변

이것은 문자셋과 관련이 없습니다. 데이터 정렬 순서를 결정하는 언어입니다. libc는 $LC_COLLATE/ $LC_ALL/ 로 표시된 언어를 검사 $LANG하고 데이터 정렬 규칙 (예 : /usr/share/i18n/locales/*GLibC)을 조회하고 지시에 따라 텍스트를 정렬 합니다.


답변

편집 : LC_COLLATE = C로 정렬 된 데이터에 대한 테스트가 추가되었습니다.


기본 조합 순서는 이러한 “천공 유형”문자를 동일한 값 Use LC_COLLATE=C으로 처리하여 코드 포인트 순서로 처리하는 것입니다.

for i in 'a1' 'a_1' 'a-1' 'a,1' 'a.1' 'a2' 'a_2' 'a-2' 'a,2' 'a.2' ;do
  echo $i;
done |LC_COLLATE=C sort

산출

a,1
a,2
a-1
a-2
a.1
a.2
a1
a2
a_1
a_2

다음 코드는 모든 테스트 유효한 기본 언어 평면에서 UTF-8 문자를 (제외 \ x00에서\ X0A , 간략화를 위해)
이 무작위로 정렬하는 파일에 대해, 공지 된 (생성) 오름차순으로 파일을 비교 한 후 다시 정렬 LC_COLLATE = C. 결과는 C 시퀀스가 원래 생성 된 시퀀스와 동일 함을 보여줍니다 .

{ i=0 j=0 k=0 l=0
  for i in {0..9} {A..F} ;do
  for j in {0..9} {A..F} ;do
  for k in {0..9} {A..F} ;do
  for l in {0..9} {A..F} ;do
     (( 16#$i$j$k$l == 16#0000 )) && { printf '.' >&2; continue; }
     (( 16#$i$j$k$l == 16#000A )) && { printf '.' >&2; continue; }
     (( 16#$i$j$k$l >= 16#D800    &&
        16#$i$j$k$l <= 16#DFFF )) && { printf '.' >&2; continue; }
     (( 16#$i$j$k$l >= 16#FFFE )) && { printf '.' >&2; continue; }
     echo 0x"$i$j$k$l" |recode UTF-16BE/x4..UTF-8 || { echo "ERROR at codepoint $i$j$k$l " >&2; continue; }
     echo
  done
  done
  done; echo -n "$i$j$k$l " >&2
  done; echo >&2
} >listGen

             sort -R listGen    > listRandom
LC_COLLATE=C sort    listRandom > listCsort

diff <(cat listGen;   echo "last line of listOrig " ) \
     <(cat listCsort; echo "last line of listCsort" )
echo
cmp listGen listCsort; echo 'cmp $?='$?

산출:

63485c63485
< last line of listOrig
---
> last line of listCsort

cmp $?=0