2017-02-14 3 views
1

Я новичок в языке C, может кто-то помочь в определении того, что я делаю неправильно в реализации программы, чтобы считать пробелы, вкладки и символы новой строки.Подсчет пробелов, вкладок и новой строки

Код:

#include <stdio.h> 
//Write a program to count blanks, tabs, and newlines. 
int main(){ 
    char str[100]; 
    printf("Enter the text"); 
    scanf("%s",&str); 
    int space=0; 
    int tabs=0; 
    int newLine=0; 
    int i=0; 
    while(str[i]!='\0'){ 
     if (str[i] == ' ') 
      space++; 
     if (str[i] == '\t') 
      tabs++; 
     if (str[i] == '\n') 
      newLine++; 
     i++; 

    } 

    printf("space:%d\ntabs:%d\nnew line:%d",space,tabs,newLine); 
    return 0; 
} 
+0

Что делать, если я хочу получить информацию от консоли вместо файла? @xing –

+0

Могу ли я использовать getchar(). Если да, то как?потому что я пробовал это, но он не дает правильного вывода –

+0

спасибо, что он помог @ xing –

ответ

0

Лучший способ проверить это для сравнения значений ASCII. C считает, что все символы находятся в ascii, и это касается C. Поэтому вместо сравнения пробела с пробелом сравните его с 0x20 (шестнадцатеричный код символа пробела ascii). Аналогичным образом выполняйте другие сравнения, и это должно быть лучше.

Не бойтесь печатать заявления на терминале о результате сравнения. Например, напечатайте символ, который проверяется, против того, что он проверяется, а также результат. Это поможет вам отладить то, что на самом деле происходит здесь. Не забудьте удалить эти инструкции печати, когда вы закончите.

PS Вот ссылка на таблицу ascii. http://www.asciitable.com

+0

Я думаю, что это не очень хорошая идея сравнить потому что в этом случае программа не может использоваться в системах, где используется, например, таблица EBCDIC. –

+0

В основном я бы согласился, но C - это стандарт ISO, который означает, что если вы используете C, то он использует ascii. Есть вариации, потому что ascii ограничивает, но тогда это не актуально. C очень похоже на C. Теперь это не делает мое решение более правильным ... это делает его менее переносимым и худшим передовым. –

+0

Почему вы думаете, что если C подтверждает стандарт ISO, то из этого следует, что все системы, в которых используется стандарт C, используют таблицу ASCII? Например, мэйнфреймы IBM используют таблицу EBCDIC. –

0

scanf функция, как она используется в вашей программе не является безопасным и не позволяет рассчитывать пробелы.


Примечание. Примите во внимание, что вместо

scanf("%s",&str); 
      ^^^ 

это будет правильно писать

scanf("%s",str); 
      ^^^ 

И в соответствии с функциональной магистралью C Стандарт без параметров должен быть объявлен как

int main(void) 

Лучше использовать функцию fgetc

Например

#include <stdio.h> 

int main(void) 
{ 
    unsigned int space = 0; 
    unsigned int tabs = 0; 
    unsigned int newLine = 0; 

    printf("Enter the text: "); 

    int c; 

    while ((c = fgetc(stdin)) != EOF) 
    { 
     switch (c) 
     { 
     case ' ': 
      ++space; 
      break; 

     case '\t': 
      ++tabs; 
      break; 

     case '\n': 
      ++newLine; 
      break; 
     } 
    } 

    printf("\nspace: %u\ntabs: %u\nnew line: %u\n", space, tabs, newLine); 

    return 0; 
} 

Если ввести текст, как этот

Hi, Marco Roberts 
Welcome to SO 

то вывод программы будет выглядеть

space: 4 
tabs: 0 
new line: 2 

Используйте Ctrl + Z или Ctrl + d (в зависимости на используемой системе) для прерывания ввода.

Другой подход может выглядеть следующим образом

#include <stdio.h> 

#define N 100 

int main(void) 
{ 
    unsigned int space = 0; 
    unsigned int tabs = 0; 
    unsigned int newLine = 0; 

    printf("Enter the text: "); 

    char str[N]; 

    while (fgets(str, sizeof(str), stdin)) 
    { 
     for (const char *p = str; *p; ++p) 
     { 
      switch (*p) 
      { 
      case ' ': 
       ++space; 
       break; 

      case '\t': 
       ++tabs; 
       break; 

      case '\n': 
       ++newLine; 
       break; 
      } 
     }   
    } 

    printf("\nspace: %u\ntabs: %u\nnew line: %u\n", space, tabs, newLine); 

    return 0; 
} 
0

Вы должны использовать fgets вместо scanf если вы хотите сделать консольный ввод (как сказал @xing в комментариях). Таким образом, мы будем иметь:

#define SIZE_MAX 255 

int main() { 
    char str[SIZE_MAX]; 
    int i; 
    int space; 
    int tabs; 

    printf("Enter the text : "); 
    fgets(str, SIZE_MAX, stdin); //stdin if it is a console input 
    // Careful, if the input length is shorter than the SIZE_MAX (here 255), 
    // Then a '\n' will be added at the end of your string. To counter it : 
    if(strchr(str, '\n') != 0) { //checks if there is a '\n' 
     str[strlen(str)-1] = '\0'; //changes it to a '\0' (end of string) 
    } 

    //For the verifications, you can do that : 
    for(i=0 ; i < strlen(str) ; i++) { 
     if (str[i] == ' ') { 
      space++; 
     } 
     if (str[i] == '\t') { 
      tabs++; 
     } 
    } 
    printf("\nspace : %d\ntabs: %d\n", space, tabs); 

    //NB : There will be no newLine because it is a console input. 
    return 0; 
} 
+0

@nsonore Как считать в этом случае новые строковые символы? :) –

+0

Ну, не будет новой строки для подсчета. Когда пользователь нажимает ввод, он проверяет ввод. Насколько я знаю, вы не можете добавить '\ n', когда используете консольный ввод. Однако если это файл, который вы хотите прочитать, то fgets будет читать до следующей новой строки, поэтому вам просто нужно создать счетчик для него. – Insonore

Смежные вопросы