1. | Welcome | ToC | FAQ | Resources | Courses | Projects | Mail Lists | Members | Misc |
2. | Fundamentals | Languages | Tools | Net | Core | Advanced |
3. | EoC | Java |
4. | Lessons |
5. | 01 | 02 | 03 | 04 | 05 | 06 | 07 | 08 | 09 | 10 | 11 |


Essence of C
8 - CONSOLE INPUT/OUTPUT

Reading and Writing Characters and Strings, Formatted Console Input/Output

Introduction

C is virtually unique as a language in that it has no keywords for input/output (I/O). Instead, I/O is accomplished through library functions.

There are two types of I/O in C, viz, console I/O and file I/O. Technically, there is little distinction between the two, although they are, conceptually, quite different worlds.

The standard C console I/O functions perform only TTY-based output; however, most compilers include in their libraries machine-specific screen control and graphics functions.

It should be noted that, although the following pertains to input from the keyboard and output to the screen, the actual source and target of C's I/O functions are the standard input and standard output of the system, which means that this input and output may be re-directed to other devices.

Reading and Writing Characters

The following functions read characters from the keyboard and write characters to the screen:

Function Operation
getchar()

Reads a character from the keyboard; waits for carriage return. Returns an integer, in which the low-order byte contains the character. Any key, including RETURN, TAB and ESC may be returned by getchar().

Note: Because it waits for a carriage return, getchar() is not useful in an interactive environment (except in the case of some compilers which actually implement getchar() as an interactive function, which is permitted by the ANSI standard). The ANSI standard does not, in fact, define any function guaranteed to provide interactive input, but many C compilers include alternative keyboard input functions which achieve this.

getch() Waits for a keypress, after which it returns immediately. Reads the character without an echo to the screen. (One of the common alternatives to getchar(). Not defined by ANSI.)
getche() Same as getch(), but echoes the character.
putchar() Writes a character to the screen. Declared as using an integer parameter; however, only the low-order byte is output to the screen. Returns the character written, or EOF (-1) if an error occurs.

Reading and Writing Strings

The following functions read and output strings:

Function Operation
gets() Reads a string of characters and places them at the address pointed to by its character pointer argument. When RETURN is entered, a null terminator is placed at the end of the string and the function returns. Typing errors may be corrected with the BACKSPACE key.
puts() Writes its string argument to the screen, followed by a newline. Recognizes the same "backslash" codes as printf() (eg, \t for TAB). Cannot output numbers, but is faster than printf() in outputting strings. Returns EOF if an error occurs.

Formatted Console I/O

The functions printf() and scanf() read and write data in various formats specified by the programmer. Both functions can operate on any of the built-in data types, including characters, strings and numbers.

printf()

The prototype for printf() is:

    int printf(char *control_string,argument_list);

Where control_string consists of two types of items, namely, characters which will be printed to the screen and format specifiers which control how the subsequent arguments are displayed.


Format Specifiers

The various format specifiers are as follows:

Specifier Description
%c Character.
%d Signed decimal integer.
%i Signed decimal integer.
%e Scientific notation (lowercase e).
%E Scientific notation (uppercase E).
%f Decimal floating point.
%g Uses %e or %f, whichever is shorter.
%G Uses %E or %F, whichever is shorter.
%o Unsigned octal.
%s String of characters.
%u Unsigned decimal integers.
%x Unsigned hexadecimal (lowercase letters).
%X Unsigned hexadecimal (uppercase letters).
%p Pointer.
%n The argument is an integer pointer into which the number of characters written so far is placed. Enables a program to perform dynamic formatting.
%% Prints a %.

The %n format specifier is different from the other specifiers. As an example of usage, this code fragment:

    int count;

    printf("this%nis a test\n", &count);
    printf("%d", count);

would cause this is a test followed by 4 to be displayed.


Format Modifiers

Many format specifiers may take format modifiers, which slightly alter their meaning. These modifiers include the following:


Left Justification (-)

By default, output is right-justified. That is, if the field width is larger than the data printed, the data will be placed at the right edge. Left justification may be forced by using a minus sign after the %. For example, %-10.2f left justifies a floating point number in a ten-character field.


