This work is licensed under a Creative Commons Attribution-ShareAlike 4.0 International License
In this lesson, you will write basic programs from an “Intro to CS” course using C. These should not be hard since C and Java are very similar. Read the C for Java Programmers document if you don’t already understand this.
Each step of the lesson asks you to answer a question or write some code. Do the steps yourself before checking your work by revealing the answer.
A few quick comments:
float
variables to store the temperature. You could have used double
instead. You should already know that it would be wrong to use int
since temperatures can clearly be fractional. Try it!%f
specifier in the printf
format string (“floating point”). You could also use g
or e
. Try it!printf
how many with a “precision” modifier, as in %.2f
. Try it!5/9
, they may be treated as integers, and five divided by nine using integer division is... 0. Try it!if
-else
and switch
.
while
, for
, and do
-while
. C also has the same increment/decrement operators (++
and --
) and compound assignment statments (+=
, etc.). In fact, Java has them because C has them!
For now, write the following two functions:
main
. Then to use them in main
, for example:
printStars(5);
printf("\n");
printf("0 degrees F is %f Kelvins\n", ftok(0.0));
Download full program: basics1.c
In Java, you use the Scanner
class to read input from the console (there are other possibilities also). It’s not quite so straightforward in C, but the basic patterns are not hard to learn.
In C, the basic building block for input is the C standard library function scanf
(defined in <stdio.h>
). It’s sort of like printf
in reverse. You give it a format string with %
specifiers, and it reads the input according to that specification. For example, %d
means “read an integer,” %f
means “read an floating-point number,” and so on. There can be more than one %
specifier, in which case scanf
tries to read more than one thing.
An important point is that scanf
usually needs to “return” more than one thing. There’s the value or values specified in the format string, and there’s an overall return value indicating whether the values were present in the input. The latter is returned as the return value of the function. To receive the individual values, you must also pass scanf
references (pointers) to where you want them stored. For primitive types, this will be a pointer to a variable of that type, for example an int*
. For reference types, including strings which are char*
s, you just just give scanf
the pointer.
FYI: The C for Java Programmers document uses scanf
as an example in its discussion of pointers. Check it out.
Then write a function that reads, separately, an integer, a floating-point value, and a string and prints out what it read.
scanf
the %s
specifier. Read the manual entry for it. That’s what it’s supposed to do. Read on for an alternative.
You could also read all three values in one call to scanf
. Try it!
scanf
says the following about the %s
specifier:
“Matches a sequence of non-white-space characters; the next pointer must be a pointer to char, and the array must be large enough to accept all the sequence and the terminating NUL character. The input string stops at white space or at the maximum field width, whichever occurs first.”This is sort of similar to what
Scanner.next
returns.
If you just want to read the next line of input (up to a newline), like Scanner.nextLine
, the function you want is fgets
. The incantation
fgets(str, 255, stdin);
reads into the character array str
at most 255 characters from the standard input (stdin
). The array str
must be big enough to hold that many characters and a terminating NUL
character, and it’s YOUR problem to make sure that it is.
Note: There is an apparently simpler function named gets
which reads from the console into the given character array with no length limit. The manual entry for gets
and fgets
says the following:
“TheSo don’t usegets()
function cannot be used securely. Because of its lack of bounds checking, and the inability for the calling program to reliably determine the length of the next incoming line, the use of this function enables malicious users to arbitrarily change a running program’s functionality through a buffer overflow attack. It is strongly suggested that thefgets()
function be used in all cases.”
gets
. Use fgets
and give an appropriate size limit for the buffer you’re reading into. Also note that fgets
includes the newline that the user typed.
Finally, for this step, write a program that reads lines from the console and prints them out as they are read. The program should stop reading when it reads an empty (blank) line.
str
, which is why we don’t have to print one ourselves. That’s also why the loop condition works: if the first (0th) character read is a newline character, then the input was an empty line. You could also use the strlen
function from <string.h>
and test for a string of length... 1 (since it includes the newline).
Download full program: basics2.c
File
objects and various flavors of InputStream
s, OutputStream
s, Reader
s, Printer
s, and Scanner
s to read and write files. In C it’s quite a bit simpler, but the standard library provides functions to get the job done. You will need to #include <stdio.h>
to use these functions.
fopen
opens a file identified by name. The name is relative to the “current working directory” of the process running your code. The format of pathnames varies by platform. You can ask for the file to be opened for reading (input) or writing (output), and there are other possibilities. If successful, fopen
returns a FILE*
(a “file pointer”, a pointer to a value of type FILE
) representing the open file. If the open fails, fopen
returns NULL
and the global variable errno
is set to a value that indicates what was the problem. You will need to #include <errno.h>
to use errno
if you need it.fprintf
is just like printf
, except that instead of printing to the console (“standard output”), it prints to the output FILE*
given as first argument.fscanf
is just like scanf
, except that instead of reading from the console (“standard inpout”), it reads from the input FILE*
given as first argument.fgets
, which reads text up to a newline. Its third argument is a FILE*
.feof
returns true if the input FILE*
given as argument has been completely read (“end of file” or “EOF”).fclose
is used to close a file when you are finished with it.stdin
used in our fgets
example in the previous step is defined in <stdio.h>
and refers to the console input (there is also stdout
).
fopen
).
Download full program: basics3.c
and sample text file xanadu.txt