singlepost

Странности C++ (scanf) ? + cin/cout & UNICODE << На главную или назад  

Хорошая статья по scanf: //www.rsdn.ru/forum/cpp/1128588.1.aspx
==================
здравствуйте.
юзаю visual studio 2008 pro
подключены stdio.h stdlib.h
собственно код

int x=0,y=0;
scanf("%c%d",&x,&y);

ввожу A1
все как надо вводится x=65,y=1;

далее сразу идет код

int fx=0,fy=0;
scanf("%c%d",&fx,&fy);

вот тут начинается вся кака, ставлю брейк поинт после этой строки, и вижу что
fx=10, fy=0;
независимо от того, какие координаты (это шахматные координаты) я вводил
как так?

вот так нормально, но неудобно мне

scanf("%c%d %c%d",&x,&y,&fx,&fy);

у меня идей нет вообще
помогите :)

31 ответов в теме “Странности C++ (scanf) ? + cin/cout & UNICODE”

  1. 31
    Константин Смотритель ответил:

    #28, #29 – это ты к чему? О_о
    Плюс, ты не проверил сброс буфера по \n в cerr
    (в cout и не должно сбрасываться =)

    #30 Как я указал выше, это есть в документации по STL

  2. 30
    ответил:

    всем спасибо большое. интересно почитал.
    моя проблема решилась так:
    scanf("%c %d");
    scanf("%*c%c %d");

  3. 29
    Валерий Лаптев ответил:

    Про сброс буфера по endl писал Николай Джосатис (Джосьютис) в своей книге о Стандартной библиотеке С++.

  4. 28
    Валик Захаренко ответил:

    _main proc near
    push bp
    mov bp,sp
    ;
    ; {
    ;printf("\n");
    ;
    mov ax,offset DGROUP:s@
    push ax
    call near ptr _printf
    pop cx
    ;
    ; }
    ;
    pop bp
    ret
    _main endp

    сброс буфера ненаблюдается, хотя он, вполне возможно, зашит в _printf

    дайте, пожалуйста, ктото ссылку на документацию С

  5. 27
    Валик Захаренко ответил:

    _main proc near
    push bp
    mov bp,sp
    ;
    ; {
    ;cout << "\n";
    ;
    mov ax,offset DGROUP:s@
    push ax
    mov ax,offset DGROUP:_cout
    push ax
    call near ptr @@ostream@$blsh$qpxzc
    pop cx
    pop cx
    ;
    ; }
    ;
    pop bp
    ret
    _main endp

    а это подтверждает, что использование printf, без спецификаторов(%) менее влияет на продуктивность нежели cout

  6. 26
    Валик Захаренко ответил:

    \n непонятно, сбрасывает или нет, //www.rsdn.ru/forum/cpp/23758.flat.aspx – сбрасывает, в //forum.ixbt.com/topic.cgi?id=26:3602 (см пост rGlory) – не сбрасывает, непонятно откуда ноги ростут, хотя я склоняюсь к тому, что всетаки сбрасывает

  7. 25
    Константин Смотритель ответил:

    Нет, не сбрасывает – см. документацию.
    P.S. Чтобы сбросить буфер, вызывается спец. метод (sync() вроде). \n – это байт, он ничего вызвать не в состоянии.

    Хотя, я "слышал слухи", что cerr сбрасывает и по /n, но, вероятно, это спецреализация cerr? Проверишь у себя? =))))

  8. 24
    Константин Смотритель ответил:

    Да, без *; исправил. Сама str пишется без взятия адреса (&) – трабл разработчиков библиотеки (все переменные пишутся с &, кроме строк =)))

  9. 23
    Валик Захаренко ответил:

    извените, забираю слова нащот endlназад, подтверждение моей неправоты:
    //www.rsdn.ru/forum/cpp/1558934.1.aspx Я на С++ писал неочень долгий промежуток времени, примерно пол года(причом это были мои первые шаги в програмировании), в оправдание скажу, что в книге Шилда "Полный справочник по С++", а также в книге Солтера и Клепера "С++ для профисионалов" о endl говорится как о манипуляторе перехода на новою строку, да и в инстетуте давали за "\n" по рукам. Ищераз извените

  10. 22
    Константин Смотритель ответил:

    #22 Да, endl() точно сбрасывает буфер //www.cplusplus.com/reference/iostream/manipula...

    А вот ends() не сбрасывает, но строки разделяет; чем можно пользоваться в своих реализациях буферизированного ostream
    //www.cplusplus.com/reference/iostream/manipula...

  11. 21
    Валик Захаренко ответил:

    #21 char* str[2]; – вы действительно имели ввиду указатель на указатель или всеже * там не должно быть?

  12. 20
    Константин Смотритель ответил:

    #17 А так?
    char str[2];
    sscanf("%s",str);

    Или ты о чём?

  13. 19
    Константин Смотритель ответил:

    #16 Да, моё "это удобнее" надо понимать как "обычно это удобнее" – я же для начинающего ответил =)))

    По поводу скорости работы – ничего не путаешь? Хотя, тут многое зависит от реализации, конечно. Но я про другое – не мог ты попутать с буферизацией, например, или ещё что?… (про буферизацию std::endl вроде сбрасывает буфера, что может давать тормоза… наверное =)

    #18 +1 но см. чуть выше про буфер (хотя, вроде его только std::flush и std::ends сбрасывают?… надо доки читать =)

    А, ну вот, #19 тоже по поводу бууфера вывод подтверждает =))

    P.S. #18 тут речь идёт о том, что scanf и подобные фйнкции с модификаторами могут использоваться, например, так:
    scanf("%s asd %s(%d)",…)

    Т.е. указывать сразу на форматную строку. Паша, ты это имел в виду? =)

    P.S. Пробелы вроде там заюзать не получится… смотрите документацию на scanf!

    Хорошая статья //www.rsdn.ru/forum/cpp/1128588.1.aspx

  14. 18
    Валерий Лаптев ответил:

    Захаренко.
    endl ОЧЕНЬ касается рантайма. endl – это манипулятор, который освобождает буфер. Сами понимаете, что освобождение буфера – это как минимум переписывание в системный буфер… :) При отсутствии endlf освобождение буфера выполняется только при его заполнении до конца, то есть ГОРАЗДО реже.

  15. 17
    Валик Захаренко ответил:

    Не знаю, на С++ сin идеальное решение(как по мне), а вот в С scanf это зло, незлюбил его по той причине, что сильно он уж дубовый, чтобы зделать приметивного антидурачка сколько проблем, хоть придумывать велосипед плохо, но зделать функцию считки(примеру инта) с использованием getch() или getche() (ни помню кто из них печатает вводимое на дисплэй), всегда гибко, да и зделал раз используеш всегда

    Касательно разници cin и scanf (ну аналогично cout printf), если говорить о производительности, давайте загляним на проблему с точки зрения теории компиляторов:

    зчитка запись в консоль реализована на асме и встроенна в компилятор, так что в этом плане разници никакой, в надстройках несложно понять, что cin это красивый пример полиморфизма, хоть в большистве случаев решается ище на стадии компиляции(особенно если речи идет о стандартных типах данных), так что накладные росходы касаются только дополнительных вложенностей стэка. А вот scanf принимает кучу спецификаторов, что само собой говорит, о наличии свичей или ифов(пускай даже на асемблере), кроме того функции с переменным количеством параметров, ОЧЕНЬ накладна в плане быстродействия.Вывод думаю на лицо.

    сказаное о endl – полный бред, поскольку endl на уровне компиляции заменяется на "\n" или на "\n\r" зависимо от платформы, и никак не касается рантайма

  16. 16
    Павел Потапов ответил:

    Если не юзать endl в конце каждой строки, то cout тормозит не намного сильнее printf.

    А вот где найти достаточно усердного пользователя, чтобы увидеть разницу cin и scanf, я вообще не представляю :)

  17. 15
    Пашка Джиоев ответил:

    когда надо читать/писать большие объемы данных, становится сильно заметно, что cin/cout намного медленнее, чем printf/scanf.
    Более того, лично мне намного удобнее пользоваться printf и scanf.
    ЗЫ Я не против использования scanf_s.

  18. 14
    Константин Смотритель ответил:

    Паш, это несекьюрная функция, она deprecated.

  19. 13
    Константин Смотритель ответил:

    Во, даже ссылку нашёл спецом для тебя =) //msdn.microsoft.com/en-us/library/9y6s16×1(VS.80).aspx

    "These functions are deprecated because more secure versions are available; see scanf_s, _scanf_s_l, wscanf_s, _wscanf_s_l."

  20. 12
    Константин Смотритель ответил:

    #11 +1, это удобнее чем scanf_s =)

    Как сдружить cin/cout с UNICODE?

    Вот есть немного инфы (раздел I/O Stream): //www.i18nguy.com/unicode/c-unicode.html

    Вот, собственно, описание wcout/wcin: //msdn.microsoft.com/en-us/library/zh80×809.aspx

    Странно, что MS не сделали tcout/tcin самостоятельно О_о

    Хотя, вот здесь есть std::tcout //wcp.codeplex.com/
    Кто найдёт в МСДН? Походу, это выдумка codeplex'a

  21. 11
    Пашка Джиоев ответил:

    #10 где написано, что это дурной тон:

  22. 10
    Сергей Старовой ответил:

    Сделай тип для координаты, перегрузи ему оператор >> и делай cin>>coord;
    так на порядок удобнее же, и бонусом идет страховка от неправильного ввода пользователя )

  23. 9
    Николай Марков ответил:

    это дурной тон …

  24. 8
    ответил:

    ввожу как символ, чтобы записать аски код.

    хочу использовать scanf, привык..

  25. 7
    Павел Гаглоев ответил:

    Зачем используешь %с в scanf для первого числа?

  26. 6
    Nickolay White ответил:

    Видимо для разбора вида C4
    Правда я бы сначала считал это, а потом бы разобрал

  27. 5
    Николай Марков ответил:

    у тебя же C++
    в нем для ввода есть "std::cin << x;"

  28. 4
    Dante-Kun Desu ответил:

    cin >> x
    небольшая поправка

  29. 3
    ответил:

    хм. помогло частично. все таки как правильно это обойти?

  30. 2
    ответил:

    хм.
    scanf("%c%d\n",&x,&y);
    помогло.
    блин, всего то..
    спасибо, я почему то не догадался)

  31. 1
    Nickolay White ответил:

    Дык, 10 – это у тебя перевод строки. Когда Enter нажимаешь

Клуб программистов работает уже ой-ой-ой сколько, а если поточнее, то с 2007 года.