2015-05-11 2 views
-2

Я пытаюсь решить эту проблему как можно меньше строк кода.Ошибка в программе C++ во время простого цикла

постановка задачи:
кому-то удалось поздороваться, если несколько букв могут быть удалены из набранного слова так, что это привело слова «привет» ... Я проверяю, может ли он или не

#include <iostream> 
int main() { 
    char c; 
    int i=0; 
    while(i!=5 && (cin>>c) && c!='\n'){ 
     if(c=="hello"[i]) 
      i++; 
    } 
    cout<<((i==5)?"YES":"NO"); 
} 

Есть ошибка, когда она должна печатать «НЕТ». Программа ожидает большего ввода. Я думаю, что цикл не заканчивается до i==5, но он никогда не заканчивается, когда c=='\n'.

+2

i + = (c == "hello" [i]) делает предположение, что true == 1. Это не обязательно так. do i + = ((c == "hello" [i])? 1: 0) – pm100

+1

Фактически предполагать, что true - это 1: ok: стандарт C++ §4.7/4 гласит: «Если тип источника - bool, значение false преобразуется в ноль, а значение true преобразуется в единицу."(Уродливый, но легальный) –

+0

_" plz "_ Не могли бы вы объяснить более подробно, что ваш вопрос имеет отношение к немецкой аббревиатуре для _postal code_ –

ответ

2

Прежде, чем вы упакуете свою программу, чтобы свести к минимуму LOC (и я предполагаю, что у вас есть действительно повод заботиться об этом, потому что в противном случае это глупо) сделать все правильно!

Попробуйте поставить тест i! = 5 ПЕРЕД ЦИН >> c test. В противном случае вы прочтете один дополнительный символ, когда получите «привет»

Редактировать: Чтобы быть ясным, код в вопросе теперь изменен, чтобы включить это предложение.

+0

Я изменил цикл, проверьте его. Это все та же проблема –

+0

Я думаю проблема связана с моим компилятором, потому что я отправил на Codeforces и получил AC –

+0

. Я думаю, это потому, что тестовый пример на Codeforces заканчивается EOF not \ n –

0

У вас есть цикл в то время

while(i!=5 && (cin>>c) && c!='\n') 
{ ... } 

... который можно переписать для облегчения отладки. В общем, вместо того, чтобы любая петля ...

while (X) 
{ Y } 

... Вы также можете написать ...

while (true) 
{ 
    if (!X) break; 
    Y 
} 

Для вашего цикла, который был бы этот код:

while (true) 
{ 
    if (!(i!=5 && (cin>>c) && c!='\n')) 
     break; 
    ... 
} 

Теперь я предполагаю, что вам известно об оценке короткого замыкания логического оператора И. Если нет, выполните поиск в Интернете для этого термина! С этими знаниями, вы можете переписать цикл так:

while (true) 
{ 
    if (!(i!=5)) 
     break; 
    if (!(cin>>c)) 
     break; 
    if (!(c!='\n')) 
     break; 
    ... 
} 

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

Наконец, все операторы >> по умолчанию пропускают пробелы, которые включают пробелы, табуляции и символы новой строки, поэтому ваша последняя проверка никогда не вызовет выхода из цикла. Вы можете сказать, что поток не пропускает пробелы, если это то, что вы хотите. Как это сделать должно быть очень просто узнать, используя другой веб-поиск. ;)

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