1+ import argparse
2+ import os
3+
4+ parser = argparse .ArgumentParser (prog = "wc" , description = "Print newline, word and byte counts" )
5+ parser .add_argument ("-l" , "--lines" , action = "store_true" , help = "Print the newline counts" )
6+ parser .add_argument ("-w" , "--words" , action = "store_true" , help = "Print the word counts" )
7+ parser .add_argument ("-c" , "--bytes" , action = "store_true" , help = "Print the byte counts" )
8+ parser .add_argument ("files" , nargs = "+" , help = "The files to count" )
9+
10+ args = parser .parse_args ()
11+
12+ show_all = not (args .lines or args .words or args .bytes )
13+ show_lines = args .lines or show_all
14+ show_words = args .words or show_all
15+ show_bytes = args .bytes or show_all
16+
17+ rows = []
18+ total = [0 , 0 , 0 ]
19+
20+ for path in args .files :
21+ with open (path , "rb" ) as f :
22+ data = f .read ()
23+ counts = [data .count (b"\n " ), len (data .split ()), len (data )]
24+ for i in range (3 ):
25+ total [i ] += counts [i ]
26+ rows .append ((counts , path ))
27+
28+ if len (args .files ) > 1 :
29+ rows .append ((total , "total" ))
30+ width = len (str (sum (os .path .getsize (path ) for path in args .files )))
31+ else :
32+ width = 1
33+
34+
35+ def selected (counts ):
36+ chosen = []
37+ if show_lines :
38+ chosen .append (counts [0 ])
39+ if show_words :
40+ chosen .append (counts [1 ])
41+ if show_bytes :
42+ chosen .append (counts [2 ])
43+ return chosen
44+
45+
46+ for counts , label in rows :
47+ columns = " " .join (f"{ value :{width }} " for value in selected (counts ))
48+ print (f"{ columns } { label } " )
0 commit comments