* better
[mascara-docs.git] / lang / C / the.ansi.c.programming.language / c.programming.notes / sx13.html
bloba75e35e7b9d692ac412ccba3669f50b92637ab02
1 <!DOCTYPE HTML PUBLIC "-//W3O//DTD W3 HTML 2.0//EN">
2 <!-- This collection of hypertext pages is Copyright 1995-7 by Steve Summit. -->
3 <!-- This material may be freely redistributed and used -->
4 <!-- but may not be republished or sold without permission. -->
5 <html>
6 <head>
7 <link rev="owner" href="mailto:scs@eskimo.com">
8 <link rev="made" href="mailto:scs@eskimo.com">
9 <title>Chapter 13: Reading the Command Line</title>
10 <link href="sx12e.html" rev=precedes>
11 <link href="sx14.html" rel=precedes>
12 <link href="top.html" rev=subdocument>
13 </head>
14 <body>
15 <H1>Chapter 13: Reading the Command Line</H1>
17 <p>[This section corresponds to K&amp;R Sec. 5.10]
18 </p><p>We've mentioned several times that a program is rarely useful
19 if it does exactly the same thing every time you run it.
20 Another way
21 of giving a program some variable input to work on
22 is by invoking it with <dfn>command line arguments</dfn>.
23 </p><p>(We should probably admit that command line user interfaces
24 are a bit old-fashioned,
25 and currently somewhat out of favor.
26 If you've used Unix or MS-DOS, you know what a command line is,
27 but if your experience is confined to
28 the Macintosh or Microsoft Windows or some other Graphical User Interface,
29 you may never have seen a command line.
30 In fact, if you're learning C on a Mac or under Windows,
31 it can be tricky to give your program a command line at all.
32 Think C for the Macintosh provides a way;
33 I'm not sure about other compilers.
34 If your compilation environment doesn't provide an easy way
35 of simulating an old-fashioned command line, you may skip this chapter.)
36 </p><p>C's model of the command line
37 is that it consists of a sequence of words,
38 typically separated by whitespace.
39 Your main program can receive these words as an array of strings,
40 one word per string.
41 In fact,
42 the C run-time startup code is always willing to pass you this array,
43 and all you have to do to receive it
44 is to declare <TT>main</TT> as accepting two parameters,
45 like this:
46 <pre>
47 int main(int argc, char *argv[])
49 ...
51 </pre>
52 When <TT>main</TT> is called,
53 <TT>argc</TT> will be a count of the number of command-line arguments,
54 and <TT>argv</TT> will be
55 an array (``vector'') of the arguments themselves.
56 Since each word is a string which is represented
57 as a pointer-to-<TT>char</TT>,
58 <TT>argv</TT> is an array-of-pointers-to-<TT>char</TT>.
59 Since we are not <dfn>defining</dfn> the <TT>argv</TT> array,
60 but merely declaring a parameter which references an array somewhere else
61 (namely, in <TT>main</TT>'s caller, the run-time startup code),
62 we do not have to supply an array dimension for <TT>argv</TT>.
63 (Actually, since functions never receive arrays as parameters in C,
64 <TT>argv</TT> can also be thought of
65 as a pointer-to-pointer-to-<TT>char</TT>,
66 or <TT>char **</TT>.
67 But multidimensional arrays and pointers to pointers can be confusing,
68 and we haven't covered them,
69 so we'll talk about <TT>argv</TT> as if it were an array.)
71 (Also, there's nothing magic about the names <TT>argc</TT> and <TT>argv</TT>.
72 You can give <TT>main</TT>'s two parameters any names you like,
73 as long as they have the appropriate types.
74 The names <TT>argc</TT> and <TT>argv</TT> are traditional.)
75 </p><p>The first program to write when playing with <TT>argc</TT> and <TT>argv</TT>
76 is one which simply prints its arguments:
77 <pre>
78 #include &lt;stdio.h&gt;
80 main(int argc, char *argv[])
82 int i;
84 for(i = 0; i &lt; argc; i++)
85 printf("arg %d: %s\n", i, argv[i]);
86 return 0;
88 </pre>
89 (This program is essentially the Unix or MS-DOS <TT>echo</TT> command.)
90 </p><p>If you run this program,
91 you'll discover that the set of ``words''
92 making up the command line
93 includes the command you typed to invoke your program
94 (that is, the name of your program).
95 In other words,
96 <TT>argv[0]</TT> typically points to the name of your program,
98 and <TT>argv[1]</TT> is the first argument.
99 </p><p>There are no hard-and-fast rules
100 for how a program should interpret its command line.
101 There is one set of conventions for Unix,
102 another for MS-DOS,
103 another for VMS.
104 Typically you'll loop over the arguments,
105 perhaps treating some as option flags and others as actual arguments
106 (input files, etc.),
107 interpreting or acting on each one.
108 Since each argument is a string,
109 you'll have to use <TT>strcmp</TT> or the like
110 to match arguments against any patterns you might be looking for.
111 Remember that <TT>argc</TT> contains
112 the number of words on the command line,
113 and that <TT>argv[0]</TT> is the command name,
114 so if <TT>argc</TT> is 1,
115 there are no arguments to inspect.
116 (You'll never want to look at <TT>argv[i]</TT>,
117 for <TT>i &gt;= argc</TT>,
118 because it will be a null or invalid pointer.)
119 </p><p>As another example,
120 also illustrating <TT>fopen</TT>
121 and the file I/O techniques of the previous chapter,
122 here is a program which copies one or more input files
123 to its standard output.
124 Since ``standard output'' is usually the screen by default,
125 this is therefore a useful program for displaying files.
126 (It's analogous to the obscurely-named Unix <TT>cat</TT> command,
127 and to the MS-DOS <TT>type</TT> command.)
128 You might also want to compare this program
129 to the character-copying program of section
131 6.2.
132 <pre>
133 #include &lt;stdio.h&gt;
135 main(int argc, char *argv[])
137 int i;
138 FILE *fp;
139 int c;
141 for(i = 1; i &lt; argc; i++)
143 fp = fopen(argv[i], "r");
144 if(fp == NULL)
146 fprintf(stderr, "cat: can't open %s\n", argv[i]);
147 continue;
150 while((c = getc(fp)) != EOF)
151 putchar(c);
153 fclose(fp);
156 return 0;
158 </pre>
159 As a historical note, the Unix <TT>cat</TT> program is so named
160 because it can be used to con<B>cat</B>enate two files together,
161 like this:
162 <pre>
163 cat a b &gt; c
164 </pre>
165 This illustrates why it's a good idea
166 to print error messages to <TT>stderr</TT>,
167 so that they don't get redirected.
168 The ``can't open file'' message
169 in this example
170 also includes the name of the program
171 as well as the name of the file.
172 </p><p>Yet another piece of information
173 which it's usually appropriate to include in error messages
174 is the reason why the operation failed, if known.
175 For operating system problems,
176 such as inability to open a file,
177 a code indicating the error is often stored
178 in the global variable <TT>errno</TT>.
179 The standard library function <TT>strerror</TT>
180 will convert an <TT>errno</TT> value
181 to a human-readable error message string.
182 Therefore,
183 an even more informative error message printout would be
184 <pre>
185 fp = fopen(argv[i], "r");
186 if(fp == NULL)
187 fprintf(stderr, "cat: can't open %s: %s\n",
188 argv[i], strerror(errno));
189 </pre>
190 If you use code like this,
191 you can <TT>#include &lt;errno.h&gt;</TT>
192 to get the declaration for <TT>errno</TT>,
193 and <TT>&lt;string.h&gt;</TT>
194 to get the declaration for <TT>strerror()</TT>.
195 </p><hr>
197 Read sequentially:
198 <a href="sx12e.html" rev=precedes>prev</a>
199 <a href="sx14.html" rel=precedes>next</a>
200 <a href="top.html" rev=subdocument>up</a>
201 <a href="top.html">top</a>
202 </p>
204 This page by <a href="http://www.eskimo.com/~scs/">Steve Summit</a>
205 // <a href="copyright.html">Copyright</a> 1995-1997
206 // <a href="mailto:scs@eskimo.com">mail feedback</a>
207 </p>
208 </body>
209 </html>