In C,how do we accept an input that has several lines and then the output has the lines in reverse order (without changing the order of the words in each line).
For example:
Input: Line 1 Line 2 Line 3 Line 4 Output: Line 4 Line 3 Line 2 Line 1
In C,how do we accept an input that has several lines and then the output has the lines in reverse order (without changing the order of the words in each line).
For example:
Input: Line 1 Line 2 Line 3 Line 4 Output: Line 4 Line 3 Line 2 Line 1
The solution is simple. Assuming that lines
is an array of lines (without trailing newlines) of length size
, one should do the following loop:
for(i = size - 1; i >= 0; --i)
puts(lines[i])
I.e., you just output the lines in the reverse order: starting from the last one and ending with the first.
About the question "How to input and store lines": there are several options. Input can be performed with the use of getline
(a POSIX function) or fgets
functions (you may manually drop trailing newlines, if necessary); don't use gets
- it's evil. You have to use a loop to input lines. Lines can be stored either in a static or in a dynamically expanding (via realloc
) array - based on your task. Or you can perform a not-so-smart trick: write a recursive function which makes use of the stack for storing lines (pseudocode):
function reverseLines():
{
string line;
input(line);
if not end-of-input():
{
reverseLines();
output(line);
}
}
But if your input is large enough, you will meet the stack overflow error.
If you can set some maximum line length, you can read lines using standard C fgets()
function. If you're on recent POSIX-compliant operating system, or have GNU glibc, you can use getline(), which will allocate memory for line, so you can read any line length. See this answer here at SO.
For each line, you will then get char*
pointer.
If you can set maximum number of lines to support, you can use char *lines[MY_MAX_LINE_COUNT]
to store the pointers, and then simply print in reverse order from array. Better is to implement a very simple linked list which allows prepending (this is probably the most simple linked list code there can be, basically a stack with just push, no need for pop...), and then print lines from that when all have been read.
For the simple case, to avoid allocating a linked list struct for every line, it might be best to store the char*
line pointers into an array, which is grown using realloc()
:.
First the variables that are need:
int arraysize = 16; /* any size will do, 16 is nice round number */
char *lines[16] = malloc(sizeof(char*) * arraysize);
int linecount = 0;
Then loop to get input:
while(/* test for eof or whatever */) {
char *line = /* code to get the line */;
if (linecount == arraysize) {
arraysize *= 2;
lines = realloc(lines, sizeof(char*) * arraysize);
}
lines[linecount] = line; /* old lines are at indexes 0..(linecount-1) */
++linecount;
And printing loop for that:
for(int index = linecount-1 ; index >= 0 ; --index) {
puts(lines[index]); /* if line has newline stripped, else printf("%s", lines[index]);
}
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
void reverseLines(void);
int main (void) {
reverseLines();
return 0;
}
void reverseLines(void) {
char *line;
size_t len = 0;
getline(&line, &len, stdin);
if (strcmp(line, "") != 0) // NOT end of input
{
reverseLines();
printf ("%s", line);
}
free (line);
}
/* References:
*
* http://www.gnu.org/software/libc/manual/html_node/Line-Input.html
* http://souptonuts.sourceforge.net/code/getline.c.html
*/
Thanks to @nameless for pseudocode and @hyde for the getline function(I didn't know it).
You can use a loop to get these lines... i.e.
for(...) {
scanf(...); /* or use getline() here*/
}
And also use a loop to print it, such as the above answer.
And it is simple, if you are a new guy in programming, please practice more and more. :)