28.4. Build Strings with { }
I've been finding
more and more uses for the {} pattern-expansion
characters in csh ,
tcsh, zsh, and
bash. They're similar
to *, ?, and [ ] (Section 33.2), but they don't match
filenames the way that *, ?,
and [ ] do. You can give them arbitrary text (not
just filenames) to expand -- that
"expand-anything" ability is what
makes them so useful.
Here are some examples to get you thinking:
-
To fix a typo in a filename (change fixbold5.c
fixbold6.c):
% mv fixbold{5,6}.c
To see what the shell will do with {}, add
echo (Section 27.5)
before the mv:
% echo mv fixbold{5,6}.c
mv fixbold5.c fixbold6.c
-
To copy filename to
filename.bak without retyping
filename:
% cp filename{,.bak}
-
To print files from other directory(s)
without retyping the whole pathname:
% lpr /usr3/hannah/training/{ed,vi,mail}/lab.{ms,out}
That would give lpr (Section 45.2) all of these files:
/usr3/hannah/training/ed/lab.ms
/usr3/hannah/training/ed/lab.out
/usr3/hannah/training/vi/lab.ms
/usr3/hannah/training/vi/lab.out
/usr3/hannah/training/mail/lab.ms
/usr3/hannah/training/mail/lab.out
...in one fell swoop!
-
To edit ten new files that don't exist yet:
% vi /usr/foo/file{a,b,c,d,e,f,g,h,i,j}
That would make /usr/foo/filea,
/usr/foo/fileb, ...
/usr/foo/filej. Because the files
don't exist before the command starts, the wildcard
vi /usr/foo/file[a-j] would not work (Section 28.3).
-
An easy way to step through three-digit numbers 000, 001, ..., 009,
010, 011, ..., 099, 100, 101, ... 299 in the C shell is:
foreach Section 28.9
foreach n ({0,1,2}{0,1,2,3,4,5,6,7,8,9}{0,1,2,3,4,5,6,7,8,9})
...Do whatever with the number $n...
end
Yes, csh also has built-in arithmetic, but its
@ operator can't make numbers
with leading zeros. This nice trick shows that the
{} operators are good for more than just
filenames.
-
In zsh, {} also understands
.. as an integer-range operator.
So you could generate the 300 numbers in the previous example with
{000..299}. The leading 00
tells zsh to pad all output numbers to three
digits with leading zeros.
If you give the range in reverse order, like
{299..0}, zsh will output the
integers in descending order: 299, 298, and so on, down to 1 and 0.
-
To send a mail (Section 1.21) message to
multiple recipients where a part of each email address is repeated:
% mail -s "Link to me" webmaster@{foo,bar,baz}.com < msgfile
-
If you're using a
graphical email program (not the command-line mail
program shown above), and you're sending an email
message to lots of people at the same host, it can be a pain to type
the same hostname over and over in the
"To:" line. Let the
shell's {} operators do the dirty
work! Use echo to output the addresses. (Note the
comma (,) after each address.) Then copy all of them -- except the
final comma -- with your mouse, and paste them into the GUI mail
program:
% echo {jane,joe,jill,john,jean}@foo.org,
jane@foo.org, joe@foo.org, jill@foo.org, john@foo.org, jean@foo.org,
-
To
create sets of subdirectories:
% mkdir man
% mkdir man/{man,cat}{1,2,3,4,5,6,7,8}
% ls -F man
cat1/ cat3/ cat5/ cat7/ man1/ man3/ man5/ man7/
cat2/ cat4/ cat6/ cat8/ man2/ man4/ man6/ man8/
-
Here's how to
copy the remote files
file1.c, file12.c,
file45.c, and file77.c from
the subdirectory foo on the remote host
remulac to the local system. Your local shell
expands the strings (into remulac:foo/file1.c,
remulac:foo/file12.c, etc.) and passes them to
scp (Section 29.14):
. Section 1.16
% scp remulac:foo/file{1,12,45,77}.c .
-
Here are two ways to
print 10 copies of the file project_report if
your lpr (Section 45.2) command
doesn't have a -#10 option. We
showed the first way in the first two editions of this book. Dimi
Shahbaz sent us the second one: 9 commas give 10 filenames. (Thanks,
Dimi!) Both of them work on all the shells I tried:
% lpr project_repor{t,t,t,t,t,t,t,t,t,t}
% lpr project_report{,,,,,,,,,}
Of course, this doesn't just work for
lpr or filenames. Remember that the shell expands
the list of strings, so you can use these tricks anywhere you use
{}.
In bash, the
complete-into-braces editor command (which is
bound to the M-{ key sequence by default in Emacs
mode) expands a string into a list of matching filenames in braces.
For example:
$ ls pr*
prog1.c prog2.c program1.c program2.c
$ cc pr META{
$ cc pr{og1.c,og2.c,ogram1.c,orgram2.c}
Then you can edit the brace expression.
-- JP
| | | 28.3. Use Wildcards to Create Files? | | 28.5. String Editing (Colon) Operators |
Copyright © 2003 O'Reilly & Associates. All rights reserved.
|
|