sed를 사용하여 시작 부분을 모두 일치하는 수의 대체 문자열로 바꿉니다.

sed를 사용하여 시작 부분을 모두 일치하는 수의 대체 문자열로 바꿉니다.

각 줄의 선행 상자 그리기 문자와 공백이 일치하는 수의 공백으로 대체되는 방식으로 $tree --noreport$의 출력을 조작하고 싶습니다. 이 문자와 일치하는 패턴을 작성한다면 sed가 유니코드 이스케이프 시퀀스를 인식하지 못하기 때문에 ^\\(\u2500\\|\u2514\\|\u251C\\| \\)*\u2500문자열이 래핑됩니다 . $'...'이 패턴은 tree --noreport첫 번째 줄을 제외한 모든 출력 줄에 나타납니다. 일치하는 모든 문자열의 모든 문자를 공백으로 바꿔야 합니다.

입력 예:

.
├── docs
│   ├── jokes
│   │   └── knock_knock.txt
│   └── work
├── images
└── .profile

출력 예:

.
    docs
        jokes
            knock_knock.txt
        work
    images
    .profile

이제 내 목적을 위해 파일 또는 폴더 이름이 시작되는 위치를 명확하게 해야 한다는 것을 깨달았습니다(파일 또는 폴더 이름은 하나 이상의 공백으로 시작할 수 있음). 따라서 출력은 실제로 다음과 같아야 합니다.

.
    /docs
        /jokes/
            /knock_knock.txt
        /work
    /images
    /.profile

제가 제공한 패턴의 끝은 \u2500실제로 트리 형식과 파일/폴더 이름의 시작을 구별합니다.

답변1

다음과 같은 루프에서 한 번에 하나씩 교체할 수 있습니다.

tree --noreport | sed $'
  :1
    s/^\\( *\\)\\([\ua0\u2500\u2502\u2514\u251C]\\)\\([\ua0\u2500\u2502\u2514\u251C ]*\u2500 \\)/\\1 \\3/
  t1
  s|\u2500 |  /|'

(적어도 내 버전의 출력에는 \ua0(단순 공백이 아닌) 및 \u2502(귀하의 예에도 표시됨)이 누락되었습니다 .)tree

"─ "이름 앞에 이러한 문자가 포함된 파일이 있다면 속고 있는 것입니다.

또 다른 방법(실제로 삽입하고 싶고 /호출하는 디렉토리에 tree해당 항목이 없다고 가정): 첫 번째 항목 다음에 삽입한 "─ "다음 루프에서 첫 번째 문자 앞의 모든 문자를 공백으로 바꿉니다./"\u2500 "/

tree --noreport | sed '
  s|'$'\u2500'' |&/|;t1
  b
  :1
    s|^\( *\)[^ /]|\1 |
  t1'

다음 명령을 사용하는 것이 더 쉽습니다 perl.

tree --noreport | perl -C -pe 's{^.*?\x{2500} }{" " x length($&) . "/"}e'

답변2

bash다음은 최상위 디렉터리에 있는 이름을 반복적으로 출력하는 함수 입니다 .

mytree () (
    topdir="${1-.}"
    indent="${2-0}"

    shopt -s nullglob
    shopt -s dotglob

    # output directory name
    printf "%${indent}s'%s'/\n" "" "${topdir##*/}"

    indent=$(( indent + 4 ))

    for name in "$topdir"/*; do
        if [ -h "$name" ]; then
            # output symbolic link name and target
            printf "%${indent}s'%s' --> '%s'\n" "" "${name##*/}" "$( readlink -- "$name" )"
        elif [ -d "$name" ]; then
            # recurse into directories
            mytree "$name" "$indent"
        else
            # output other type of name (not directory or symbolic link)
            printf "%${indent}s'%s'\n" "" "${name##*/}"
        fi
    done
)

이 함수는 mytree처리할 최상위 디렉터리인 하나의 인수(두 번째 인수는 재귀 호출에만 사용됨)를 사용합니다. 인수가 제공되지 않으면 현재 디렉터리를 나열된 최상위 디렉터리로 사용합니다.

출력은 다음과 같습니다.

'Work'/
    'Data'/
        's3wes.all.tab.frq.counts'
        's3wes.con.tab.frq.counts'
        'sullivan.txt'
    'Development'/
        'ENA-submission'/
            '.git'/
                'COMMIT_EDITMSG'

등.

즉, 이름은 작은따옴표로 묶이고 디렉터리 뒤에는 이라는 이름이 붙습니다 /. 또한 기호 링크는 다음과 같이 표시됩니다.

'embl-validator.jar' --> 'embl-api-validator-1.1.158.jar'

세 가지 호출을 변경하면 출력 형식을 쉽게 변경할 수 있습니다 printf.

관련 정보