App-diroctopus

 view release on metacpan or  search on metacpan

diroctopus  view on Meta::CPAN

  given ( $o{d} ) { 
    push @ret , join "+" , $ddirs , scalar @files - $ddirs  when /d/i && /f/i ;
    push @ret , $ddirs when /d/i ;
    push @ret , scalar @files - $ddirs when /f/i ;
  }
  push @ret , sum0 map { -s "$dirname$I$_" } @files  if $o{d} =~ m/s/i ;

	return join ":" , @ret ; #, sum0 map { -s "$_[0]$I$_" } @files ;
}

# ディリクトリ名の連結したパス名から、それぞれのディレクトリに、付属するディレクトリの数を数える
sub path2dnum ( $ $ ) { 
  my @f = splitdir $_[0] ;
  my $tdir = "." ;
  if ( exists $o{d} ) { 
   for ( @f ) { 
  	$tdir .= $I . $_ ;
  	my $dnum = dirfinum ( $tdir ) ;
  	$_ .= FAINT "($dnum)" ;
   }
  }
  #* YELLOW = sub { BRIGHT_YELLOW @_ } ;
  $f[ - $_[1] ] = YELLOW $f[ - $_[1] ] if  $o{y} eq '1' ;
  grep { $f[ $_ ] = YELLOW $f[ $_ ] } -$_[1] .. -1 if  $o{y} eq '2' ;  
  join $I , @f ;
}

sub main () {

  # ヘッダの出力
  my @header ; 
  push @header , "Distance" ;
  push @header , "Directory_path" ; 
  push @header , "File_number" , "File_bytesize_sum" if ! exists $o{d} ;
  say UNDERLINE join "\t" , @header ;

  $root -> build_recursive ( "." , 0 ) ; #  第二引数 my $depth = 0 ;
  $root -> shrink_recursive if $o{S} ;
  my $first ; # 最初のディレクトリに相当するインスタンス 
  my $furthest ; # 最も離れたインスタンス
  my $distance ;  # その最も離れた距離を格納
  my $path  ; # ディレクトリ名のパス

  $first = $root -> {children}[0];
  
  for ( 1 .. $o{g} ) { 
    $furthest = $first -> scan ;
    $distance = $furthest -> {farness} ;
    $path = $furthest -> pathProc ;
    my $steps = splitdir $path ;
    last if $distance < $o{l} ;
    my @lf = leafs $path if ! exists $o{d} ;
    #say CYAN "$furthest->{name}, $distance, $path" ; 
    my $decopath = path2dnum ( $path , $distance ) ;#if defined $o{d} ; #&& $o{d} == 1 ;
    do { say join "\t" , (int $distance).(FAINT "/".$steps ) ,  $decopath.$I, @lf ; $OutRec ++ } 
  }
  
  # メインの後の出力
  * REVERSE = sub { @_ } ;
  print STDERR " -- " ;
  print STDERR BOLD " NO OUTPUT RECORD ! -- " if $OutRec == 0 ;
  print STDERR REVERSE ITALIC " Output records: " , CLEAR " $OutRec " ; 
  print STDERR " " , REVERSE ITALIC " Used random seed: " , CLEAR " $o{s} " ;
  say STDERR " " , REVERSE ITALIC " Process time: " , CLEAR " " , ( tv_interval $time_start , [ gettimeofday ] ) , " second(s)." ;
}

## ヘルプの扱い
sub VERSION_MESSAGE {}
sub HELP_MESSAGE {
    use FindBin qw[ $Script ] ; 
    $ARGV[1] //= '' ;
    open my $FH , '<' , $0 ;
    while(<$FH>){
        s/\$0/$Script/g ;
        print $_ if s/^=head1// .. s/^=cut// and $ARGV[1] =~ /^o(p(t(i(o(ns?)?)?)?)?)?$/i ? m/^\s+\-/ : 1;
    }
    close $FH ;
    exit 0 ;
}

=encoding utf8
=head1
 $0 [dirname]
   
 主要な機能:   
  その下の階層たちに多数のファイルを持つディレクトリに対して、その構造を把握するためにつかう。
  与えられたディレトリの下のディレクトリ全てに対して、それらを木構造と見なす。最初に与えた
  ディリクトリはその木構造のルート(根)と見なす。探索したディレクトリをその木構造のノード(頂点)と見なす。
  そして、下記の計算を反復する。
    1. 最も深い(最も下にある)ディレクトリを最初に探し出す。
    2. それに対応する頂点から根までの経路から、最も遠い頂点に相当するディレクトリを探し出す。
    3. 既に探し出した全てのそれぞれの頂点から根までの経路から、同様に最も遠いものを探し出す。
    4. 反復的に3.を必要な回数に達するまで繰り返す。
 補足: 探し出す頂点は、多数ある中から1つを選ぶが、等確率にランダムに選ぶ。
 オプション: 
    -. 0 : ピリオドでファイル名が始まる隠しファイルは探索しない。
    -g N : 最大限N個を探し出すこととする。
    -l N : 探索を続ける際に、遠さの最小限を設定する。
    -s N : 乱数シードをNに設定する。
    -d str : strの値により、出力するパスに現れる各ディレクトリに次の補助情報を括弧内に追加。
     -d d : その下のディレクトリの個数を出力。
     -d f : その下のディレクトリ以外のファイルの個数を出力。
     -d s : その下のディレクトリにあるファイルのバイトサイズの合計を出力。
     -d D : その上のディレクトリの直下にあるディレクトリの個数を出力。(兄弟ディレクトリに相当)
     -d F : その上のディレクトリの直下にある、ディレクトリ以外のファイルの個数を出力。
    -y N : Nの値により,出力するパスの部分的な強調のさせ方に関して下記の異なる動作をする。
     -y 0 : 着色をしない。
     -y 1 : 分岐の発生したディレクトリの1箇所のみを明るい色で強調する。(初期設定)
     -y 2 : 分岐の発生したディレクトリ箇所から下も全て明るい色で強調する。
    -x DIRNAME ; ディレクトリ名をオプション上で指定する
    -L シンボリックリンクに関する処理 (辿るようにする)
 開発上のメモ
    * 初期化時に、blessの前に、$x->{name}がうまくいかなかった。
    * $first を $root から分ける必要があったのか
    * given を使ったこと
    * 具体的なファイル名 -f で。
    *  (乱数の利用の最適か -- 比較せよ MSソフトで)
    *  ( 最遠距離の等しいものが多数あるばあいに、出力優先順位を考えた方が良さそう。)
    *  (ランダムになってない!?)
    * -h Nを実装したい。
    * -S で 直下にファイルがたった1個のディレクトリしかない場合に、縮めることをしようとしたが、厄介。



( run in 0.694 second using v1.01-cache-2.11-cpan-13bb782fe5a )