2017-02-22 37 views
0

ЭТО РАЗЛИЧНЫЙ ВОПРОС. ДРУГОЙ ОДИН КОНЦЕПТИЧЕСКИЙ МИН. Это просто пример.Как отформатировать введенную пользователем строку?

Так вот мой код:

main() 
{ 
     char input[150];                  //Create a variable of type char named input to store user input 

     printf(" Enter a standard line: ");              //Ask the user for some standard input 

     if (fgets(input, 150, stdin) == NULL)             //Initiate a series of checks to make sure there is valid input 
     { 
       puts(" End-of-File or Input Error Detected. ");         //If the end of the file is reached or there is a problem with input output a message 
     } 
     else if (input[0] == '\n')                //If the user neglected to enter anything output a message 
     { 
       puts(" Oops! Looks like you forgot to enter something! "); 
     } 
     else 
     { 
       printf(" Here's what you entered: %s ", input);         //If there is valid user input echo it back to the user 

      int i = 0; 
      while (input[i] != '\n') 
      { 
        if (input[i] = '/') 
          putchar("%2F"); 
        i++ 

      } 

     } 
} 

я должен заменить и отрегулировать входную линию соответственно путем замены определенных символов с их ASCII-код.

Например: 1. пользователь вводит: google.COM/search?client
2. Изменения программы и печатает обратно к пользователю, как: GOOGLE.com% 2FSEARCH% 3FCLIENT

Но система дает мне это длинное сообщение об ошибке при попытке скомпилировать мой код.

/home/cs/carroll/cssc0154/One/p1.c: In function 'main': 
/home/cs/carroll/cssc0154/One/p1.c:41:5: warning: passing argument 1 of 'putchar' makes integer from pointer without a cast [enabled by default] 
    putchar("%2F"); 
    ^
In file included from /home/cs/carroll/cssc0154/One/p1.c:15:0: 
/usr/include/stdio.h:580:12: note: expected 'int' but argument is of type 'char *' 
extern int putchar (int __c); 

Куда я иду не так?

+2

' "% 2F"' немного длиннее, чем один символ ... –

+0

@EugeneSh. Я это понимаю. Но я должен заменить символы типа «/» на их коды ASCII, так что это действительно не поможет. – Polly

+1

Затем используйте правильную функцию для печати более одного символа. Вы уже использовали 'puts' и' printf'. –

ответ

0

Вы пытаетесь передать 3 символа% '' 2 '' f 'функции putchar(), которая ожидает одного символа.

Рассмотрите возможность использования printf("%%2f") вместо putchar("%2f"), вы получите тот же результат в стандартный вывод.

Примечание: вам нужно избежать символа процента в printf с помощью (%).

+0

Итак, я использовал 'puts («% 2f »);' но он заменил всю строку и распечатал только '% 2F'. – Polly

+0

Ну, это неожиданно. putchar(), очевидно, принимает символ в форме 'int' (обычно 4 байта). Вы являетесь строкой: «% 2f» имеет 3 символа и автоматически добавляет терминатор «\ 0» для строковых литералов, поэтому вы не получаете ошибку и, вероятно, можете скомпилировать. Но вы, по крайней мере, получаете предупреждение от компилятора. Результат от вызова функции 'putchar()', которая явно ожидает, что один символ окажется неожиданным, если вы передадите его более одного. – Fredster

+0

Хм я вижу. Какая головоломка. Ну, как насчет этого, знаете ли вы, как сложить длинную строку ввода пользователя? Как и после определенного количества символов, он перерывается на новую строку. – Polly

0

Поскольку у меня нет точки комментировать выше ...

фона:

  • C не действительно «струны» - это есть указатели на символы, которые она обрабатывает очень похоже на массивы.
  • Стандартные функции библиотеки ожидают, что последнее значение в массиве будет '\ 0', и они будут обрабатывать символы до тех пор, пока не будет прочитан один из этих «нулевых символов».

Эта линия:

putchar("%2F"); 

передает указатель (символ *) к 'putchar()' вместо целое.

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

Большинство машин/компиляторов в настоящее время являются LP64. Это означает, что «putchar()» ожидает 32-битное целое число, и вы предоставляете 64-битный указатель.

Причина этого кода:

int i = 0; 
while (input[i] != '\n') 
{ 
    if (input[i] == '/') 
     puts("%2F"); 
    i++  
} 

печатает «% 2F» (я полагаю, учитывая вход «google.COM/search?client») происходит потому, что он находит «/» один раз, и печатает строка, которую вы указали «% 2F». Ни один другой символ не выполняет оператор печати.
Если вы добавили:

int i = 0; 
while (input[i] != '\n') 
{ 
    if (input[i] == '/') 
     puts("%2F"); 
    else 
     putc(intput[i]); 
    i++  
} 

вы получите

google.COM%2F 
search?client 

потому что путы() печатает символ новой строки ('\ п') после печати его ввода.

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

Е() печатает «отформатированные» текст, который использует «%», чтобы указать параметры форматирования, поэтому печать одного «%» требует, чтобы «убежать» он, который выглядит как «%%»

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

if (input[i] == 'CHAR') printf("%%XX"); 
else if (input[i] == ... 

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

Если символ найден, я печатаю '%', за которым следует шестнадцатеричное значение символа. «% 02X» сообщает printf(), чтобы записать шестнадцатеричное значение не менее чем с двумя символами и поставить 0 впереди, если ему нужно заполнить это значение. В принципе, он никогда не напишет «9», а вместо этого напишет «09».

Вы также можете использовать функции isalpha() ... isalphanum() ... ispunct() для идентификации типов символов, которые вы должны кодировать.

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

int main(int argc, char ** argv) 
{ 
    char *decodeStr = "/:\\+"; 
    int decodeLen = strlen(decodeStr); 

    while(--argc >= 0 && ++argv && *argv){ 
     char *str = *argv; 
     for(int i = 0; str[i] != '\0'; i++){ 
      if (NULL != memchr(decodeStr, str[i], decodeLen)) 
       printf("%%%02X", str[i]); 
      else 
       putchar(str[i]); 
     } 
     putchar('\n'); 
    } 
    return 0; 
} 

Пример запуска:

./test http://google.com/atest+with+things 
http%3A%2F%2Fgoogle.com%2Fatest%2Bwith%2Bthings 
+0

О, боже мой, большое спасибо! Я сейчас попробую! – Polly

+0

Итак, для целей этого класса я должен использовать компилятор gcc и, по-видимому, он не нравится для циклов. Спасибо за вашу помощь. Может быть, я могу как-то настроить код так, чтобы компилятор gcc ему понравился. – Polly

+0

@Полный gcc не должен иметь никаких проблем с этим. Какая ошибка вы получали? (Если это было что-то вроде «начальных деклараций цикла», попробуйте передать «-std = c99» в gcc или переместить объявление «int i» из цикла. Возможность объявлять переменные в заголовках цикла wasn ' t на языке изначально, а gcc по умолчанию использует старый стандарт.) – Ray