we’ve seen, scripts can grab a listing of file and directory names at this level by simply
spawning the appropriate platform-specific command line and reading its output (the
text normally thrown up on the console window):
C:\temp> python
>>> import os
>>> os.popen('dir /B').readlines()
['parts\n', 'PP3E\n', 'random.bin\n', 'spam.txt\n', 'temp.bin\n', 'temp.txt\n']
Lines read from a shell command come back with a trailing end-of-line character, but
it’s easy enough to slice it off; the os.popen result also gives us a line iterator just like
normal files:
>>> for line in os.popen('dir /B'):
... print(line[:-1])
...
parts
PP3E
random.bin
spam.txt
temp.bin
temp.txt
>>> lines = [line[:-1] for line in os.popen('dir /B')]
>>> lines
['parts', 'PP3E', 'random.bin', 'spam.txt', 'temp.bin', 'temp.txt']
For pipe objects, the effect of iterators may be even more useful than simply avoiding
loading the entire result into memory all at once: readlines will always block the caller
until the spawned program is completely finished, whereas the iterator might not.
The dir and ls commands let us be specific about filename patterns to be matched and
directory names to be listed by using name patterns; again, we’re just running shell
commands here, so anything you can type at a shell prompt goes:
>>> os.popen('dir *.bin /B').readlines()
['random.bin\n', 'temp.bin\n']
>>> os.popen(r'c:\cygwin\bin\ls *.bin').readlines()
['random.bin\n', 'temp.bin\n']
>>> list(os.popen(r'dir parts /B'))
['part0001\n', 'part0002\n', 'part0003\n', 'part0004\n']
>>> [fname for fname in os.popen(r'c:\cygwin\bin\ls parts')]
['part0001\n', 'part0002\n', 'part0003\n', 'part0004\n']
These calls use general tools and work as advertised. As I noted earlier, though, the
downsides of os.popen are that it requires using a platform-specific shell command and
it incurs a performance hit to start up an independent program. In fact, different listing
tools may sometimes produce different results:
>>> list(os.popen(r'dir parts\part* /B'))
['part0001\n', 'part0002\n', 'part0003\n', 'part0004\n']
Directory Tools | 165