dapatkan hanya integer dari wc di bash


115

Apakah ada cara untuk mendapatkan integer yang wc dikembalikan dalam bash?

Pada dasarnya saya ingin menulis nomor baris dan jumlah kata ke layar setelah nama file.

output: filename linecount wordcount Inilah yang saya miliki sejauh ini:

files=`ls`
for f in $files;
do
        if [ ! -d $f ] #only print out information about files !directories
        then
                # some way of getting the wc integers into shell variables and then printing them
                echo "$f $lines $ words"
        fi
done

Jawaban:


57

Anda dapat menggunakan cutperintah untuk mendapatkan hanya kata pertama dari wckeluaran (yaitu jumlah baris atau kata):

lines=`wc -l $f | cut -f1 -d' '`
words=`wc -w $f | cut -f1 -d' '`

5
Menjalankan wc dua kali untuk file yang sama tidak efisien.
gawi

3
Benar, itulah mengapa saya pikir jawaban James Broadhead jauh lebih baik. Saya tidak bisa cutmengerjakan hasil penuh wc $fkarena jumlah spasi antar bidang bervariasi.
casablanca

1
@casablanca Anda dapat menekan jumlah spasi menggunakan 'tr -s'. Saya telah membuat daftar solusi yang lebih portabel untuk pertanyaan ini dalam jawaban saya di bawah ini.
rubel

Karena dalam jawaban ini kami menetapkan ke variabel, kami dapat mematikan spasi dengan
cycollins

88

Jawaban paling sederhana yang pernah ada:

wc < filename 

5
Tetapi tidak menghasilkan keluaran yang diinginkan.
Dave Newton

tentu saja demikian, Anda cukup memasukkan parameter yang sesuai yang Anda inginkan. misalnya, jika Anda melakukannya wc -c < file name, itu hanya akan memberi Anda bilangan bulat byte dan tidak ada yang lain.
BananaNeil

13
Maksud saya adalah bahwa jika Anda akan menjawab pertanyaan (1,5 tahun), sebaiknya Anda memasukkan semua info ke dalam jawabannya, itu saja :)
Dave Newton

whoops, hanya membaca kembali pertanyaan .. # FAIL, saya sedang meneliti bagaimana untuk mendapatkan hanya bilangan bulat, dan saya menggunakan informasi dari salah satu jawaban, ketika saya menemukan jawaban yang lebih baik, dan kemudian memutuskan untuk posting tentang hal itu. maaf ..
BananaNeil

3
Anda telah menjawab Google, itulah yang terpenting. :-)
Ciro Santilli 郝海东 冠状 病 六四 事件 法轮功

82

Hanya:

wc -l < file_name

akan melakukan pekerjaan itu. Tapi keluaran ini menyertakan spasi kosong sebagai wcangka rata kanan.


3
Untuk mendapatkan hitungan baris saja tanpa spasi: wc -l < foo.txt | xargsref - stackoverflow.com/a/12973694/149428
Taylor Edmiston

1
Jadi, sementara perintah menghasilkan jawaban dengan spasi di depan, penanya menetapkan ke variabel dan itu menghilangkan spasi di depan secara otomatis (setidaknya itu adalah pengalaman saya pada pesta OSX yang lebih lama). Dengan kata lain, lines=`wc -l < $f`menghasilkan variabel "baris" yang nilainya tidak memiliki spasi di depan.
cycollin

Bagaimana jika saya bergabung dengan find? Saya mendapatkan kesalahan: find . -path -prune -o -name "*.swift" -print0 | xargs -0 wc -lberfungsi dengan baik tetapi mencetak setiap file. Jika saya menggunakan find . -path -prune -o -name "*.swift" -print0 | xargs -0 wc -l <saya mendapatkan kesalahan. parse error near '\n'
Nuno Gonçalves

55
wc $file | awk {'print "$4" "$2" "$1"'}

Sesuaikan seperlunya untuk tata letak Anda.

Juga lebih baik menggunakan logika positif ("adalah file") daripada negatif ("bukan direktori")

[ -f $file ] && wc $file | awk {'print "$4" "$2" "$1"'}

1
Di Windows saya di Cmder (bash 4.4.12) ini berfungsi: wc $file | awk '{print $4" "$2" "$1}'- apostrof di luar {}.
Grzegorz Gierlik

36

Terkadang output wc dalam format berbeda di platform berbeda. Sebagai contoh:

Di OS X:

$ echo aa | wc -l

         1

Di Centos:

$ echo aa | wc -l

