Задача 1
После этого кода переменная line
содержит строку текста, включая символ новой строки от конца строки
while(fgets(line,sizeof line,stdin) != NULL)
{
Вот почему вы получаете "лишние" переводы строк. Значение ASCII для новой строки меньше, чем значение ASCII для «A». Вот почему символы новой строки заканчиваются в начале каждой строки, как только вы отсортировали символы. Например. "компьютер \ n" становится "\ ncemoprtu".
Чтобы решить эту проблему, вы можете удалить символы новой строки с конца ваших строк после цикла for
if(i > 0 && word[i-1] == '\n')
{
word[i-1] = '\0';
line[i-1] = '\0';
--i;
}
...
printf("%s %s\n",line,word); /* notice the addition of the newline at the end */
Это также решает проблему 2, но, пожалуйста, читайте дальше, чтобы увидеть, что было не так.
Задача 2
После цикла
for (i=0; line[i] != '\0'; i++) { /* */ }
Строка word
не будет оканчиваться нулем (кроме случаев слепой удачи, поскольку она готова к случайной неинициализированной памяти). Вот почему вы получаете «тер», потому что это часть данных, которые вы оставили, когда вы скопировали слово «компьютер» в word
.
Задача 3
После цикла
for (i=0; line[i] != '\0'; i++) { /* */ }
Значение line[i] != '\0'
всегда будет ложным. Это означает, что этот код ничего не будет делать
while (line[i] != '\0')
i++;
Это может сделать проблему более очевидной, если я заменим цикл for и цикл while на практически идентичный код, используя goto:
i=0;
begin_for_loop:
if(line[i] != '\0')
{
{
word[i]=line[i];
}
i++;
goto begin_for_loop;
}
begin_while_loop:
if(line[i] != '\0')
{
i++;
goto begin_while_loop;
}
(кстати, большинство профессиональных программистов сделают что угодно, от смеха до крика на вас, если вы упомянули об использовании goto :) Я использую это здесь только для иллюстрации сути)
Совет, который я нахожу удобным, - это нарисовать мои массивы, переменные и т. Д. На листе бумаги, а затем проследить каждую строку моего кода (опять же на бумаге), чтобы отладить, как он работает.