简体   繁体   中英

Counting whitespaces -argc/argv in C

I would like to count whitespaces, like ' ' (ASCII SP or 32). I have to pass the arguments using the command line. So for example, I enter Hello World and would like to receive the amount of whitespaces, in this case the result should be 2.

I already tried following: Text = Hello World

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

int main(int argc, char* argv[]){
    int spaces = 0;
    char* mystring = argv[1];
    int size = strlen(argv[1]) + strlen(argv[2]);
     for(int i = 0; i < size; i++){
         if((*(mystring + i)) == ' '){
             spaces++;
             printf("%d\n", spaces);
         }
     }
}

I know that *(argv + 1) is Hello ( or ASCII number) and *(argv + 2) = World and thats the problem I do have. How can I count the spaces between the argv[n] ? The amount of whitespaces can be different, so therefore I don't want to code like If(argc > 1){ spaces++;} .

Can someone help?

Best regards,

Keita

在双引号中传递字符串,例如“Hello World”。

If you execute:

$ a.out Hello      world # There are 5 spaces between both args here.

the shell is going to extract the arguments to the command by splitting the input command into arguments at the positions of a sequence os spaces (a contiguous sequence of spaces, tabs and/or newlines), and comments (like the above one) are eliminated from imput, so if you issue the command above, you'll get an argv like this:

int argc = 3;
char *argv[] = { "a.out", "Hello", "world", NULL, };

in case you use quotes to delimit arguments, you can issue

$ a.out "Hello     world"  # there are also 5 spaces between the words.

and it that case you will get something like:

int argc = 2;
char *argv[] = { "a.out", "Hello     world", NULL, };

In that case you'll get the spaces into the arguments.

Important

You don't check the number of arguments passed to a.out so in the case you post, you can be trying to pass NULL pointer to strlen() which will result in Undefined Behaviour. This is an error, for your program to work correctly you might do the following (i have corrected some other errors and commented them in comments in your code):

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

int main(int argc, char* argv[])
{
    int spaces = 0;
    int arg_ix;  /* index of the argument to consider */
    for (arg_ix = 1; arg_ix < argc; arg_ix++) { /* so we don't check more arguments than available */
        char *mystring = argv[arg_ix];
        int size = strlen(mystring);
        for(int i = 0; i < size; i++) {
            if(mystring[i] == ' '){  /* why use such hell notation? */
                spaces++;
            }
        }
    }
    printf("%d\n", spaces); /* print the value collected at the end, not before */
}

and this code could be simplified (taking advantage of mystring being a pointer, by moving the pointer until we reach the end of string (pointing to a \\0 char) with this approach (it also avoids to compute the string length, which makes another pass on the string ---unnecessary)

#include <stdio.h>
/* string.h is not needed anymore, as we don't use strlen() */

int main(int argc, char* argv[]){
    int spaces = 0;
    int arg_ix;
    for (arg_ix = 1; arg_ix < argc; arg_ix++) {
        char* mystring = argv[arg_ix];
        for( /* empty */; *mystring != '\0'; mystring++) {
            if(*mystring == ' '){
                spaces++;
            }
        }
     }
     printf("%d\n", spaces);
}

and finally, you have a <ctype.h> header with functions like isspace(c) to check if a character is a space (in this case, it checks for space and tab characters.

#include <stdio.h>
#include <ctype.h>

int main(int argc, char* argv[]){
    int spaces = 0;
    int arg_ix;
    for (arg_ix = 1; arg_ix < argc; arg_ix++) {
        char* mystring = argv[arg_ix];
        for(; *mystring != '\0'; mystring++) {
            if(isspace(*mystring)){
                spaces++;
            }
        }
     }
     printf("%d\n", spaces);
}

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM