2

ソフトウェアリリースバージョンであるディレクトリのリストが与えられた場合、ls -l人間が好む形式に分類する方法は? 例えば:

$ ls -loghF
合計 209
drwxr-xr-x 2 3 6 月 18 日 11:33 12.0.40.0/
drwxr-xr-x 2 3 8 月 24 日 14:45 13.0.11.10/
drwxr-xr-x 2 3 7 月 13 日 14:12 13.0.11.4/
drwxr-xr-x 2 3 7 月 26 日 15:30 13.0.11.5/
drwxr-xr-x 2 4 7 月 27 日 11:33 13.0.11.6/
drwxr-xr-x 2 3 8 月 3 日 11:41 13.0.11.7/
drwxr-xr-x 2 3 8 月 10 日 11:53 13.0.11.8/
drwxr-xr-x 2 3 8 月 17 日 17:00 13.0.11.9/
drwxr-xr-x 2 3 8 月 3 日 14:37 13.0.17.0/
drwxr-xr-x 2 3 8 月 13 日 11:50 13.0.18.0/
drwxr-xr-x 2 3 8 月 17 日 11:21 13.0.19.0/
drwxr-xr-x 2 3 7 月 28 日 15:00 13.0.9.1/

望ましい結果は次のとおりです。

$ ls -loghF | 選別 ...
合計 209
drwxr-xr-x 2 3 6 月 18 日 11:33 12.0.40.0/
drwxr-xr-x 2 3 7 月 28 日 15:00 13.0.9.1/
drwxr-xr-x 2 3 7 月 13 日 14:12 13.0.11.4/
drwxr-xr-x 2 3 7 月 26 日 15:30 13.0.11.5/
drwxr-xr-x 2 4 7 月 27 日 11:33 13.0.11.6/
drwxr-xr-x 2 3 8 月 3 日 11:41 13.0.11.7/
drwxr-xr-x 2 3 8 月 10 日 11:53 13.0.11.8/
drwxr-xr-x 2 3 8 月 17 日 17:00 13.0.11.9/
drwxr-xr-x 2 3 8 月 24 日 14:45 13.0.11.10/
drwxr-xr-x 2 3 8 月 3 日 14:37 13.0.17.0/
drwxr-xr-x 2 3 8 月 13 日 11:50 13.0.18.0/
drwxr-xr-x 2 3 8 月 17 日 11:21 13.0.19.0/

並べ替えでは、各行の日付部分をスキップしてから、「.」を使用して数値順に並べ替える必要があります (たとえば、12 または 13 から開始)。フィールド区切りとして。

私は2つのアプローチを考えましたが、サポートされている場合、 sort -k 構文に問題があります:

(1) 最初の 36 文字をスキップし、次に「.」を使用します。フィールド区切りとして、次の 4 つのフィールドで数値順に並べ替えます。

(2) フィールド セパレータを空白として、7 番目のフィールドにスキップし、フィールド セパレータを「.」に変更します。次の 4 つのフィールドで数値順に並べ替えます。

代替手段は小さな Perl スクリプトですが、Unix はこの「単純な」タスクを実行できないのでしょうか?

4

3 に答える 3

2

awkバージョン番号を最初に配置し、4 つの数字キーを使用してソートしcut、前にある一時的なものを取り除くために使用するコマンド ラインを次に示します。

$ ls -loghF | awk '{ print $7, $0; }' | sort -n -t. -k1,1 -k2,2 -k3,3 -k4,4 | cut -d' ' -f2-
drwxr-xr-x   2       3 Jun 18 11:33 12.0.40.0/
drwxr-xr-x   2       3 Jul 28 15:00 13.0.9.1/
drwxr-xr-x   2       3 Jul 13 14:12 13.0.11.4/
drwxr-xr-x   2       3 Jul 26 15:30 13.0.11.5/
drwxr-xr-x   2       4 Jul 27 11:33 13.0.11.6/
drwxr-xr-x   2       3 Aug  3 11:41 13.0.11.7/
drwxr-xr-x   2       3 Aug 10 11:53 13.0.11.8/
drwxr-xr-x   2       3 Aug 17 17:00 13.0.11.9/
drwxr-xr-x   2       3 Aug 24 14:45 13.0.11.10/
drwxr-xr-x   2       3 Aug  3 14:37 13.0.17.0/
drwxr-xr-x   2       3 Aug 13 11:50 13.0.18.0/
drwxr-xr-x   2       3 Aug 17 11:21 13.0.19.0/

そこにあるソートコマンドは、この回答から借用されています。sort -V別の答えは(バージョンの並べ替え)を示唆していますが、私のバージョンにsortはそれがありません(ただし、あなたのバージョンにはあるかもしれないので、試してみる価値があります)。バージョンの並べ替えは、新しい GNU coreutils に固有のものである可能性があります (私の Linux ボックスにはそれがあり、並べ替えは GNU Coreutils 8.5 のものです)。

バージョンソートあり:

$ ls -loghF | sort -k7,7V
drwxr-xr-x   2       3 Jun 18 11:33 12.0.40.0/
drwxr-xr-x   2       3 Jul 28 15:00 13.0.9.1/
drwxr-xr-x   2       3 Jul 13 14:12 13.0.11.4/
drwxr-xr-x   2       3 Jul 26 15:30 13.0.11.5/
drwxr-xr-x   2       4 Jul 27 11:33 13.0.11.6/
drwxr-xr-x   2       3 Aug  3 11:41 13.0.11.7/
drwxr-xr-x   2       3 Aug 10 11:53 13.0.11.8/
drwxr-xr-x   2       3 Aug 17 17:00 13.0.11.9/
drwxr-xr-x   2       3 Aug 24 14:45 13.0.11.10/
drwxr-xr-x   2       3 Aug  3 14:37 13.0.17.0/
drwxr-xr-x   2       3 Aug 13 11:50 13.0.18.0/
drwxr-xr-x   2       3 Aug 17 11:21 13.0.19.0/
于 2012-08-27T05:17:04.167 に答える
1

参考:これが私がやったことです。
特別な感謝: http://www.sysarch.com/Perl/sort_paper.html

$ ls -loghF | perl -e '
use strict;
my @in = <>;
my @out = grep(m|\d+\.\d+\.\d+\.\d+/$|, @in);
print sort {
    my @aa = $a =~
            m|(\d+)\.(\d+)\.(\d+)\.(\d+)/$|;
    my @bb = $b =~
            m|(\d+)\.(\d+)\.(\d+)\.(\d+)/$|;
    $aa[0] <=> $bb[0] or
    $aa[1] <=> $bb[1] or
    $aa[2] <=> $bb[2] or
    $aa[3] <=> $bb[3]
    } @out;
'
drwxr-xr-x 2 3 6 月 18 日 11:33 12.0.40.0/
drwxr-xr-x 2 3 7 月 28 日 15:00 13.0.9.1/
drwxr-xr-x 2 3 7 月 13 日 14:12 13.0.11.4/
drwxr-xr-x 2 3 7 月 26 日 15:30 13.0.11.5/
drwxr-xr-x 2 4 7 月 27 日 11:33 13.0.11.6/
drwxr-xr-x 2 3 8 月 3 日 11:41 13.0.11.7/
drwxr-xr-x 2 3 8 月 10 日 11:53 13.0.11.8/
drwxr-xr-x 2 3 8 月 17 日 17:00 13.0.11.9/
drwxr-xr-x 2 3 8 月 24 日 14:45 13.0.11.10/
drwxr-xr-x 2 3 8 月 29 日 17:31 13.0.11.11/
drwxr-xr-x 2 3 8 月 3 日 14:37 13.0.17.0/
drwxr-xr-x 2 3 8 月 13 日 11:50 13.0.18.0/
drwxr-xr-x 2 3 8 月 17 日 11:21 13.0.19.0/
于 2012-08-31T04:29:00.390 に答える
1

これは最速の方法ではありませんが、説明するのはかなり簡単です。

ls -loghF |
awk '{ print $7 " " $0 }' |
sort -t. -k 1,1n -k 2,2n -k3,3n -k 4,4n |
sed 's/^[^ ]* //'

「awk」コマンドは、ディレクトリ フィールドを行の先頭にコピーします。sort コマンドは単一の区切り記号のみを使用し ( .; 行の異なる部分に異なる区切り記号を使用できるとは思わない)、4 つの数値部分を数値順に明示的に並べ替えます。次に、sed前に追加されたフィールドを削除します。

これは、「sortキーを簡単に見つけられるようにする」の単純なバージョンです。入力の分割は の高価な操作の 1 つだからですsort

于 2012-08-27T05:19:58.343 に答える