0

The question is to find spaces between the string. And if spaces are detected the next word should be printed in the next line. For e.g "This is C" It would be printed as: This\n is\n C

#include <stdio.h>
#include <stdlib.h>

int main()
{
    char str[20];
    int a,i;
    scanf("%[^\n]", str);
    a=strlen(str);
    for(i=0;i<a;i++)
    {
        printf("%s",str[i]);
        if(str[i]==0)
        {
          printf("\n");
        } 
    }
    return 0;
}

How do I make this code work?

J...S
  • 5,079
  • 1
  • 20
  • 35
  • Use `fgets(str, sizeof str, stdin)` instead of `scanf("%[^\n]", str);`. Follow with `str[strcspn(str, "\n")] = 0;` if you want to lop off a potential trailing `'\n`'. – chux - Reinstate Monica Jun 17 '18 at 04:37
  • Use a temporary pointer? – machine_1 Jun 17 '18 at 04:44
  • 2
    the posted code is missing the statement: `#include ` to expose the prototype for the function: `strlen()` Which, BTW, returns a `size_t`, not a `int` – user3629249 Jun 17 '18 at 04:51
  • 2
    when calling any of the `scanf()` family of functions: 1) always check the returned value (not the parameter values) to assure the operation was successful. 2) when using the input format specifiers '%s' and/or '%[...]', always include a max characters modifier that is 1 less than the length of the input buffer as these format specifiers always append a NUL byte and to avoid any possibility of a input buffer overflow – user3629249 Jun 17 '18 at 04:54
  • 3
    Use [`strtok()`](http://www.cplusplus.com/reference/cstring/strtok/) and give space as delimiter and print the tokens. – H.S. Jun 17 '18 at 04:54

4 Answers4

3

Use isspace() function. Also, don't forget that in C strings are terminated by '\0'.

Look at the man page for more detail.

alk
  • 69,737
  • 10
  • 105
  • 255
Mohmmed
  • 77
  • 9
3

In your program, make

printf("%s",str[i]);

to

printf("%c",str[i]);

as str[i] is character not a string and the format specifier for character is %c. %s for a string.

And change

    if(str[i]==0)
    {
      printf("\n");
    }

to

    if(str[i]==' ')
    {
      printf("\n");
    }

inorder to print a newline each time a space is detected.

And use a width specifier for scanf() like

scanf("%19[^\n]", str);

where 19 is the size of the str character array.

You might also want to check the return value of scanf() which is the number of successful assignments it did. In this case it should be 1.

Also, include string.h header file to use strlen() and there is no need to include stdlib.h.

And as noted in the comments section, strlen() returns a size_t not exactly an int although basically size_t is an unsigned integer.
See What is size_t in C and this.


Or you could use fgets() and strtok() like

char *ptr;
if( fgets(str, sizeof(str), stdin) )
{
    for(char *ptr=strtok(str, " "); ptr!=NULL; ptr=strtok(NULL, " "))
    {
        printf("\n%s", ptr);
    }
}

strtok() uses the characters in its second argument as delimiters to tokenize str.

Note that fgets() reads in the trailing \n as well. If you need to remove it, do

str[strlen(str)-1]='\0';

if the last character is a \n.

J...S
  • 5,079
  • 1
  • 20
  • 35
2

the following proposed code:

  1. performs the desired functionality
  2. cleanly compiles

and now, the proposed code:

#include <stdio.h>

int main( void )
{
    int ch;

    while( ( ch = getchar() ) != '\n' && EOF != ch )
    {
        if( ' ' == ch )
        {
            puts( "" );
        }

        putc( ch, stdout );
    }

    puts( "" );

    return 0;
}
user3629249
  • 16,402
  • 1
  • 16
  • 17
0

Your program is having undefined behavior here

printf("%s",str[i]);

because str[i] is of type char and you are printing it using %s format specifier which is used to printf null terminated array of characters.

From C Standard#7.21.6.1p9

If a conversion specification is invalid, the behavior is undefined.282) If any argument is not the correct type for the corresponding conversion specification, the behavior is undefined. [emphasis mine]

Also, avoid using scanf() for string input. If not used carefully, it can have the buffer overflow problem. You should use fgets instead.

Coming to your question: The question is to find spaces between the string. And if spaces are detected the next word should be printed in the next line.

As I have suggested in comment, you can use strtok() to do this by giving space as delimiter. The strtok() will split the input string into tokens. A point to note about strtok() is that it modifies the input string by being broken into smaller strings (tokens). If you are okay with it then you can do:

#include <stdio.h>
#include <string.h>
#include <stdlib.h>

#define BUF_SZ 20

int main() {
        char str[BUF_SZ];
        char *pch;

        if (fgets (str, BUF_SZ, stdin) == NULL) {
                perror ("fgets failed");
                exit (EXIT_FAILURE);
        }

        str[strcspn (str, "\n")] = 0;

        pch = strtok (str," ");
        while (pch != NULL) {
                printf ("%s\n", pch);
                pch = strtok (NULL, " ");
        }

        return EXIT_SUCCESS;
}

After while loop, the content of str is not same as it was before calling strtok() on it. Though, whether to modify the original input string or not doesn't make sense over here because after breaking it into tokens it is not more used.

Your question says - if spaces are detected the next word should be printed in the next line... If it is just about printing the words in new line, you can do:

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#define BUF_SZ 20

int main() {
        char str[BUF_SZ];
        int word_size = 0;
        int i = 0, start = 0;

        if (fgets (str, BUF_SZ, stdin) == NULL) {
                perror ("fgets failed");
                exit (EXIT_FAILURE);
        }

        str[strcspn(str, "\n")] = 0;

        for (i = 0; str[i] != '\0'; i++) {
                start = i;
                if (str[i] != ' ') {
                        word_size++;
                        if (str[i+1] != '\0')
                                continue;
                        start++;
                }

                if (word_size != 0) {
                        printf ("%.*s\n", word_size, str + start - word_size);
                        word_size = 0;
                }
        }

        return EXIT_SUCCESS;
}

This solution does not modify the input string but just parse it and if the space is detected next word printed in new line.

H.S.
  • 11,654
  • 2
  • 15
  • 32