The l, h and L Modifiers

The l and h modifiers may prefix the d, i, o, u, and x type specifiers. l tells printf() that a long data type follows. h tells printf() to display a short int.

The L modifier may also prefix the floating point specifiers e, f, and g and indicates that a long double follows.


The # Modifier

Preceding g, f, or e specifiers with a # ensures that there will be a decimal point even if there are no decimal digits.

Preceding the x specifier with a # ensures that the hexadecimal number will be printed with a 0x prefix.


The * Modifier

The minimum field width and precision specifiers are usually constants; however, they may also be provided by arguments to printf(). To achieve this, * is used as a placeholder. For example, in:

    printf("%*.*f", 10, 4, 1234.34);

the minimum field width is 10, the precision is 4 and the value to be displayed is 1234.34.

scanf()

scanf() is the general purpose console input function. It can read in all of the built-in data types and automatically convert numbers into the proper internal format. The prototype is:

    int scanf(char *control_string, argument_list);

scanf() returns the number of data items successfully assigned a value. If an error occurs, EOF is returned


Format Specifiers

The input format specifiers tell scanf() what type of data is to be read next. The codes are as follows:

Specifier Description
%c Read a single character.
%d Read a decimal integer.
%i Read a decimal integer.
%e Read a floating-point number.
%f Read a floating-point number.
%g Read a floating-point number.
%o Read an octal number.
%s Read a string.
%x Read a hexadecimal number.
%p Read a pointer.
%n Receive an integer value equal to the number of characters read so far.
%u Read an unsigned integer.
%[] Scan for a set of characters.


Reading Strings

%s causes scanf() to read characters until it encounters a white-space character (RETURN, TAB or space). The characters read are placed in a character array pointed to be the corresponding argument, and null-terminated.

Unlike gets(), which reads a string until RETURN is typed, scanf() reads a string until the first white space is encountered.


The %n Specifier

The %n specifier instructs scanf() to assign the number of characters read at the point at which the %n was encountered to the variable pointed to by the corresponding argument.


Using a Scanset

The ANSI standard added the new scanset feature. A scanset defines a set of characters which may be read and assigned to the corresponding character array.

A scanset is defined by placing the characters inside square brackets prefixed with a %, as in the following example:

     %["XYZ"]

scanf() will then continue to read characters and continue to put them into the array until it encounters a character not in the scanset. For example, given the following code:

     scanf(%d%[abcdefg]%s", &i, str, str2);
     printf(%d %s %s, i, str, str2);

entering 123abcdtye followed by ENTER would display:

     123 abcd tye

because the t is not part of the scanset, causing it and the remaining characters to be put into str2.

If the first character in the set is a ^, scanf() will accept any character not defined by the scanset. A range may be specified using a hyphen. Scansets are case sensitive.


The Need For Addresses

All the variables used to receive values through scanf() must be passed by their addresses, which means that all arguments must be pointers to the variables used as arguments. This is, of course, C's way of creating a call-by-reference, which is a way of allowing a function to alter the contents of its calling argument. This is illustrated in the following example:

     scanf("%d", &count);
     scanf("%s", str);

The second line in the above code works because an array name, without an index, is the address of the first element of the array. Hence the & operator is not required.


Format Modifiers

An integer, placed between the % and the format, limits the number of characters read for that field. (Any characters in the input stream outside this limit will be placed in the relevant variable at the next scanf() call.)

l placed in front of f, e and g causes scanf() to assign the data to a double. L tells scanf() that the variable receiving the data is a long double.


Suppressing Input

scanf() may be told to read a field but not assign it to any variable by preceding that field's format code with a *. For example, given:

    scanf("%d*c%d", &x, &y);

the coordinate pair 10,10 could be entered. The comma would be read but not assigned to anything.

Assignment suppression is particularly useful when part of what is input needs to be suppressed.

Prior Chapter · Index · Next Chapter


Copyright © 1996, 1997, 1998. Last Update to This Page: 1998/10/24
This Page Maintained by: radar pangaean * * * Original Author: K.J.Bricknell
The MOST web site is built and maintained by the voluntary efforts/donations of our members.