Perlでファイルサイズを取得する方法を教えてください。


Windows上でPerlスクリプトを実行しています。
ファイルのサイズを取得するのに
$fsize = -s $filename;
としてファイルサイズを取得していますが、これではファイルのプロパティの「サイズ」項しか分かりません。

「ディスク上のサイズ」を取得したいのですが、その方法を教えてください。

回答の条件
  • 1人2回まで
  • 登録:2008/07/30 11:32:45
  • 終了:2008/07/31 09:53:22

ベストアンサー

id:MAS3 No.3

MAS3回答回数40ベストアンサー獲得回数22008/07/30 21:44:22

ポイント200pt

クラスタサイズから逆算すれば取れると思います。

use strict;
use warnings;

my $filename = 'test.txt';
my $filesize = -s $filename;

print $filesize, "\n";
print get_disk_filesize($filesize), "\n";

sub get_disk_filesize {
    my $size = shift;
    my $cluster_size = 4096; # クラスタサイズ
  
    my $disk_filesize = (int(($size-1) / $cluster_size) + 1) * $cluster_size;
    return $disk_filesize;
}

クラスタサイズの取り方が分からなかったので4,096バイト固定にしています。

何らかの手段でクラスタサイズをちゃんと取得するか、1バイトのファイルを

作ってサイズを確認するというのが確実だと思います。

参考

FAT および NTFS のデフォルトのクラスタ サイズ

http://support.microsoft.com/default.aspx?scid=kb%3bja%3b140365

id:harrypotter

回答ありがとうございます。

明日試してみます。

ちなみにストレージはDataONTAPでCIFSを使っています。

  • 追記----------------

完璧です。

ありがとうございます。

2008/07/31 09:51:59

その他の回答(2件)

id:rubikitch No.1

るびきち回答回数120ベストアンサー獲得回数222008/07/30 11:55:34

ポイント10pt

ブロックサイズじゃだめですか?

@a = stat "/r/.skk-jisyo";
$blocks = $a[12];
print "blocks=$blocks\n";

http://www.ksknet.net/perl/stat_1.html

id:harrypotter

回答ありがとうございます。

残念ながらWindowsではブロック数もブロックサイズも取得できません。

2008/07/30 12:14:16
id:kn1967 No.2

kn1967回答回数2915ベストアンサー獲得回数3012008/07/30 12:43:14

ポイント15pt
$filename = 'a.txt';
open(IN, "dir /v $filename |");
while (<IN>) {
    if(/.+\s+.+\s+\d+\s+([0-9,]+).+$filename/){
      print $1;
    }
}
close(IN);

エラートラップなどは適宜仕込んでください。

id:harrypotter

回答ありがとうございます。

/vのオプションが無効なスイッチとしてエラーになるのですが、何のオプションでしょうか?

2008/07/30 13:01:44
id:MAS3 No.3

MAS3回答回数40ベストアンサー獲得回数22008/07/30 21:44:22ここでベストアンサー

ポイント200pt

クラスタサイズから逆算すれば取れると思います。

use strict;
use warnings;

my $filename = 'test.txt';
my $filesize = -s $filename;

print $filesize, "\n";
print get_disk_filesize($filesize), "\n";

sub get_disk_filesize {
    my $size = shift;
    my $cluster_size = 4096; # クラスタサイズ
  
    my $disk_filesize = (int(($size-1) / $cluster_size) + 1) * $cluster_size;
    return $disk_filesize;
}

クラスタサイズの取り方が分からなかったので4,096バイト固定にしています。

何らかの手段でクラスタサイズをちゃんと取得するか、1バイトのファイルを

作ってサイズを確認するというのが確実だと思います。

参考

FAT および NTFS のデフォルトのクラスタ サイズ

http://support.microsoft.com/default.aspx?scid=kb%3bja%3b140365

id:harrypotter

回答ありがとうございます。

明日試してみます。

ちなみにストレージはDataONTAPでCIFSを使っています。

  • 追記----------------

完璧です。

ありがとうございます。

2008/07/31 09:51:59
  • id:rubikitch
    あ、ブロックサイズじゃなくて、ブロック数です(^^;
  • id:kn1967
    Windows版では
      11 最適ブロックサイズ
      12 ファイルに割当てられているブロック数
    いずれの値も取得できませんけど・・・。

    代案として
    DOSコマンドのdir /vを使ってはどうかと検討中なんだけど
    スマートじゃないよね。
  • id:kn1967
    スマートじゃないけどサンプルあげさせていただきました。
  • id:kn1967
    /v は詳細表示させるためのオプションです。
    コマンドプロンプトで
     dir
     dir /v
    それぞれの出力結果を比べてみてください。

    無効なオプションと出てきたとなると
    "dir /v $filename |"
    の展開に失敗したのだと思いますが
    $filenameの中に/が入っているとかではありませんか?
  • id:harrypotter
    すいません、回答欄にも書いた通り、無効なオプションとしてエラーになります。
    ---
    コマンドプロンプト > dir /v
    無効なスイッチです - "v"
    ---
    OSはXP SP2です。
  • id:kn1967
    済みません。MEで動作確認してました。
    XPであれば /n オプションが相当すると思うのですが現在確認の術がありません。
    申し訳ありませんが /nオプションで
    ”割り当てサイズ(ディスク上のサイズ)”が出てくるか確認願えますでしょうか。

    配置も異なってくる事でしょうから、それに伴い
    /.+\s+.+\s+\d+\s+([0-9,]+).+$filename/
    も改造が必要になってきます。ご迷惑おかけして申し訳ないです。


  • id:Mook
    XP での DIR のヘルプですが、該当する項目がなさそうです。
    -----------------------------------------------------------------------------------------
    DIR [ドライブ:][パス][ファイル名] [/A[[:]属性]] [/B] [/C] [/D] [/L] [/N]
    [/O[[:]ソート順]] [/P] [/Q] [/S] [/T[[:]タイムフィールド]] [/W] [/X] [/4

    [ドライブ:][パス][ファイル名]
    一覧表示するドライブ、ディレクトリ、またはファイルを指定しま

    /A 指定された属性のファイルを表示します。
    属性 D ディレクトリ R 読み取り専用
    H 隠しファイル A アーカイブ
    S システム ファイル - その属性以外
    /B ファイル名のみを表示します (見出しや要約が付きません)。
    /C ファイル サイズを桁区切り表示します。これは
    既定の設定です。/-C とすると桁区切り表示されません。
    /D /W と同じですが、ファイルを列で並べ替えた一覧を表示します。
    /L 小文字で表示します。
    /N ファイル名を右端に表示する一覧形式を使用します。
    /O ファイルを並べ替えて表示します。
    ソート順 N 名前順 (アルファベット) S サイズ順 (小さいほうから)
    E 拡張子順 (アルファベット) D 日時順 (古いほうから)
    G グループ (ディレクトリから) - 降順
    /P 1 画面ごとに停止して表示します。
    /Q ファイルの所有者を表示します。
    /S 指定されたディレクトリおよびそのサブディレクトリのすべての
    ファイルを表示します。
    /T どのタイムフィールドを表示するか、または並べ替えに使用するか
    指定します。
    タイムフィールド C 作成
    A 最終アクセス
    W 最終更新
    /W ワイド一覧形式で表示します。
    /X このオプションは MS-DOS 形式以外のファイル名に対する短い名前
    表示します。長い名前の前に短い名前を表示する点を除けば、
    /N オプションと同じです。短い名前がない場合は、ブランクに
    なります。
    /4 4 つの数字で年を表示します。

    環境変数 DIRCMD にスイッチを設定できます。
    /-W のように - (ハイフン) を前につけると、そのスイッチは無効になります。
    -----------------------------------------------------------------------------------------
    NTFS になって対応から外れたのでしょうか。

この質問への反応(ブックマークコメント)

トラックバック

「あの人に答えてほしい」「この質問はあの人が答えられそう」というときに、回答リクエストを送ってみてましょう。

これ以上回答リクエストを送信することはできません。制限について

絞り込み :
はてなココの「ともだち」を表示します。
回答リクエストを送信したユーザーはいません