1

Jadi menggunakan hanya potongan tidak dapat mengambil nomor tersebut. Sebagai gantinya coba tr untuk menghapus karakter spasi:

$ echo aa | wc -l | tr -d ' '

23

Jawaban yang diterima / populer tidak berfungsi di OSX.

Salah satu dari berikut ini harus portabel di bsd dan linux.

wc -l < "$f" | tr -d ' '

ATAU

wc -l "$f" | tr -s ' ' | cut -d ' ' -f 2

ATAU

wc -l "$f" | awk '{print $1}'

11

Jika Anda mengarahkan nama file ke wcdalamnya menghilangkan nama file pada output.

Pesta:

read lines words characters <<< $(wc < filename)

atau

read lines words characters <<EOF
$(wc < filename)
EOF

Alih-alih menggunakan foruntuk mengulangi keluaran ls, lakukan ini:

for f in *

yang akan berfungsi jika ada nama file yang menyertakan spasi.

Jika Anda tidak dapat menggunakan globbing, Anda harus menyalurkan ke while readloop:

find ... | while read -r f

atau gunakan substitusi proses

while read -r f
do
    something
done < <(find ...)

Saya tetap memberi suara positif kepada Anda, tetapi Anda tidak perlu mengalihkan nama file. Tangkap saja sebagai bidang tambahan. read lines words characters filename <<< $(wc "$f")Oh, dan jika Anda dulu * dikeraskan dengan spasi, Anda juga ingin mengutip ganda var saat menggunakannya.
Bruno Bronosky

Menggunakan variabel tambahan memang cara lain untuk melakukannya, tetapi jika Anda tidak akan menggunakan variabel (mungkin Anda sudah memiliki nama file dalam variabel - $fdalam hal ini), itu tidak perlu. Juga, OP meminta bagaimana untuk mendapatkan hanya integer. Anda benar tentang mengutip variabel, tetapi saya tidak menunjukkan penggunaan variabel, jadi saya menghilangkan penyebutan hal itu. The for f in *Bentuk harus hampir selalu digunakan daripada menggunakan output dari ls, seperti yang Anda tahu.
Dijeda sampai pemberitahuan lebih lanjut.

Saya setuju sepenuhnya tentang hal lsitu. Itu akan memberimu penghargaan. partmaps.org/era/unix/award.html#ls
Bruno Bronosky

Jika Anda tidak menginginkan nama file, Anda dapat melakukan ini:read lines words characters _ <<< $(wc "$f")

@EvanTeitelman: Seperti yang dibahas dalam beberapa komentar di atas milik Anda. $_hanyalah variabel yang berbeda.
Dijeda sampai pemberitahuan lebih lanjut.

3

Jika filenya kecil, Anda dapat menelepon wcdua kali, dan menggunakan sesuatu seperti berikut, yang menghindari menyalurkan ke proses tambahan:

lines=$((`wc -l "$f"`))
words=$((`wc -w "$f"`))

Itu $((...))adalah Ekspansi Aritmatika dari bash. Ini menghapus spasi apa pun dari output wcdalam kasus ini.

Solusi ini lebih masuk akal jika Anda perlu baik yang linecount atau wordcount tersebut.


2

Bagaimana dengan sed?

wc -l /path/to/file.ext | sed 's/ *\([0-9]* \).*/\1/'


1

Coba ini untuk hasil numerik:
nlines = $ (wc -l <$ myfile)


0

Coba ini:

wc `ls` | awk '{ LINE += $1; WC += $2 } END { print "lines: " LINE  " words: " WC }'

Ini membuat jumlah baris, dan jumlah kata (LINE dan WC), dan meningkatkannya dengan nilai yang diekstrak dari wc (menggunakan $ 1 untuk nilai kolom pertama dan $ 2 untuk yang kedua) dan akhirnya mencetak hasilnya.


0

"Pada dasarnya saya ingin menulis nomor baris dan jumlah kata ke layar setelah nama file."

answer=(`wc $f`)
echo -e"${answer[3]}
lines:  ${answer[0]}
words:  ${answer[1]}
bytes:  ${answer[2]}"

Keluaran: baris myfile.txt: 10 kata: 20 byte: 120


0
files=`ls`
echo "$files" | wc -l | perl -pe "s#^\s+##"

Jika Anda perltetap menggunakannya , sebaiknya lakukan penghitungan kata di Perl juga. Pendekatan yang lebih ekonomis adalah dengan menyalurkan ketr -d '[:space:]'
tripleee
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.