Ограничить пробелы до одного в тексте - c
Я читаю через K&R, и вопрос заключается в следующем: написать программу, чтобы скопировать ее входные данные на свой выход, заменяя каждую строку одного или нескольких пробелов одним пробелом. Я думаю, что знаю, что мне нужно сделать, настроить логическое значение, чтобы знать, когда я в космосе или нет. Я пытался и не удалось. Я нашел этот код, и он работает, я изо всех сил пытаюсь выяснить, что мешает писать пространство. Я думаю, что у меня может быть это, но мне нужно разъяснение.
#include <stdio.h>
int main(void)
{
int c;
int inspace;
inspace = 0;
while((c = getchar()) != EOF)
{
if(c == ' ')
{
if(inspace == 0)
{
inspace = 1;
putchar(c);
}
}
/* We haven't met 'else' yet, so we have to be a little clumsy */
if(c != ' ')
{
inspace = 0;
putchar(c);
}
}
return 0;
}
Я создал текстовый файл для работы, текст гласит:
so this is where you have been
После 's' на 'this' состояние меняется на 1, потому что мы находимся в пространстве. Пробел записывается, и читается следующий пробел. Итак, теперь мы входим:
while((c = getchar()) != EOF)
{
if(c == ' ')
{
if(inspace == 0)
{
inspace = 1;
putchar(c);
}
Но inspace не 0, а 1. Так что же происходит? Код пропускает, возвращая 0;, ничего не записывая и просто продолжает цикл while? вернуть 0; находится вне цикла, но это единственный способ увидеть, что значение не возвращается.
4 ответа
С этой точки зрения:
if(c == ' ')
{
if(inspace == 0) // <-- here
Если inspace равно 1, он не будет выполнять тело if, он перейдет к:
if(c != ' ') {
И до тех пор, пока c == ' ' выше будет ложным, он пропустит тело if и перейдет к:
while((c = getchar()) != EOF) {
И это будет продолжаться до конца файла или до (c != ' ')
оценивает как истинное. Когда с не является пробелом:
if(c != ' ')
{
inspace = 0;
putchar(c);
пробел обнуляется, и символ печатается.
Когда inspace равен 1, а c - это выражение:
inspace == 0
оценивает в 0 и код
inspace = 1;
putchar(c);
не исполняется.
Затем программа перейдет к следующей итерации цикла while, если сможет, но не вернет 0, пока цикл while не закончится.
Вы можете упростить цикл while для этого кода:
while((c = getchar()) != EOF)
{
if(c == ' ')
{
if(inspace == 0)
{
inspace = 1;
putchar(c);
}
} else
{
inspace = 0;
putchar(c);
}
}
Если условие в операторе if не является истинным, следующее выражение не выполняется. Это означает, что все внутри соответствующих скобок пропускается, и выполнение возобновляется "после" закрывающей скобки.
Поскольку следующий оператор if также ложен, внутри этой итерации цикла for ничего не делается.
Да, в случае, который вы упомянули, он ничего не записывает и продолжает цикл while и получает следующий символ. Если следующий символ снова будет пробелом, он будет делать то же самое, то есть перейти к следующей итерации без печати. Всякий раз, когда он находит первый не пробел, он устанавливает значение пробела в 0 и начинает печать.
Цикл while будет прерываться всякий раз, когда getchar будет вызывать EOF. Тогда программа вернет 0.