Bashスクリプトで各ファイルのバイトサイズをどのように印刷しますか? [閉鎖]

Bashスクリプトで各ファイルのバイトサイズをどのように印刷しますか? [閉鎖]

私の現在のコードは次のとおりです。

スキャン.sh:

#!/bin/bash
while IFS= read -r line;
do
    byte = $(stat -c%s "$line");
    echo "$line : $byte";
done< <(ls *.$1)

出力は次のとおりです。

./scan.sh cpp
./scan.sh: line 4: byte: command not found
arraysum.cpp :
./scan.sh: line 4: byte: command not found
countLines.cpp :
./scan.sh: line 4: byte: command not found
createtext.cpp :
./scan.sh: line 4: byte: command not found
multiproc1.cpp :
./scan.sh: line 4: byte: command not found
myWc.cpp :
./scan.sh: line 4: byte: command not found
test.cpp :

デフォルトでは、私のコードは構文を使用し、その構文に基づいてディレクトリを検索します。問題は、「ファイル名」+「ファイルバイトサイズ」を印刷したいのですが、正しく機能しないようです。

答え1

Bourneのシェルに似た構文では、bashシンボル割り当ての周りにスペースを含めることはできません=

byte=value

しかし、ここで解析された出力lsは悪い考えです。

次のように書くことができます。

#! /bin/sh -
stat -c '%n: %s' -- *."$1"

ループが本当に必要な場合は、次のように書きます。

#! /bin/zsh -
for file in *.$1; do
  stat -c '%n: %s' -- $file
done

または、以下を使用する必要がある場合bash

#! /bin/bash -
shopt -s failglob
for file in *."$1"; do
  stat -c '%n: %s' -- "$file"
done

答え2

これはこれを行う簡単な方法で、次のように使用する必要があります。ボンシェル正確な出力形式に大変気にしない場合、その子孫(bashとkshを含む)は次のようになります。

$ for file in *; do if [ -f "$file" ] && [ -r "$file" ]; then wc -c "$file"; fi; done
      23 HEAD
     111 config
      73 description

バグや特殊な場合でも大きく気にしない場合(このような場合は幸運です):

$ for file in *; do wc -c $file; done

メモ:

  • bashまたはkshを使用してこのコードを書く場合は、代わりに(( ))orを使用することをお勧めします。 ([[ ]][ ]源泉)また、以下の代わりに$(wc -c <"$file"))を使用することを検討してください`wc -c <"$file"`。 (源泉)

  • -f見ているものが一般的なファイルであるかどうかをテストしてください(ディレクトリ、デバイス、パイプ、ソケット、tty、または通常はバイト単位のサイズを持っているとは言えない奇妙なファイルではありません)。-rファイルが読めるかどうかをテストします。つまり、wc成功する可能性が高い。大容量ファイルや読めないファイルを見ている場合は、stat元のバージョンとStéphaneの答えに従ってください。

  • "$file"ファイルにスペースやタブが含まれている場合(名前付きファイルなど)、引用符()を使用する必要がありますmy stuff.txt

  • 正しい形式に興味がある場合は`wc -c <"$file"`(ファイル名を印刷しない)echoまたはecho -n(必要に応じて印刷する)を組み合わせて使用​​する必要があります。

  • 興味のあるファイルがスクリプトの引数である場合"$@"説明する)。

ls私は;の出力を解析してはならないという@stéphane-chazelasのコメントに同意します。だが、そうすればそうする必要はない。プロセスの交換。コマンドの出力をより簡単に読み取ることができます。

ls | while IFS= read -r ちょっと待ってちょっと待って

またはディレクトリを再帰的に使用したい場合:

find 無意味な言葉 -type f -print | while IFS= read -r バラバラ

または、より良い方法は次のとおりです。

find 無意味な言葉 -type f print0 | xargs -o バラバラ

スペースまたはタブを含むファイル名を-print0正しく正しく処理します。xargs -0

関連情報